diff --git a/ci/tools/openeuler-purl/.gitignore b/ci/tools/openeuler-purl/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..20e876632be43d1e98b2df6309f952254ff81576 --- /dev/null +++ b/ci/tools/openeuler-purl/.gitignore @@ -0,0 +1,145 @@ +### Python template +# Byte-compiled / optimized / DLL files +__pycache__/ +*.py[cod] +*$py.class + +# C extensions +*.so + +# Distribution / packaging +.Python +build/ +develop-eggs/ +dist/ +downloads/ +eggs/ +.eggs/ +lib/ +lib64/ +parts/ +sdist/ +var/ +wheels/ +share/python-wheels/ +*.egg-info/ +.installed.cfg +*.egg +MANIFEST + +# PyInstaller +# Usually these files are written by a python script from a template +# before PyInstaller builds the exe, so as to inject date/other infos into it. +*.manifest +*.spec + +# Installer logs +pip-log.txt +pip-delete-this-directory.txt + +# Unit test / coverage reports +htmlcov/ +.tox/ +.nox/ +.coverage +.coverage.* +.cache +nosetests.xml +coverage.xml +*.cover +*.py,cover +.hypothesis/ +.pytest_cache/ +cover/ + +# Translations +*.mo +*.pot + +# Django stuff: +*.log +local_settings.py +db.sqlite3 +db.sqlite3-journal + +# Flask stuff: +instance/ +.webassets-cache + +# Scrapy stuff: +.scrapy + +# Sphinx documentation +docs/_build/ + +# PyBuilder +.pybuilder/ +target/ + +# Jupyter Notebook +.ipynb_checkpoints + +# IPython +profile_default/ +ipython_config.py + +# pyenv +# For a library or package, you might want to ignore these files since the code is +# intended to run in multiple environments; otherwise, check them in: +# .python-version + +# pipenv +# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. +# However, in case of collaboration, if having platform-specific dependencies or dependencies +# having no cross-platform support, pipenv may install dependencies that don't work, or not +# install all needed dependencies. +#Pipfile.lock + +# PEP 582; used by e.g. github.com/David-OConnor/pyflow +__pypackages__/ + +# Celery stuff +celerybeat-schedule +celerybeat.pid + +# SageMath parsed files +*.sage.py + +# Environments +.env +.venv +env/ +venv/ +ENV/ +env.bak/ +venv.bak/ + +# Spyder project settings +.spyderproject +.spyproject + +# Rope project settings +.ropeproject + +# mkdocs documentation +/site + +# mypy +.mypy_cache/ +.dmypy.json +dmypy.json + +# Pyre type checker +.pyre/ + +# pytype static type analyzer +.pytype/ + +# Cython debug symbols +cython_debug/ + +#config +configs.json + +#logs +logs/ \ No newline at end of file diff --git a/ci/tools/openeuler-purl/.python-version b/ci/tools/openeuler-purl/.python-version new file mode 100644 index 0000000000000000000000000000000000000000..d20cc2bf020ea4d4e6b4237229024d03130d0203 --- /dev/null +++ b/ci/tools/openeuler-purl/.python-version @@ -0,0 +1 @@ +3.8.10 diff --git a/ci/tools/openeuler-purl/README.md b/ci/tools/openeuler-purl/README.md new file mode 100644 index 0000000000000000000000000000000000000000..28431181748697b1ac8484ea02da87eb0c031194 --- /dev/null +++ b/ci/tools/openeuler-purl/README.md @@ -0,0 +1,180 @@ +--- +typora-copy-images-to: ./img/ +--- + + + +# openeuler-purl + +## 介绍 +获取 openeuler 软件仓中所有软件包的 purl 的工具 + +## 软件架构 + +### 目录说明 + +- /bin:syft 的可执行文件目录位置,有 linux 和 windows 两个子目录,分别可以在两个不同的平台 (x64) 下运行。 +- /examples:syft 解析得到的结果示例,all_packages_purls.json 为批处理(syft.py)得到的结果,one_package_purls.json 为单次解析得到的结果示例。 +- /logs:程序的运行日志保存目录。 +- /syft-dev syft 程序源码 +- /img:说明文档中用到的一些图片。 + +## 快速使用 + +程序的整体运行分为四步: + +- 运行初始化,安装python环境以及依赖,编写配置文件。 +- 运行 download.py ,下载需要解析的 src.rpm 包到工作目录。 +- 运行 syft.py,解析工作目录下所有包的 purl +- 查看运行结果,检查运行日志。 + +### 1. 初始化环境 + +安装 python,版本需要 >= 3.8。 + +(建议新建一个虚拟环境)接下来安装必要的依赖。进入项目根目录,执行: + +```bash +pip install -r requirements.txt +``` + +复制 configs.temp.json ,并重命名为 configs.json , 修改其中一些必要的配置信息: + +```json +{ + "dir_path": "/home/test/rpm", + "mirror_host": "http://121.36.97.194", + "syft": "./bin/linux/syft", + "template": "./purl.json.tmpl", + "download_limit": 10, + "syft_limit": 10 +} +``` + +配置文件各项的作用: + +- dir_path: **必须配置**。主路径,工作目录,所有的的包会在下载到此目录下,并以版本号区分,syft 解析的结果也会存储在这个目录 +- mirror_host:**可选**。软件仓(镜像)的主机 +- syft:**必须配置**。syft 可执行文件的位置 +- template:**必须配置**。syft 解析所用模板的位置 +- download_limit:**可选**。 下载src rpm包的时候同时下载的文件数量 +- syft_limit:**可选**。解析src rpm包同时解析的文件数量 + +### 2. 下载待解析的包 + +在项目根目录,执行: + +```bash +python download.py +``` + +能看到进度条则代表正在下载,耐心等待即可。 + +![](.\img\image-20220914174732555.png) + +### 3. 开始解析 + +包下载结束后,同样是在项目根目录,执行: + +```bash +python syft.py +``` + +![](.\img\image-20220914201526168.png) + +执行结束后,最终结果会按系统版本输出到不同的目录:`$dir_path/$os_version/all_packages_purls.json` + +## 进阶使用 + +### 独立解析 + +`syft.py` 是批处理脚本,用于大批量生成解析结果,在某些情况下(测试或者验证结果)时,可能也需要独立解析单个包结果。 + +单独解析一个包的命令为: + +```bash +$syft_executable $rpm_source -o template -t $template_file +``` + +linux下: + +```bash +./bin/linux/syft ~/rpm/openEuler-20.03-LTS/packages/abattis-cantarell-fonts-0.111-2.oe1.src.rpm -o template -t ./purl.json.tmpl +``` + +windows下: + +```bash +./bin/windows/syft.exe F:\\rpm\\openEuler-20.03-LTS\\packages\\abattis-cantarell-fonts-0.111-2.oe1.src.rpm -o template -t ./purl.json.tmpl +``` + +### 日志文件介绍 + +不管是在包下载阶段或是解析阶段,程序都或多或少会出现异常情况,为了方便排错,程序记录了一些日志(项目 logs 目录下),下面介绍这些日志的作用。 + +首先是在下载阶段,总共会生成两种类型的日志: + +- download.log:记录整个下载过程所有输出的日志,包括异常记录。 +- download_error_list-`os_version`-LTS:当前 `os_version`下载失败的包列表,用于手动下载。 + +其次是在解析阶段,总共会生成三种类型的日志: + +- syft.log:记录整个解析过程所有输出的日志,同样包括异常记录。 +- syft_catalog_error_list-`os_version`-LTS.log:解析过程中,syft 解析 **输出结果为异常** 的包列表,这些包在解析时无法输出解析结果(purls)。 +- syft_catalog_none_list-`os_version`-LTS.log:解析过程中,syft 解析 **输出结果为空** 的包列表,这些包在解析时能够正常解析,但是无法获取到解析的结果(purls)。 + +包名后缀一定要为 src.rpm,不然无法解析 + +1. download.py 负责下载所有包到 `$dir_path/$os_version/packages`目录下,并按系统版本号($os_version)存放在不同的目录 +2. syft.py 负责解析下载下来的包,并将解析的结果按系统版本($os_version)输出到不同的目录下,最终的文件位置 + +## FAQ + +1 如果有新版本的系统,如何添加到下载并解析? + +> 首先确认镜像站 `$mirror_host` 根路径(如下图所示)中能找到到该版本系统对应的文件夹名字,假设为 openEuler-23.03-LTS。 +> +> ![](img/image-20220915010735394.png) +> +> 编辑 `download.py` , 在 35 行左右,找到: +> +> ```python +> version_name_list = [ +> "openEuler-20.03-LTS", +> "openEuler-20.03-LTS-SP1", +> "openEuler-20.03-LTS-SP2", +> "openEuler-20.03-LTS-SP3", +> "openEuler-20.09", +> "openEuler-21.03", +> "openEuler-21.09", +> "openEuler-22.03-LTS" +> ] +> ``` +> +> 在最后面加上 openEuler-23.03-LTS,那么在运行 `download.py` 批量下载时,便可以下载该版本系统的所有包。 + +2 如何自定义输出格式? + +> syft 支持输出多种格式,但是数据都过于冗杂,不符合项目需求,还好 syft 支持自定义模板。 +> +> 为了方便本项目需求,这边自定义了一个模板文件 `purl.json.tmpl`: +> +> ```go +> { +> "name": "{{.Source.Target | osBase}}", +> "purls": [ +> {{- $artifactLength := len .Artifacts -}} +> {{- range $index, $value := .Artifacts}} +> {{$pos := add $index 1 -}} +> "{{$value.PURL -}}"{{if lt $pos $artifactLength}},{{else}}{{break}}{{end}} +> {{- end}} +> ] +> } +> +> ``` +> +> 这个模板的语法来自于 Golang [text/template](https://pkg.go.dev/text/template#hdr-Functions)。如果需要自定义,可以参考 syft 的官方文档 [使用模板](syft-dev\README.md#Using templates) + +3 syft 源码的修改部分? + +> syft 功能其实已经挺完善了,基本的功能已经支持我们项目的需求,我主要修改的部分为 `syft-dev/source/source.go` 这个文件,添加了对 rpm 包的解压,然后解析得到结果的逻辑。修改的部分很少,如有需要修改或者查看,可以使用 diff 工具对比 `syft/source/source.go` 和源仓库 anchore/syft 中对应文件的差异。 diff --git a/ci/tools/openeuler-purl/bin/linux/syft b/ci/tools/openeuler-purl/bin/linux/syft new file mode 100755 index 0000000000000000000000000000000000000000..1b0b648c846f7ecb36f0192057214d57c3760e87 Binary files /dev/null and b/ci/tools/openeuler-purl/bin/linux/syft differ diff --git a/ci/tools/openeuler-purl/bin/windows/syft.exe b/ci/tools/openeuler-purl/bin/windows/syft.exe new file mode 100644 index 0000000000000000000000000000000000000000..39f52dfecf07c9857279443340187a70d5de28eb Binary files /dev/null and b/ci/tools/openeuler-purl/bin/windows/syft.exe differ diff --git a/ci/tools/openeuler-purl/configs.temp.json b/ci/tools/openeuler-purl/configs.temp.json new file mode 100644 index 0000000000000000000000000000000000000000..4cada47aa2d85735350c226bedfefcc1bc5af8cb --- /dev/null +++ b/ci/tools/openeuler-purl/configs.temp.json @@ -0,0 +1,8 @@ +{ + "dir_path": "/home/unknow/data/openeuler-purl/rpm", + "mirror_url": "https://mirrors.nju.edu.cn/openeuler/", + "syft": "./bin/linux/syft.exe", + "template": "./purl.json.tmpl", + "download_limit": 50, + "syft_limit": 10 +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/download.py b/ci/tools/openeuler-purl/download.py new file mode 100644 index 0000000000000000000000000000000000000000..b12dba8ed46aebd46a1a95f2c453683031e058e1 --- /dev/null +++ b/ci/tools/openeuler-purl/download.py @@ -0,0 +1,222 @@ +import json +import os.path +import sys + +from loguru import logger +import aiohttp +from bs4 import BeautifulSoup +import asyncio +import aiofiles +import requests +from tqdm import tqdm + +# logging.basicConfig(level=logging.DEBUG) +logger.remove() +default_id = logger.add(sys.stderr, level="INFO", filter=lambda x: 'INFO' == x['level'].name) +logger.add("./logs/download.log", level="DEBUG", backtrace=True, diagnose=True, mode="w") +# err_id = logger.add("./logs/download_error.log", level="ERROR", backtrace=True, diagnose=True, mode="w", +# filter=lambda x: 'ERROR' == x['level'].name) +# debug_id = logger.add("./logs/download_debug.log", level="DEBUG", backtrace=True, diagnose=True, mode="w", +# filter=lambda x: 'DEBUG' == x['level'].name) + +# 记录下载逻辑已处理的文件数量 +global download_count + + +# 记录下载失败的文件列表 +global down_error_packages + + +def get_version_list_by_name(): + """ + 根据系统版本号获取不同系统版本的包根目录 + :return: 一个列表,包含不同版本号的 src.rpm 包的URL路径 + """ + version_name_list = [ + "openEuler-20.03-LTS", + "openEuler-20.03-LTS-SP1", + "openEuler-20.03-LTS-SP2", + "openEuler-20.03-LTS-SP3", + "openEuler-20.09", + "openEuler-21.03", + "openEuler-21.09", + "openEuler-22.03-LTS" + ] + version_list = [] + for version_name in version_name_list: + version_dict = {} + if "openEuler-2" in version_name: + version_dict["name"] = version_name + urlpath = f"/{version_name}/source/Packages/" + version_dict["source_path"] = urlpath + version_list.append(version_dict) + return version_list + + +def get_package_list(package_urlpath): + """ + 根据指定的 URL 路径获取该路径下所有的软件包名列表 + :param package_urlpath: + :return: 一个列表,都是软件包名 + """ + base_path = f'{MIRROR_URL}{package_urlpath}' + res = requests.get(base_path) + soup = BeautifulSoup(res.text, features="html.parser") + index_list = soup.select("#list tbody tr a[title]") + package_list = [] + for index in index_list: + package_dict = {} + package_name = index.text + if ".src.rpm" in package_name: + package_dict["name"] = package_name + urlpath = f"{base_path}{package_name}" + package_dict["source_path"] = urlpath + package_list.append(package_dict) + return package_list + + +async def save_file(response, filepath): + """ + 异步保存文件流到指定的文件 + :param response: + :param filepath: + :return: + """ + content_length = int(response.headers.get('Content-Length', 0)) + if os.path.exists(filepath): + if os.path.getsize(filepath) != content_length: + try: + logger.debug(f"文件大小异常,尝试删除异常文件:{filepath}, 并重新下载") + os.remove(filepath) + except IOError as ie: + logger.debug(f"删除异常文件:{filepath} 未完成,请手动检查是否删除成功!!!{ie}") + else: + return + current_length = 0 + async with aiofiles.open(filepath, mode='wb') as fd: + async for chunk in response.content.iter_chunked(n=1024): + if chunk: + await fd.write(chunk) + current_length = current_length + len(chunk) + + +async def download_job(session, package, dest_path, semaphore): + """ + 异步任务,下载某个URL 路径下所有的 rpm src 包 + :param session: + :param semaphore: + :param package: + :param dest_path: + :return: + """ + global download_count + async with semaphore: + package_name = package['name'] + filepath = os.path.join(dest_path, package_name) + try: + async with session.get(package["source_path"]) as response: + await save_file(response, filepath=filepath) + except Exception as ex: + try: + logger.debug(f"{package_name} 包下载异常,尝试删除异常文件。{ex}") + if os.path.exists(filepath): + os.remove(filepath) + except IOError as ie: + logger.debug(f"删除异常文件:{package_name} 未完成,请手动检查!!!{ie}") + finally: + down_error_packages.append(package_name) + finally: + download_count += 1 + + +async def show_bar(max_length): + """ + 进度条 + :param max_length: + :return: + """ + # 初始化已下载个数为 0 + global download_count + download_count = 0 + bar = tqdm(initial=0, total=max_length, mininterval=0.1, maxinterval=0.1, nrows=16) + bar.set_description("Download Processing: ") + current_count = 0 + while download_count <= max_length: + update_step = download_count - current_count + bar.update(update_step) + current_count = download_count + if download_count == max_length: + bar.close() + return + await asyncio.sleep(0.1) + + +async def save_download_error_packages(version_name, packages): + async with aiofiles.open(f"./logs/download_error_list-{version_name}.log", "w") as fs: + for package_name in packages: + await fs.write(f"{package_name}\n") + + +async def main(limit): + """ + 异步主函数,包括四个步骤 + 1. 获取所有的版本号对应的 src.rpm 包的根路径 + 2. 根据对应系统版本的根路径构建下载不同的下载目录 + 3. 提交对应系统版本的所有下载任务,并发运行 + 4. 记录下载结果,将下载异常的包记录到对应系统版本的日志中 + :param limit: + :return: + """ + _version_list = get_version_list_by_name() + logger.info("版本列表:") + for v in _version_list: + logger.info(" {}", v.get('name')) + async with aiohttp.ClientSession() as session: + for index, version in enumerate(_version_list): + logger.info(f"开始下载第 {index + 1} 个版本:{version['name']}") + await asyncio.sleep(1.5) + _package_list = get_package_list(version["source_path"]) + version_path = os.path.join(DIR_PATH, version["name"]) + + # 指定当前版本下载到的目录 + dest_path = os.path.join(version_path, "packages") + os.makedirs(dest_path, exist_ok=True) + # 信号量,用来限制并发数 + semaphore = asyncio.Semaphore(limit) + # 每个包的下载都作为一个任务 + tasks = [download_job(session, package, dest_path, semaphore) for package in _package_list] + job_count = len(tasks) + # 进度条任务也加到异步任务中 + tasks.append(show_bar(job_count)) + # 提交所有任务 + await asyncio.gather(*tasks) + if down_error_packages: + await save_download_error_packages(version["name"], down_error_packages) + logger.info("{} Download Finished, But Some Package Download Error, Try Manually Download It!", + version["name"]) + for p in down_error_packages: + logger.info(f" {p}") + logger.info("You Can Also Look What Package Fail In ./logs/download_error_list-{} \n\n", + version["name"]) + + +if __name__ == '__main__': + download_count = 0 + down_error_packages = [] + with open("configs.json", "r") as f: + configs = json.load(f) + # 下载到的目录必须指定 + DIR_PATH = "" + if configs.get("dir_path"): + DIR_PATH = configs.get("dir_path") + else: + logger.error("dir_path is not set") + raise "dir_path is not set" + # 如果没有设置镜像地址和下载限制,则使用默认 + MIRROR_URL = "http://121.36.97.194" + if configs.get("mirror_url"): + MIRROR_URL = configs.get("mirror_url") + DOWNLOAD_LIMIT = 30 + if configs.get('download_limit'): + DOWNLOAD_LIMIT = configs.get("download_limit") + asyncio.run(main(limit=DOWNLOAD_LIMIT)) diff --git a/ci/tools/openeuler-purl/examples/all_packages_purls.json b/ci/tools/openeuler-purl/examples/all_packages_purls.json new file mode 100644 index 0000000000000000000000000000000000000000..924f1af722ffad96438b017cc4ad2cdfc33f2256 --- /dev/null +++ b/ci/tools/openeuler-purl/examples/all_packages_purls.json @@ -0,0 +1,4353 @@ +{ + "version": "openEuler-20.03-LTS", + "data": [ + { + "name": "python-setuptools_scm-3.1.0-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/setuptools-scm@3.1.0" + ] + }, + { + "name": "python-SecretStorage-2.3.1-11.oe1.src.rpm", + "purls": [ + "pkg:pypi/SecretStorage@2.3.1" + ] + }, + { + "name": "python-freezegun-0.3.8-12.oe1.src.rpm", + "purls": [ + "pkg:pypi/freezegun@0.3.8" + ] + }, + { + "name": "jq-1.5-17.oe1.src.rpm", + "purls": [ + "pkg:gem/activesupport@4.2.3", + "pkg:gem/addressable@2.3.8", + "pkg:gem/bonsai@1.4.9", + "pkg:gem/builder@3.2.2", + "pkg:gem/hpricot@0.8.6", + "pkg:gem/i18n@0.7.0", + "pkg:gem/json@1.8.3", + "pkg:gem/launchy@2.4.3", + "pkg:gem/liquid@3.0.6", + "pkg:gem/maruku@0.7.2", + "pkg:gem/minitest@5.8.0", + "pkg:gem/mustache@0.99.8", + "pkg:gem/rack@1.6.4", + "pkg:gem/rack-protection@1.5.3", + "pkg:gem/rake@10.4.2", + "pkg:gem/rdiscount@2.1.8", + "pkg:gem/ronn@0.7.3", + "pkg:gem/sass@3.4.16", + "pkg:gem/sinatra@1.4.6", + "pkg:gem/thread_safe@0.3.5", + "pkg:gem/tilt@2.0.1", + "pkg:gem/tzinfo@1.2.2", + "pkg:gem/watch@0.1.0", + "pkg:gem/yui-compressor@0.12.0" + ] + }, + { + "name": "PyPAM-0.5.0-1.oe1.src.rpm", + "purls": [ + "pkg:rpm/PyPAM@0.5.0-1?arch=athlon&epoch=0&upstream=PyPAM-0.5.0-1.src.rpm", + "pkg:rpm/PyPAM@0.5.0-1?arch=athlon&epoch=0", + "pkg:rpm/PyPAM-debuginfo@0.5.0-1?arch=athlon&epoch=0&upstream=PyPAM-0.5.0-1.src.rpm" + ] + }, + { + "name": "python-pytest-mock-1.10.0-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytest-mock@1.10.0" + ] + }, + { + "name": "python-packaging-17.1-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/packaging@17.1" + ] + }, + { + "name": "python-mimeparse-1.6.0-8.oe1.src.rpm", + "purls": [ + "pkg:pypi/python-mimeparse@1.6.0" + ] + }, + { + "name": "python-setuptools_git-1.1-10.oe1.src.rpm", + "purls": [ + "pkg:pypi/setuptools-git@1.1" + ] + }, + { + "name": "python-httplib2-0.13.1-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/flake8@3.4.1", + "pkg:pypi/future@0.16.0", + "pkg:pypi/httplib2@0.13.1", + "pkg:pypi/mock@2.0.0", + "pkg:pypi/pytest@3.2.1", + "pkg:pypi/pytest-cov@2.5.1", + "pkg:pypi/pytest-forked@0.2", + "pkg:pypi/pytest-randomly@1.2.1", + "pkg:pypi/pytest-timeout@1.2.0", + "pkg:pypi/pytest-xdist@1.20.0", + "pkg:pypi/six@1.10.0" + ] + }, + { + "name": "python-whoosh-2.7.4-13.oe1.src.rpm", + "purls": [ + "pkg:pypi/Whoosh@2.7.4" + ] + }, + { + "name": "drpm-0.4.1-3.oe1.src.rpm", + "purls": [ + "pkg:rpm/drpm-devel@0.1.3-1.fc20?arch=x86_64&epoch=0&upstream=drpm-0.1.3-1.fc20.src.rpm", + "pkg:rpm/drpm-devel@0.3.0-1.fc20?arch=x86_64&epoch=0&upstream=drpm-0.3.0-1.fc20.src.rpm", + "pkg:rpm/libcmocka@0.4.1-3.fc21?arch=i686&epoch=0&upstream=cmocka-0.4.1-3.fc21.src.rpm", + "pkg:rpm/libcmocka@1.0.1-1.fc21?arch=i686&epoch=0&upstream=cmocka-1.0.1-1.fc21.src.rpm" + ] + }, + { + "name": "python-unittest2-1.1.0-16.oe1.src.rpm", + "purls": [ + "pkg:pypi/unittest2@1.1.0" + ] + }, + { + "name": "python-tornado-5.0.2-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/tornado@5.0.2" + ] + }, + { + "name": "dnf-4.2.15-8.oe1.src.rpm", + "purls": [ + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/bash@4.2.46-21?arch=x86_64&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash@4.2.46-21?arch=x86_64&epoch=0", + "pkg:rpm/bash@4.2.46-21?arch=x86_64&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=x86_64&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=x86_64&epoch=0", + "pkg:rpm/bash@4.4.12-2?arch=x86_64&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=x86_64&epoch=0", + "pkg:rpm/bash@4.4.12-2?arch=x86_64&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/dummy-nscd@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/dummy-nscd@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/dummy-nscd@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/dummy-nscd@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/dummy-nscd@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/dummy-nscd@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/filesystem@3.2-21?arch=x86_64&epoch=0&upstream=filesystem-3.2-21.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=x86_64&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=x86_64&epoch=0", + "pkg:rpm/filesystem@3.2-40?arch=x86_64&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=x86_64&epoch=0", + "pkg:rpm/filesystem@3.2-40?arch=x86_64&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-21?arch=x86_64&epoch=0", + "pkg:rpm/filesystem@3.2-21?arch=x86_64&epoch=0&upstream=filesystem-3.2-21.src.rpm", + "pkg:rpm/glibc@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc@2.17-157?arch=x86_64&epoch=0", + "pkg:rpm/glibc@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc@2.25-4?arch=x86_64&epoch=0", + "pkg:rpm/glibc@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc@2.25.90-2?arch=x86_64&epoch=0", + "pkg:rpm/glibc@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-common@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-common@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-common@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-common@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-common@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-common@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/grub2@2.02-0.40?arch=x86_64&epoch=0&upstream=grub2-2.02-0.40.src.rpm", + "pkg:rpm/grub2@2.02-0.40?arch=x86_64&epoch=0", + "pkg:rpm/grub2@2.02-0.40?arch=x86_64&epoch=0&upstream=grub2-2.02-0.40.src.rpm", + "pkg:rpm/httpd@2.2.10-1?arch=x86_64&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd@2.2.10-1?arch=x86_64&epoch=0", + "pkg:rpm/httpd@2.2.10-1?arch=x86_64&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd@2.2.15-59?arch=x86_64&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd@2.2.15-59?arch=x86_64&epoch=0", + "pkg:rpm/httpd@2.2.15-59?arch=x86_64&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd@2.4.25-7?arch=x86_64&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd@2.4.25-8?arch=x86_64&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd@2.4.25-7?arch=x86_64&epoch=0", + "pkg:rpm/httpd@2.4.25-7?arch=x86_64&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd@2.4.25-8?arch=x86_64&epoch=0", + "pkg:rpm/httpd@2.4.25-8?arch=x86_64&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-doc@2.2.10-1?arch=x86_64&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd-doc@2.2.10-1?arch=x86_64&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd-doc@2.2.15-59?arch=x86_64&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd-doc@2.2.15-59?arch=x86_64&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-7?arch=x86_64&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-8?arch=x86_64&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-7?arch=x86_64&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-8?arch=x86_64&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-provides-name@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name@3.0-1?arch=x86_64&epoch=0", + "pkg:rpm/httpd-provides-name@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-doc@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-doc@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=x86_64&epoch=0", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release-doc@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release-doc@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/kernel@3.10.0-514?arch=x86_64&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel@3.10.0-514?arch=x86_64&epoch=0", + "pkg:rpm/kernel@3.10.0-514?arch=x86_64&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=x86_64&epoch=0", + "pkg:rpm/kernel@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=x86_64&epoch=0", + "pkg:rpm/kernel@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@3.10.0-514?arch=x86_64&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-headers@3.10.0-514?arch=x86_64&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=x86_64&epoch=0", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=x86_64&epoch=0", + "pkg:rpm/libnghttp2@1.21.1-1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=x86_64&epoch=0", + "pkg:rpm/libnghttp2@1.21.1-1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/m4@1.4.18-6?arch=x86_64&epoch=0&upstream=m4-1.4.18-6.src.rpm", + "pkg:rpm/m4@1.4.18-6?arch=x86_64&epoch=0", + "pkg:rpm/m4@1.4.18-6?arch=x86_64&epoch=0&upstream=m4-1.4.18-6.src.rpm", + "pkg:rpm/systemd@219-30?arch=x86_64&epoch=0&upstream=systemd-219-30.src.rpm", + "pkg:rpm/systemd@219-30?arch=x86_64&epoch=0", + "pkg:rpm/systemd@219-30?arch=x86_64&epoch=0&upstream=systemd-219-30.src.rpm", + "pkg:rpm/systemd@233-3?arch=x86_64&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=x86_64&epoch=0", + "pkg:rpm/systemd@233-3?arch=x86_64&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=x86_64&epoch=0", + "pkg:rpm/systemd@233-3?arch=x86_64&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/tour@4-4?arch=noarch&epoch=0&upstream=tour-4-4.src.rpm", + "pkg:rpm/tour@5-0?arch=noarch&epoch=0&upstream=tour-5-0.src.rpm", + "pkg:rpm/tour@5-1?arch=noarch&epoch=0&upstream=tour-5-1.src.rpm" + ] + }, + { + "name": "python-google-apputils-0.4.2-15.oe1.src.rpm", + "purls": [ + "pkg:pypi/google-apputils@0.4.2" + ] + }, + { + "name": "iSulad-img-2.0.0-20200318.002428.gitdbc56638.oe1.src.rpm", + "purls": [ + "pkg:golang/golang.org/x/crypto@v0.0.0-20190308221718-c2843e01d9a2", + "pkg:golang/golang.org/x/sys@v0.0.0-20190215142949-d0b11bdaac8a", + "pkg:golang/golang.org/x/text@v0.3.0" + ] + }, + { + "name": "python-u-msgpack-python-2.5.0-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/u-msgpack-python@2.5.0" + ] + }, + { + "name": "python-toml-0.10.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/toml@0.10.0" + ] + }, + { + "name": "python-humanize-0.5.1-16.oe1.src.rpm", + "purls": [ + "pkg:pypi/humanize@0.5.1" + ] + }, + { + "name": "python-pip-18.0-12.oe1.src.rpm", + "purls": [ + "pkg:pypi/pip@18.0" + ] + }, + { + "name": "python-aniso8601-7.0.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/aniso8601@7.0.0" + ] + }, + { + "name": "gpgme-1.13.1-5.oe1.src.rpm", + "purls": [ + "pkg:npm/gpgmejs@0.0.1-dev" + ] + }, + { + "name": "python-requests-file-1.4.3-9.oe1.src.rpm", + "purls": [ + "pkg:pypi/requests-file@1.4.3" + ] + }, + { + "name": "python-keyczar-0.71c-13.oe1.src.rpm", + "purls": [ + "pkg:pypi/python-keyczar@0.71c" + ] + }, + { + "name": "python-enchant-2.0.0-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/pyenchant@2.0.0" + ] + }, + { + "name": "python-pycurl-7.43.0.2-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/pycurl@7.43.0.2" + ] + }, + { + "name": "opencc-1.0.5-4.oe1.src.rpm", + "purls": [ + "pkg:npm/opencc@1.0.5" + ] + }, + { + "name": "python-dateutil-2.7.0-7.oe1.src.rpm", + "purls": [ + "pkg:pypi/python-dateutil@2.7.0" + ] + }, + { + "name": "python-pytest-cov-2.5.1-7.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytest-cov@2.5.1" + ] + }, + { + "name": "m2crypto-0.30.1-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/M2Crypto@0.30.1" + ] + }, + { + "name": "python-pytest-virtualenv-1.2.11-11.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytest-virtualenv@1.2.11" + ] + }, + { + "name": "python-zipp-0.5.1-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/zipp@0.5.1" + ] + }, + { + "name": "python-scikit-learn-0.20.4-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/cython@0.27.3" + ] + }, + { + "name": "subscription-manager-1.23.3-5.oe1.src.rpm", + "purls": [ + "pkg:npm/abbrev@1.1.0", + "pkg:npm/acorn@3.3.0", + "pkg:npm/acorn@4.0.13", + "pkg:npm/acorn@5.0.3", + "pkg:npm/acorn@5.1.1", + "pkg:npm/acorn-dynamic-import@2.0.2", + "pkg:npm/acorn-jsx@3.0.1", + "pkg:npm/ajv@4.11.8", + "pkg:npm/ajv@5.2.2", + "pkg:npm/ajv-keywords@1.5.1", + "pkg:npm/align-text@0.1.4", + "pkg:npm/alphanum-sort@1.0.2", + "pkg:npm/ansi-escapes@1.4.0", + "pkg:npm/ansi-regex@2.1.1", + "pkg:npm/ansi-regex@3.0.0", + "pkg:npm/ansi-styles@1.0.0", + "pkg:npm/ansi-styles@2.2.1", + "pkg:npm/ansi-styles@3.2.0", + "pkg:npm/anymatch@1.3.0", + "pkg:npm/aproba@1.1.2", + "pkg:npm/are-we-there-yet@1.1.4", + "pkg:npm/argparse@1.0.9", + "pkg:npm/arr-diff@2.0.0", + "pkg:npm/arr-flatten@1.0.3", + "pkg:npm/array-union@1.0.2", + "pkg:npm/array-uniq@1.0.3", + "pkg:npm/array-unique@0.2.1", + "pkg:npm/array.prototype.find@2.0.4", + "pkg:npm/arrify@1.0.1", + "pkg:npm/asap@2.0.6", + "pkg:npm/asn1@0.2.3", + "pkg:npm/asn1.js@4.9.1", + "pkg:npm/assert@1.4.1", + "pkg:npm/assert-plus@0.2.0", + "pkg:npm/assert-plus@1.0.0", + "pkg:npm/async@2.4.1", + "pkg:npm/async-each@1.0.1", + "pkg:npm/asynckit@0.4.0", + "pkg:npm/autoprefixer@6.7.7", + "pkg:npm/aws-sign2@0.6.0", + "pkg:npm/aws4@1.6.0", + "pkg:npm/babel-code-frame@6.22.0", + "pkg:npm/babel-core@6.25.0", + "pkg:npm/babel-generator@6.25.0", + "pkg:npm/babel-helper-builder-binary-assignment-operator-visitor@6.24.1", + "pkg:npm/babel-helper-builder-react-jsx@6.24.1", + "pkg:npm/babel-helper-call-delegate@6.24.1", + "pkg:npm/babel-helper-define-map@6.24.1", + "pkg:npm/babel-helper-explode-assignable-expression@6.24.1", + "pkg:npm/babel-helper-function-name@6.24.1", + "pkg:npm/babel-helper-get-function-arity@6.24.1", + "pkg:npm/babel-helper-hoist-variables@6.24.1", + "pkg:npm/babel-helper-optimise-call-expression@6.24.1", + "pkg:npm/babel-helper-regex@6.24.1", + "pkg:npm/babel-helper-remap-async-to-generator@6.24.1", + "pkg:npm/babel-helper-replace-supers@6.24.1", + "pkg:npm/babel-helpers@6.24.1", + "pkg:npm/babel-loader@7.0.0", + "pkg:npm/babel-messages@6.23.0", + "pkg:npm/babel-plugin-check-es2015-constants@6.22.0", + "pkg:npm/babel-plugin-syntax-async-functions@6.13.0", + "pkg:npm/babel-plugin-syntax-exponentiation-operator@6.13.0", + "pkg:npm/babel-plugin-syntax-jsx@6.18.0", + "pkg:npm/babel-plugin-syntax-trailing-function-commas@6.22.0", + "pkg:npm/babel-plugin-transform-async-to-generator@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-arrow-functions@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-block-scoped-functions@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-block-scoping@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-classes@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-computed-properties@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-destructuring@6.23.0", + "pkg:npm/babel-plugin-transform-es2015-duplicate-keys@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-for-of@6.23.0", + "pkg:npm/babel-plugin-transform-es2015-function-name@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-literals@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-modules-amd@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-modules-commonjs@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-modules-systemjs@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-modules-umd@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-object-super@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-parameters@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-shorthand-properties@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-spread@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-sticky-regex@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-template-literals@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-typeof-symbol@6.23.0", + "pkg:npm/babel-plugin-transform-es2015-unicode-regex@6.24.1", + "pkg:npm/babel-plugin-transform-exponentiation-operator@6.24.1", + "pkg:npm/babel-plugin-transform-react-jsx@6.24.1", + "pkg:npm/babel-plugin-transform-regenerator@6.24.1", + "pkg:npm/babel-plugin-transform-strict-mode@6.24.1", + "pkg:npm/babel-preset-env@1.5.2", + "pkg:npm/babel-register@6.24.1", + "pkg:npm/babel-runtime@6.23.0", + "pkg:npm/babel-runtime@6.25.0", + "pkg:npm/babel-template@6.25.0", + "pkg:npm/babel-traverse@6.25.0", + "pkg:npm/babel-types@6.25.0", + "pkg:npm/babylon@6.17.3", + "pkg:npm/balanced-match@0.4.2", + "pkg:npm/balanced-match@1.0.0", + "pkg:npm/base64-js@1.2.0", + "pkg:npm/bcrypt-pbkdf@1.0.1", + "pkg:npm/big.js@3.1.3", + "pkg:npm/binary-extensions@1.8.0", + "pkg:npm/block-stream@0.0.9", + "pkg:npm/bluebird@2.11.0", + "pkg:npm/bn.js@4.11.6", + "pkg:npm/boom@2.10.1", + "pkg:npm/bootstrap@3.3.7", + "pkg:npm/bootstrap-datepicker@1.6.4", + "pkg:npm/bootstrap-select@1.12.4", + "pkg:npm/bootstrap-switch@3.3.4", + "pkg:npm/bootstrap-touchspin@3.1.1", + "pkg:npm/brace-expansion@1.1.8", + "pkg:npm/braces@1.8.5", + "pkg:npm/brorand@1.1.0", + "pkg:npm/browserify-aes@1.0.6", + "pkg:npm/browserify-cipher@1.0.0", + "pkg:npm/browserify-des@1.0.0", + "pkg:npm/browserify-rsa@4.0.1", + "pkg:npm/browserify-sign@4.0.4", + "pkg:npm/browserify-zlib@0.1.4", + "pkg:npm/browserslist@1.7.7", + "pkg:npm/browserslist@2.1.5", + "pkg:npm/buffer@4.9.1", + "pkg:npm/buffer-xor@1.0.3", + "pkg:npm/builtin-modules@1.1.1", + "pkg:npm/builtin-status-codes@3.0.0", + "pkg:npm/c3@0.4.18", + "pkg:npm/caller-path@0.1.0", + "pkg:npm/callsites@0.2.0", + "pkg:npm/camelcase@1.2.1", + "pkg:npm/camelcase@3.0.0", + "pkg:npm/caniuse-api@1.6.1", + "pkg:npm/caniuse-db@1.0.30000715", + "pkg:npm/caniuse-lite@1.0.30000684", + "pkg:npm/caseless@0.12.0", + "pkg:npm/center-align@0.1.3", + "pkg:npm/chalk@0.4.0", + "pkg:npm/chalk@1.1.3", + "pkg:npm/chalk@2.1.0", + "pkg:npm/chokidar@1.7.0", + "pkg:npm/cipher-base@1.0.3", + "pkg:npm/circular-json@0.3.3", + "pkg:npm/clap@1.2.0", + "pkg:npm/classnames@2.2.5", + "pkg:npm/cli@1.0.1", + "pkg:npm/cli-cursor@1.0.2", + "pkg:npm/cli-width@2.1.0", + "pkg:npm/cliui@2.1.0", + "pkg:npm/cliui@3.2.0", + "pkg:npm/clone@1.0.2", + "pkg:npm/co@4.6.0", + "pkg:npm/coa@1.0.4", + "pkg:npm/code-point-at@1.1.0", + "pkg:npm/color@0.11.4", + "pkg:npm/color-convert@1.9.0", + "pkg:npm/color-name@1.1.3", + "pkg:npm/color-string@0.3.0", + "pkg:npm/colormin@1.1.2", + "pkg:npm/colors@1.1.2", + "pkg:npm/combined-stream@1.0.5", + "pkg:npm/commondir@1.0.1", + "pkg:npm/compression-webpack-plugin@1.0.0", + "pkg:npm/concat-map@0.0.1", + "pkg:npm/concat-stream@1.6.0", + "pkg:npm/console-browserify@1.1.0", + "pkg:npm/console-control-strings@1.1.0", + "pkg:npm/constants-browserify@1.0.0", + "pkg:npm/convert-source-map@1.5.0", + "pkg:npm/copy-webpack-plugin@3.0.1", + "pkg:npm/core-js@1.2.7", + "pkg:npm/core-js@2.4.1", + "pkg:npm/core-util-is@1.0.2", + "pkg:npm/create-ecdh@4.0.0", + "pkg:npm/create-hash@1.1.3", + "pkg:npm/create-hmac@1.1.6", + "pkg:npm/create-react-class@15.6.2", + "pkg:npm/cryptiles@2.0.5", + "pkg:npm/crypto-browserify@3.11.0", + "pkg:npm/css-color-names@0.0.4", + "pkg:npm/css-loader@0.28.4", + "pkg:npm/css-selector-tokenizer@0.7.0", + "pkg:npm/cssesc@0.1.0", + "pkg:npm/cssnano@3.10.0", + "pkg:npm/csso@2.3.2", + "pkg:npm/d@1.0.0", + "pkg:npm/d3@3.5.17", + "pkg:npm/dashdash@1.14.1", + "pkg:npm/datatables.net@1.10.16", + "pkg:npm/datatables.net@2.1.1", + "pkg:npm/datatables.net-bs@2.1.1", + "pkg:npm/datatables.net-colreorder@1.3.3", + "pkg:npm/datatables.net-colreorder@1.4.1", + "pkg:npm/datatables.net-colreorder-bs@1.3.3", + "pkg:npm/datatables.net-select@1.2.3", + "pkg:npm/date-now@0.1.4", + "pkg:npm/debug@2.6.8", + "pkg:npm/decamelize@1.2.0", + "pkg:npm/deep-extend@0.4.2", + "pkg:npm/deep-is@0.1.3", + "pkg:npm/define-properties@1.1.2", + "pkg:npm/defined@1.0.0", + "pkg:npm/del@2.2.2", + "pkg:npm/delayed-stream@1.0.0", + "pkg:npm/delegates@1.0.0", + "pkg:npm/des.js@1.0.0", + "pkg:npm/detect-indent@4.0.0", + "pkg:npm/diffie-hellman@5.0.2", + "pkg:npm/doctrine@1.5.0", + "pkg:npm/doctrine@2.0.0", + "pkg:npm/dom-helpers@3.2.1", + "pkg:npm/dom-serializer@0.1.0", + "pkg:npm/domain-browser@1.1.7", + "pkg:npm/domelementtype@1.1.3", + "pkg:npm/domelementtype@1.3.0", + "pkg:npm/domhandler@2.3.0", + "pkg:npm/domutils@1.5.1", + "pkg:npm/drmonty-datatables-colvis@1.1.2", + "pkg:npm/ecc-jsbn@0.1.1", + "pkg:npm/electron-to-chromium@1.3.14", + "pkg:npm/electron-to-chromium@1.3.18", + "pkg:npm/elliptic@6.4.0", + "pkg:npm/emojis-list@2.1.0", + "pkg:npm/encoding@0.1.12", + "pkg:npm/enhanced-resolve@3.1.0", + "pkg:npm/entities@1.0.0", + "pkg:npm/entities@1.1.1", + "pkg:npm/eonasdan-bootstrap-datetimepicker@4.17.47", + "pkg:npm/errno@0.1.4", + "pkg:npm/error-ex@1.3.1", + "pkg:npm/es-abstract@1.7.0", + "pkg:npm/es-to-primitive@1.1.1", + "pkg:npm/es5-ext@0.10.24", + "pkg:npm/es6-iterator@2.0.1", + "pkg:npm/es6-map@0.1.5", + "pkg:npm/es6-set@0.1.5", + "pkg:npm/es6-symbol@3.1.1", + "pkg:npm/es6-weak-map@2.0.2", + "pkg:npm/escape-string-regexp@1.0.5", + "pkg:npm/escope@3.6.0", + "pkg:npm/eslint@3.19.0", + "pkg:npm/eslint-loader@1.6.3", + "pkg:npm/eslint-plugin-react@6.9.0", + "pkg:npm/espree@3.4.3", + "pkg:npm/esprima@2.7.3", + "pkg:npm/esprima@4.0.0", + "pkg:npm/esquery@1.0.0", + "pkg:npm/esrecurse@4.2.0", + "pkg:npm/estraverse@4.2.0", + "pkg:npm/esutils@2.0.2", + "pkg:npm/event-emitter@0.3.5", + "pkg:npm/events@1.1.1", + "pkg:npm/evp_bytestokey@1.0.0", + "pkg:npm/exit@0.1.2", + "pkg:npm/exit-hook@1.1.1", + "pkg:npm/expand-brackets@0.1.5", + "pkg:npm/expand-range@1.8.2", + "pkg:npm/extend@3.0.1", + "pkg:npm/extglob@0.3.2", + "pkg:npm/extract-text-webpack-plugin@2.1.2", + "pkg:npm/extsprintf@1.0.2", + "pkg:npm/fast-deep-equal@1.0.0", + "pkg:npm/fast-levenshtein@2.0.6", + "pkg:npm/fastparse@1.1.1", + "pkg:npm/fbjs@0.8.14", + "pkg:npm/fbjs@0.8.16", + "pkg:npm/figures@1.7.0", + "pkg:npm/file-entry-cache@2.0.0", + "pkg:npm/file-loader@1.1.5", + "pkg:npm/filename-regex@2.0.1", + "pkg:npm/fill-range@2.2.3", + "pkg:npm/find-cache-dir@0.1.1", + "pkg:npm/find-up@1.1.2", + "pkg:pypi/flake8@3.0.4", + "pkg:npm/flat-cache@1.2.2", + "pkg:npm/flatten@1.0.2", + "pkg:npm/font-awesome@4.7.0", + "pkg:npm/for-in@1.0.2", + "pkg:npm/for-own@0.1.5", + "pkg:npm/foreach@2.0.5", + "pkg:npm/forever-agent@0.6.1", + "pkg:npm/form-data@2.1.4", + "pkg:npm/fs-extra@0.26.7", + "pkg:npm/fs.realpath@1.0.0", + "pkg:npm/fsevents@1.1.2", + "pkg:npm/fstream@1.0.11", + "pkg:npm/fstream-ignore@1.0.5", + "pkg:npm/function-bind@1.1.0", + "pkg:npm/gauge@2.7.4", + "pkg:npm/generate-function@2.0.0", + "pkg:npm/generate-object-property@1.2.0", + "pkg:npm/get-caller-file@1.0.2", + "pkg:npm/getpass@0.1.7", + "pkg:npm/gettext-parser@1.1.0", + "pkg:npm/glob@6.0.4", + "pkg:npm/glob@7.1.2", + "pkg:npm/glob-base@0.3.0", + "pkg:npm/glob-parent@2.0.0", + "pkg:npm/globals@9.18.0", + "pkg:npm/globby@5.0.0", + "pkg:npm/google-code-prettify@1.0.5", + "pkg:npm/graceful-fs@4.1.11", + "pkg:npm/har-schema@1.0.5", + "pkg:npm/har-validator@4.2.1", + "pkg:npm/has@1.0.1", + "pkg:npm/has-ansi@2.0.0", + "pkg:npm/has-color@0.1.7", + "pkg:npm/has-flag@1.0.0", + "pkg:npm/has-flag@2.0.0", + "pkg:npm/has-unicode@2.0.1", + "pkg:npm/hash-base@2.0.2", + "pkg:npm/hash.js@1.0.3", + "pkg:npm/hawk@3.1.3", + "pkg:npm/hmac-drbg@1.0.1", + "pkg:npm/hoek@2.16.3", + "pkg:npm/home-or-tmp@2.0.0", + "pkg:npm/hosted-git-info@2.4.2", + "pkg:npm/html-comment-regex@1.1.1", + "pkg:npm/htmlparser2@3.8.3", + "pkg:npm/http-signature@1.1.1", + "pkg:npm/https-browserify@0.0.1", + "pkg:npm/iconv-lite@0.4.18", + "pkg:npm/icss-replace-symbols@1.1.0", + "pkg:npm/icss-utils@2.1.0", + "pkg:npm/ieee754@1.1.8", + "pkg:npm/ignore@3.3.3", + "pkg:npm/imurmurhash@0.1.4", + "pkg:npm/indexes-of@1.0.1", + "pkg:npm/indexof@0.0.1", + "pkg:npm/inflight@1.0.6", + "pkg:npm/inherits@2.0.1", + "pkg:npm/inherits@2.0.3", + "pkg:npm/ini@1.3.4", + "pkg:npm/inquirer@0.12.0", + "pkg:npm/interpret@1.0.3", + "pkg:npm/invariant@2.2.2", + "pkg:npm/invert-kv@1.0.0", + "pkg:npm/is-absolute-url@2.1.0", + "pkg:npm/is-arrayish@0.2.1", + "pkg:npm/is-binary-path@1.0.1", + "pkg:npm/is-buffer@1.1.5", + "pkg:npm/is-builtin-module@1.0.0", + "pkg:npm/is-callable@1.1.3", + "pkg:npm/is-date-object@1.0.1", + "pkg:npm/is-dotfile@1.0.3", + "pkg:npm/is-equal-shallow@0.1.3", + "pkg:npm/is-extendable@0.1.1", + "pkg:npm/is-extglob@1.0.0", + "pkg:npm/is-finite@1.0.2", + "pkg:npm/is-fullwidth-code-point@1.0.0", + "pkg:npm/is-fullwidth-code-point@2.0.0", + "pkg:npm/is-glob@2.0.1", + "pkg:npm/is-my-json-valid@2.16.0", + "pkg:npm/is-number@2.1.0", + "pkg:npm/is-number@3.0.0", + "pkg:npm/is-path-cwd@1.0.0", + "pkg:npm/is-path-in-cwd@1.0.0", + "pkg:npm/is-path-inside@1.0.0", + "pkg:npm/is-plain-obj@1.1.0", + "pkg:npm/is-posix-bracket@0.1.1", + "pkg:npm/is-primitive@2.0.0", + "pkg:npm/is-property@1.0.2", + "pkg:npm/is-regex@1.0.4", + "pkg:npm/is-resolvable@1.0.0", + "pkg:npm/is-stream@1.1.0", + "pkg:npm/is-svg@2.1.0", + "pkg:npm/is-symbol@1.0.1", + "pkg:npm/is-typedarray@1.0.0", + "pkg:npm/is-utf8@0.2.1", + "pkg:npm/isarray@0.0.1", + "pkg:npm/isarray@1.0.0", + "pkg:npm/isobject@2.1.0", + "pkg:npm/isomorphic-fetch@2.2.1", + "pkg:npm/isstream@0.1.2", + "pkg:npm/jasmine@2.8.0", + "pkg:npm/jasmine-core@2.8.0", + "pkg:npm/jquery@3.2.1", + "pkg:npm/jquery-match-height@0.7.2", + "pkg:npm/js-base64@2.1.9", + "pkg:npm/js-tokens@3.0.1", + "pkg:npm/js-yaml@3.7.0", + "pkg:npm/js-yaml@3.9.1", + "pkg:npm/jsbn@0.1.1", + "pkg:npm/jsesc@0.5.0", + "pkg:npm/jsesc@1.3.0", + "pkg:npm/jshint@2.9.5", + "pkg:npm/jshint-loader@0.8.4", + "pkg:npm/json-loader@0.5.4", + "pkg:npm/json-schema@0.2.3", + "pkg:npm/json-schema-traverse@0.3.1", + "pkg:npm/json-stable-stringify@1.0.1", + "pkg:npm/json-stringify-safe@5.0.1", + "pkg:npm/json5@0.5.1", + "pkg:npm/jsonfile@2.4.0", + "pkg:npm/jsonify@0.0.0", + "pkg:npm/jsonpointer@4.0.1", + "pkg:npm/jsprim@1.4.0", + "pkg:npm/jsx-ast-utils@1.4.1", + "pkg:npm/keycode@2.1.9", + "pkg:npm/kind-of@3.2.2", + "pkg:npm/kind-of@4.0.0", + "pkg:npm/klaw@1.3.1", + "pkg:npm/lazy-cache@1.0.4", + "pkg:npm/lcid@1.0.0", + "pkg:npm/levn@0.3.0", + "pkg:npm/load-json-file@1.1.0", + "pkg:npm/loader-runner@2.3.0", + "pkg:npm/loader-utils@0.2.17", + "pkg:npm/loader-utils@1.1.0", + "pkg:npm/lodash@2.4.2", + "pkg:npm/lodash@3.7.0", + "pkg:npm/lodash@4.17.4", + "pkg:npm/lodash.camelcase@4.3.0", + "pkg:npm/lodash.clonedeep@4.5.0", + "pkg:npm/lodash.memoize@4.1.2", + "pkg:npm/lodash.uniq@4.5.0", + "pkg:npm/longest@1.0.1", + "pkg:npm/loose-envify@1.3.1", + "pkg:npm/macaddress@0.2.8", + "pkg:npm/math-expression-evaluator@1.2.17", + "pkg:npm/memory-fs@0.4.1", + "pkg:npm/micromatch@2.3.11", + "pkg:npm/miller-rabin@4.0.0", + "pkg:npm/mime-db@1.27.0", + "pkg:npm/mime-types@2.1.15", + "pkg:npm/minimalistic-assert@1.0.0", + "pkg:npm/minimalistic-crypto-utils@1.0.1", + "pkg:npm/minimatch@3.0.4", + "pkg:npm/minimist@0.0.8", + "pkg:npm/minimist@1.2.0", + "pkg:npm/mkdirp@0.5.1", + "pkg:npm/moment@2.14.1", + "pkg:npm/moment@2.18.1", + "pkg:npm/moment-timezone@0.4.1", + "pkg:npm/ms@2.0.0", + "pkg:npm/mute-stream@0.0.5", + "pkg:npm/nan@2.6.2", + "pkg:npm/natural-compare@1.4.0", + "pkg:npm/node-dir@0.1.17", + "pkg:npm/node-fetch@1.7.2", + "pkg:npm/node-libs-browser@2.0.0", + "pkg:npm/node-pre-gyp@0.6.36", + "pkg:npm/nomnom@1.8.1", + "pkg:npm/nopt@4.0.1", + "pkg:npm/normalize-package-data@2.3.8", + "pkg:npm/normalize-path@2.1.1", + "pkg:npm/normalize-range@0.1.2", + "pkg:npm/normalize-url@1.9.1", + "pkg:npm/npmlog@4.1.0", + "pkg:npm/num2fraction@1.2.2", + "pkg:npm/number-is-nan@1.0.1", + "pkg:npm/oauth-sign@0.8.2", + "pkg:npm/object-assign@4.1.1", + "pkg:npm/object-hash@1.1.8", + "pkg:npm/object-keys@1.0.11", + "pkg:npm/object.omit@2.0.1", + "pkg:npm/once@1.4.0", + "pkg:npm/onetime@1.1.0", + "pkg:npm/optionator@0.8.2", + "pkg:npm/os-browserify@0.2.1", + "pkg:npm/os-homedir@1.0.2", + "pkg:npm/os-locale@1.4.0", + "pkg:npm/os-tmpdir@1.0.2", + "pkg:npm/osenv@0.1.4", + "pkg:npm/pako@0.2.9", + "pkg:npm/parse-asn1@5.1.0", + "pkg:npm/parse-glob@3.0.4", + "pkg:npm/parse-json@2.2.0", + "pkg:npm/path-browserify@0.0.0", + "pkg:npm/path-exists@2.1.0", + "pkg:npm/path-is-absolute@1.0.1", + "pkg:npm/path-is-inside@1.0.2", + "pkg:npm/path-parse@1.0.5", + "pkg:npm/path-type@1.1.0", + "pkg:npm/patternfly@3.27.6", + "pkg:npm/patternfly-bootstrap-combobox@1.1.7", + "pkg:npm/patternfly-bootstrap-treeview@2.1.5", + "pkg:npm/patternfly-react@0.8.0", + "pkg:npm/pbkdf2@3.0.12", + "pkg:pypi/pep8@1.5.7", + "pkg:npm/performance-now@0.2.0", + "pkg:npm/pify@2.3.0", + "pkg:npm/pinkie@2.0.4", + "pkg:npm/pinkie-promise@2.0.1", + "pkg:npm/pkg-dir@1.0.0", + "pkg:npm/pluralize@1.2.1", + "pkg:npm/po2json@0.4.5", + "pkg:npm/postcss@5.2.17", + "pkg:npm/postcss@6.0.9", + "pkg:npm/postcss-calc@5.3.1", + "pkg:npm/postcss-colormin@2.2.2", + "pkg:npm/postcss-convert-values@2.6.1", + "pkg:npm/postcss-discard-comments@2.0.4", + "pkg:npm/postcss-discard-duplicates@2.1.0", + "pkg:npm/postcss-discard-empty@2.1.0", + "pkg:npm/postcss-discard-overridden@0.1.1", + "pkg:npm/postcss-discard-unused@2.2.3", + "pkg:npm/postcss-filter-plugins@2.0.2", + "pkg:npm/postcss-merge-idents@2.1.7", + "pkg:npm/postcss-merge-longhand@2.0.2", + "pkg:npm/postcss-merge-rules@2.1.2", + "pkg:npm/postcss-message-helpers@2.0.0", + "pkg:npm/postcss-minify-font-values@1.0.5", + "pkg:npm/postcss-minify-gradients@1.0.5", + "pkg:npm/postcss-minify-params@1.2.2", + "pkg:npm/postcss-minify-selectors@2.1.1", + "pkg:npm/postcss-modules-extract-imports@1.2.0", + "pkg:npm/postcss-modules-local-by-default@1.2.0", + "pkg:npm/postcss-modules-scope@1.1.0", + "pkg:npm/postcss-modules-values@1.3.0", + "pkg:npm/postcss-normalize-charset@1.1.1", + "pkg:npm/postcss-normalize-url@3.0.8", + "pkg:npm/postcss-ordered-values@2.2.3", + "pkg:npm/postcss-reduce-idents@2.4.0", + "pkg:npm/postcss-reduce-initial@1.0.1", + "pkg:npm/postcss-reduce-transforms@1.0.4", + "pkg:npm/postcss-selector-parser@2.2.3", + "pkg:npm/postcss-svgo@2.1.6", + "pkg:npm/postcss-unique-selectors@2.0.2", + "pkg:npm/postcss-value-parser@3.3.0", + "pkg:npm/postcss-zindex@2.2.0", + "pkg:npm/prelude-ls@1.1.2", + "pkg:npm/prepend-http@1.0.4", + "pkg:npm/preserve@0.2.0", + "pkg:npm/private@0.1.7", + "pkg:npm/process@0.11.10", + "pkg:npm/process-nextick-args@1.0.7", + "pkg:npm/progress@1.1.8", + "pkg:npm/promise@7.3.1", + "pkg:npm/prop-types@15.6.0", + "pkg:npm/prop-types-extra@1.0.1", + "pkg:npm/prr@0.0.0", + "pkg:npm/public-encrypt@4.0.0", + "pkg:npm/punycode@1.3.2", + "pkg:npm/punycode@1.4.1", + "pkg:pypi/python-dateutil@1.5", + "pkg:npm/q@1.5.0", + "pkg:npm/qs@6.4.0", + "pkg:npm/query-string@4.3.4", + "pkg:npm/querystring@0.2.0", + "pkg:npm/querystring-es3@0.2.1", + "pkg:npm/randomatic@1.1.7", + "pkg:npm/randombytes@2.0.5", + "pkg:npm/rc@1.2.1", + "pkg:npm/rcfinder@0.1.9", + "pkg:npm/rcloader@0.1.2", + "pkg:npm/react@15.6.2", + "pkg:npm/react-bootstrap@0.31.5", + "pkg:npm/react-dom@15.6.2", + "pkg:npm/react-overlays@0.7.4", + "pkg:npm/read-pkg@1.1.0", + "pkg:npm/read-pkg-up@1.0.1", + "pkg:npm/readable-stream@1.1.13", + "pkg:npm/readable-stream@2.2.11", + "pkg:npm/readable-stream@2.3.3", + "pkg:npm/readdirp@2.1.0", + "pkg:npm/readline2@1.0.1", + "pkg:npm/rechoir@0.6.2", + "pkg:npm/reduce-css-calc@1.3.0", + "pkg:npm/reduce-function-call@1.0.2", + "pkg:npm/regenerate@1.3.2", + "pkg:npm/regenerator-runtime@0.10.5", + "pkg:npm/regenerator-transform@0.9.11", + "pkg:npm/regex-cache@0.4.3", + "pkg:npm/regexpu-core@1.0.0", + "pkg:npm/regexpu-core@2.0.0", + "pkg:npm/regjsgen@0.2.0", + "pkg:npm/regjsparser@0.1.5", + "pkg:npm/remove-trailing-separator@1.0.2", + "pkg:npm/repeat-element@1.1.2", + "pkg:npm/repeat-string@1.6.1", + "pkg:npm/repeating@2.0.1", + "pkg:npm/request@2.81.0", + "pkg:npm/require-directory@2.1.1", + "pkg:npm/require-main-filename@1.0.1", + "pkg:npm/require-uncached@1.0.3", + "pkg:npm/resolve@1.4.0", + "pkg:npm/resolve-from@1.0.1", + "pkg:npm/restore-cursor@1.0.1", + "pkg:npm/right-align@0.1.3", + "pkg:npm/rimraf@2.6.1", + "pkg:npm/ripemd160@2.0.1", + "pkg:npm/run-async@0.1.0", + "pkg:npm/rx-lite@3.1.2", + "pkg:npm/safe-buffer@5.0.1", + "pkg:npm/safe-buffer@5.1.0", + "pkg:npm/safe-buffer@5.1.1", + "pkg:npm/sax@1.2.4", + "pkg:npm/schema-utils@0.3.0", + "pkg:npm/semver@5.3.0", + "pkg:npm/set-blocking@2.0.0", + "pkg:npm/set-immediate-shim@1.0.1", + "pkg:npm/setimmediate@1.0.5", + "pkg:npm/sha.js@2.4.8", + "pkg:npm/shelljs@0.3.0", + "pkg:npm/shelljs@0.7.8", + "pkg:npm/signal-exit@3.0.2", + "pkg:pypi/six@1.11.0", + "pkg:npm/slash@1.0.0", + "pkg:npm/slice-ansi@0.0.4", + "pkg:npm/sntp@1.0.9", + "pkg:npm/sort-keys@1.1.2", + "pkg:npm/source-list-map@0.1.8", + "pkg:npm/source-list-map@1.1.2", + "pkg:npm/source-list-map@2.0.0", + "pkg:npm/source-map@0.5.6", + "pkg:npm/source-map-support@0.4.15", + "pkg:npm/spdx-correct@1.0.2", + "pkg:npm/spdx-expression-parse@1.0.4", + "pkg:npm/spdx-license-ids@1.2.2", + "pkg:npm/sprintf-js@1.0.3", + "pkg:npm/sshpk@1.13.1", + "pkg:npm/stream-browserify@2.0.1", + "pkg:npm/stream-http@2.7.2", + "pkg:npm/strict-uri-encode@1.1.0", + "pkg:npm/string-width@1.0.2", + "pkg:npm/string-width@2.1.1", + "pkg:npm/string_decoder@0.10.31", + "pkg:npm/string_decoder@1.0.2", + "pkg:npm/string_decoder@1.0.3", + "pkg:npm/stringstream@0.0.5", + "pkg:npm/strip-ansi@0.1.1", + "pkg:npm/strip-ansi@3.0.1", + "pkg:npm/strip-ansi@4.0.0", + "pkg:npm/strip-bom@2.0.0", + "pkg:npm/strip-bom@3.0.0", + "pkg:npm/strip-json-comments@0.1.3", + "pkg:npm/strip-json-comments@1.0.4", + "pkg:npm/strip-json-comments@2.0.1", + "pkg:npm/style-loader@0.18.2", + "pkg:npm/subscription-manager@0.1.0", + "pkg:npm/supports-color@2.0.0", + "pkg:npm/supports-color@3.2.3", + "pkg:npm/supports-color@4.2.1", + "pkg:npm/svgo@0.7.2", + "pkg:npm/table@3.8.3", + "pkg:npm/tapable@0.2.6", + "pkg:npm/tar@2.2.1", + "pkg:npm/tar-pack@3.4.0", + "pkg:npm/text-table@0.2.0", + "pkg:npm/through@2.3.8", + "pkg:npm/timers-browserify@2.0.2", + "pkg:npm/to-arraybuffer@1.0.1", + "pkg:npm/to-fast-properties@1.0.3", + "pkg:npm/tough-cookie@2.3.2", + "pkg:npm/trim-right@1.0.1", + "pkg:npm/tryit@1.0.3", + "pkg:npm/tty-browserify@0.0.0", + "pkg:npm/tunnel-agent@0.6.0", + "pkg:npm/tweetnacl@0.14.5", + "pkg:npm/type-check@0.3.2", + "pkg:npm/typedarray@0.0.6", + "pkg:npm/ua-parser-js@0.7.14", + "pkg:npm/uglify-js@2.8.29", + "pkg:npm/uglify-to-browserify@1.0.2", + "pkg:npm/uid-number@0.0.6", + "pkg:npm/uncontrollable@4.1.0", + "pkg:npm/underscore@1.6.0", + "pkg:npm/uniq@1.0.1", + "pkg:npm/uniqid@4.1.1", + "pkg:npm/uniqs@2.0.0", + "pkg:npm/url@0.11.0", + "pkg:npm/user-home@2.0.0", + "pkg:npm/util@0.10.3", + "pkg:npm/util-deprecate@1.0.2", + "pkg:npm/uuid@3.0.1", + "pkg:npm/validate-npm-package-license@3.0.1", + "pkg:npm/vendors@1.0.1", + "pkg:npm/verror@1.3.6", + "pkg:npm/vm-browserify@0.0.4", + "pkg:npm/warning@3.0.0", + "pkg:npm/watchpack@1.3.1", + "pkg:npm/webpack@2.6.1", + "pkg:npm/webpack-sources@0.2.3", + "pkg:npm/webpack-sources@1.0.1", + "pkg:npm/whatwg-fetch@2.0.3", + "pkg:npm/whet.extend@0.9.9", + "pkg:npm/which-module@1.0.0", + "pkg:npm/wide-align@1.1.2", + "pkg:npm/window-size@0.1.0", + "pkg:npm/wordwrap@0.0.2", + "pkg:npm/wordwrap@1.0.0", + "pkg:npm/wrap-ansi@2.1.0", + "pkg:npm/wrappy@1.0.2", + "pkg:npm/write@0.2.1", + "pkg:npm/xtend@4.0.1", + "pkg:npm/y18n@3.2.1", + "pkg:npm/yargs@3.10.0", + "pkg:npm/yargs@6.6.0", + "pkg:npm/yargs-parser@4.2.1" + ] + }, + { + "name": "python-mock-2.0.0-11.oe1.src.rpm", + "purls": [ + "pkg:pypi/mock@2.0.0" + ] + }, + { + "name": "python-distro-1.3.0-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/distro@1.3.0" + ] + }, + { + "name": "python-zope-event-4.2.0-12.oe1.src.rpm", + "purls": [ + "pkg:pypi/zope.event@4.2.0" + ] + }, + { + "name": "rpmlint-1.10-18.oe1.src.rpm", + "purls": [ + "pkg:rpm/PamCheck@0.1-1?arch=i586&epoch=0&upstream=PamCheck-0.1-1.src.rpm", + "pkg:rpm/autofs@5.0.7-28.fc19?arch=i686&epoch=1&upstream=autofs-5.0.7-28.fc19.src.rpm", + "pkg:rpm/cyrus-imapd@2.4.17-9.fc22?arch=x86_64&epoch=0&upstream=cyrus-imapd-2.4.17-9.fc22.src.rpm", + "pkg:rpm/dovecot@2.2.9-1.fc20?arch=x86_64&epoch=1&upstream=dovecot-2.2.9-1.fc20.src.rpm", + "pkg:rpm/netmask-debugsource@2.4.3-5.fc27?arch=x86_64&epoch=0&upstream=netmask-2.4.3-5.fc27.src.rpm", + "pkg:rpm/ngircd@22-2.fc22?arch=x86_64&epoch=0&upstream=ngircd-22-2.fc22.src.rpm", + "pkg:rpm/nodejs010@1-7.el6_4?arch=x86_64&epoch=0", + "pkg:rpm/nodejs010-nodejs@0.10.3-3.el6_4?arch=x86_64&epoch=0&upstream=nodejs010-nodejs-0.10.3-3.el6_4.src.rpm", + "pkg:rpm/nodejs010-nodejs@0.10.3-3.el6_4?arch=x86_64&epoch=0", + "pkg:rpm/nodejs010-nodejs-forever-agent@0.2.0-2.el6_4?arch=noarch&epoch=0", + "pkg:rpm/nodejs010-nodejs-oauth-sign@0.2.0-2.el6_4?arch=noarch&epoch=0&upstream=nodejs010-nodejs-oauth-sign-0.2.0-2.el6_4.src.rpm", + "pkg:rpm/nodejs010-nodejs-oauth-sign@0.2.0-2.el6_4?arch=noarch&epoch=0&upstream=nodejs010-nodejs-oauth-sign-0.2.0-2.el6_4.src.rpm", + "pkg:rpm/nodejs010-nodejs-oauth-sign@0.2.0-2.el6_4?arch=noarch&epoch=0&upstream=nodejs010-nodejs-oauth-sign-0.2.0-2.el6_4.src.rpm", + "pkg:rpm/nodejs010-runtime@1-7.el6_4?arch=x86_64&epoch=0&upstream=nodejs010-1-7.el6_4.src.rpm", + "pkg:rpm/nodejs110-nodejs-oauth-sign@0.2.0-2.el6_4?arch=noarch&epoch=0&upstream=nodejs110-nodejs-oauth-sign-0.2.0-2.el6_4.src.rpm", + "pkg:rpm/non-utf8@1.0-1.el5.centos?arch=x86_64&epoch=0&upstream=non-utf8-1.0-1.el5.centos.src.rpm", + "pkg:rpm/non-utf8@1.0-1.el5.centos?arch=x86_64&epoch=0", + "pkg:rpm/python3-power@1.1-4.20121103git2cfe611.fc19?arch=noarch&epoch=0&upstream=python-power-1.1-4.20121103git2cfe611.fc19.src.rpm" + ] + }, + { + "name": "libdnf-0.37.2-2.oe1.src.rpm", + "purls": [ + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0", + "pkg:rpm/basesystem@10.0-7?arch=noarch&epoch=0&upstream=basesystem-10.0-7.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0", + "pkg:rpm/basesystem@11-3?arch=noarch&epoch=0&upstream=basesystem-11-3.src.rpm", + "pkg:rpm/bash@4.2.46-21?arch=i686&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash@4.2.46-21?arch=s390x&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash@4.2.46-21?arch=x86_64&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash@4.2.46-21?arch=i686&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash@4.2.46-21?arch=s390x&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash@4.2.46-21?arch=s390x&epoch=0", + "pkg:rpm/bash@4.2.46-21?arch=x86_64&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=i686&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=s390x&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=x86_64&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=i686&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=s390x&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=s390x&epoch=0", + "pkg:rpm/bash@4.4.12-2?arch=x86_64&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=i686&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=s390x&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash@4.4.12-2?arch=s390x&epoch=0", + "pkg:rpm/bash@4.4.12-2?arch=x86_64&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.2.46-21?arch=noarch&epoch=0&upstream=bash-4.2.46-21.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/bash-doc@4.4.12-2?arch=noarch&epoch=0&upstream=bash-4.4.12-2.src.rpm", + "pkg:rpm/dummy-nscd@2.17-157?arch=i686&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/dummy-nscd@2.17-157?arch=s390x&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/dummy-nscd@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/dummy-nscd@2.17-157?arch=i686&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/dummy-nscd@2.17-157?arch=s390x&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/dummy-nscd@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/dummy-nscd@2.25-4?arch=i686&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/dummy-nscd@2.25-4?arch=s390x&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/dummy-nscd@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/dummy-nscd@2.25-4?arch=i686&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/dummy-nscd@2.25-4?arch=s390x&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/dummy-nscd@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/dummy-nscd@2.25.90-2?arch=i686&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/dummy-nscd@2.25.90-2?arch=s390x&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/dummy-nscd@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/dummy-nscd@2.25.90-2?arch=i686&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/dummy-nscd@2.25.90-2?arch=s390x&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/dummy-nscd@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/filesystem@3.2-21?arch=i686&epoch=0&upstream=filesystem-3.2-21.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=i686&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-21?arch=s390x&epoch=0&upstream=filesystem-3.2-21.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=s390x&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-21?arch=x86_64&epoch=0&upstream=filesystem-3.2-21.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=x86_64&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=i686&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=s390x&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=s390x&epoch=0", + "pkg:rpm/filesystem@3.2-40?arch=x86_64&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=i686&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=s390x&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-40?arch=s390x&epoch=0", + "pkg:rpm/filesystem@3.2-40?arch=x86_64&epoch=0&upstream=filesystem-3.2-40.src.rpm", + "pkg:rpm/filesystem@3.2-21?arch=i686&epoch=0&upstream=filesystem-3.2-21.src.rpm", + "pkg:rpm/filesystem@3.2-21?arch=s390x&epoch=0&upstream=filesystem-3.2-21.src.rpm", + "pkg:rpm/filesystem@3.2-21?arch=s390x&epoch=0", + "pkg:rpm/filesystem@3.2-21?arch=x86_64&epoch=0&upstream=filesystem-3.2-21.src.rpm", + "pkg:rpm/glibc@2.17-157?arch=i686&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc@2.17-157?arch=s390x&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc@2.17-157?arch=i686&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc@2.17-157?arch=s390x&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc@2.17-157?arch=s390x&epoch=0", + "pkg:rpm/glibc@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc@2.25-4?arch=i686&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc@2.25-4?arch=s390x&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc@2.25-4?arch=i686&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc@2.25-4?arch=s390x&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc@2.25-4?arch=s390x&epoch=0", + "pkg:rpm/glibc@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc@2.25.90-2?arch=i686&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc@2.25.90-2?arch=s390x&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc@2.25.90-2?arch=i686&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc@2.25.90-2?arch=s390x&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc@2.25.90-2?arch=s390x&epoch=0", + "pkg:rpm/glibc@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-common@2.17-157?arch=i686&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-common@2.17-157?arch=s390x&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-common@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-common@2.17-157?arch=i686&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-common@2.17-157?arch=s390x&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-common@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-common@2.25-4?arch=i686&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-common@2.25-4?arch=s390x&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-common@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-common@2.25-4?arch=i686&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-common@2.25-4?arch=s390x&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-common@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-common@2.25.90-2?arch=i686&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-common@2.25.90-2?arch=s390x&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-common@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-common@2.25.90-2?arch=i686&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-common@2.25.90-2?arch=s390x&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-common@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.17-157?arch=i686&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.17-157?arch=s390x&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.17-157?arch=i686&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.17-157?arch=s390x&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.17-157?arch=x86_64&epoch=0&upstream=glibc-2.17-157.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25-4?arch=i686&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25-4?arch=s390x&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25-4?arch=i686&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25-4?arch=s390x&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25-4?arch=x86_64&epoch=0&upstream=glibc-2.25-4.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25.90-2?arch=i686&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25.90-2?arch=s390x&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25.90-2?arch=i686&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25.90-2?arch=s390x&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/glibc-debuginfo-common@2.25.90-2?arch=x86_64&epoch=0&upstream=glibc-2.25.90-2.src.rpm", + "pkg:rpm/grub2@2.02-0.40?arch=i686&epoch=0&upstream=grub2-2.02-0.40.src.rpm", + "pkg:rpm/grub2@2.02-0.40?arch=s390x&epoch=0&upstream=grub2-2.02-0.40.src.rpm", + "pkg:rpm/grub2@2.02-0.40?arch=x86_64&epoch=0&upstream=grub2-2.02-0.40.src.rpm", + "pkg:rpm/grub2@2.02-0.40?arch=i686&epoch=0&upstream=grub2-2.02-0.40.src.rpm", + "pkg:rpm/grub2@2.02-0.40?arch=s390x&epoch=0&upstream=grub2-2.02-0.40.src.rpm", + "pkg:rpm/grub2@2.02-0.40?arch=s390x&epoch=0", + "pkg:rpm/grub2@2.02-0.40?arch=x86_64&epoch=0&upstream=grub2-2.02-0.40.src.rpm", + "pkg:rpm/httpd@2.2.10-1?arch=i686&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd@2.2.10-1?arch=s390x&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd@2.2.10-1?arch=x86_64&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd@2.2.10-1?arch=i686&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd@2.2.10-1?arch=s390x&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd@2.2.10-1?arch=s390x&epoch=0", + "pkg:rpm/httpd@2.2.10-1?arch=x86_64&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd@2.2.15-59?arch=i686&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd@2.2.15-59?arch=s390x&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd@2.2.15-59?arch=x86_64&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd@2.2.15-59?arch=i686&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd@2.2.15-59?arch=s390x&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd@2.2.15-59?arch=s390x&epoch=0", + "pkg:rpm/httpd@2.2.15-59?arch=x86_64&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd@2.4.25-7?arch=i686&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd@2.4.25-8?arch=i686&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd@2.4.25-7?arch=s390x&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd@2.4.25-8?arch=s390x&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd@2.4.25-7?arch=x86_64&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd@2.4.25-8?arch=x86_64&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd@2.4.25-7?arch=i686&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd@2.4.25-7?arch=s390x&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd@2.4.25-7?arch=s390x&epoch=0", + "pkg:rpm/httpd@2.4.25-7?arch=x86_64&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd@2.4.25-8?arch=i686&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd@2.4.25-8?arch=s390x&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd@2.4.25-8?arch=s390x&epoch=0", + "pkg:rpm/httpd@2.4.25-8?arch=x86_64&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-doc@2.2.10-1?arch=i686&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd-doc@2.2.10-1?arch=s390x&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd-doc@2.2.10-1?arch=x86_64&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd-doc@2.2.10-1?arch=i686&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd-doc@2.2.10-1?arch=s390x&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd-doc@2.2.10-1?arch=x86_64&epoch=0&upstream=httpd-2.2.10-1.src.rpm", + "pkg:rpm/httpd-doc@2.2.15-59?arch=i686&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd-doc@2.2.15-59?arch=s390x&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd-doc@2.2.15-59?arch=x86_64&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd-doc@2.2.15-59?arch=i686&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd-doc@2.2.15-59?arch=s390x&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd-doc@2.2.15-59?arch=x86_64&epoch=0&upstream=httpd-2.2.15-59.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-7?arch=i686&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-8?arch=i686&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-7?arch=s390x&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-8?arch=s390x&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-7?arch=x86_64&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-8?arch=x86_64&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-7?arch=i686&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-7?arch=s390x&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-7?arch=x86_64&epoch=0&upstream=httpd-2.4.25-7.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-8?arch=i686&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-8?arch=s390x&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-doc@2.4.25-8?arch=x86_64&epoch=0&upstream=httpd-2.4.25-8.src.rpm", + "pkg:rpm/httpd-provides-name@3.0-1?arch=i686&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name@3.0-1?arch=s390x&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name@3.0-1?arch=i686&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name@3.0-1?arch=s390x&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name@3.0-1?arch=s390x&epoch=0", + "pkg:rpm/httpd-provides-name@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-doc@3.0-1?arch=i686&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-doc@3.0-1?arch=s390x&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-doc@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-doc@3.0-1?arch=i686&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-doc@3.0-1?arch=s390x&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-doc@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=i686&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=s390x&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=i686&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=s390x&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=s390x&epoch=0", + "pkg:rpm/httpd-provides-name-version-release@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release-doc@3.0-1?arch=i686&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release-doc@3.0-1?arch=s390x&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release-doc@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release-doc@3.0-1?arch=i686&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release-doc@3.0-1?arch=s390x&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/httpd-provides-name-version-release-doc@3.0-1?arch=x86_64&epoch=0&upstream=httpd-provides-name-version-release-3.0-1.src.rpm", + "pkg:rpm/kernel@3.10.0-514?arch=i686&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel@3.10.0-514?arch=s390x&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel@3.10.0-514?arch=x86_64&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel@3.10.0-514?arch=i686&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel@3.10.0-514?arch=s390x&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel@3.10.0-514?arch=s390x&epoch=0", + "pkg:rpm/kernel@3.10.0-514?arch=x86_64&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=i686&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=s390x&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=i686&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=s390x&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=s390x&epoch=0", + "pkg:rpm/kernel@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=i686&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=s390x&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel@4.11.0-1?arch=s390x&epoch=0", + "pkg:rpm/kernel@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@3.10.0-514?arch=noarch&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-doc@4.11.0-1?arch=noarch&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@3.10.0-514?arch=i686&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-headers@3.10.0-514?arch=s390x&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-headers@3.10.0-514?arch=x86_64&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-headers@3.10.0-514?arch=i686&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-headers@3.10.0-514?arch=s390x&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-headers@3.10.0-514?arch=x86_64&epoch=0&upstream=kernel-3.10.0-514.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=i686&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=s390x&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=i686&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=s390x&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=i686&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=s390x&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/kernel-headers@4.11.0-1?arch=x86_64&epoch=0&upstream=kernel-4.11.0-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=i686&epoch=0&upstream=libnghttp2-1.21.1-1.1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=i686&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=s390x&epoch=0&upstream=libnghttp2-1.21.1-1.1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=s390x&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=i686&epoch=0&upstream=libnghttp2-1.21.1-1.1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=s390x&epoch=0&upstream=libnghttp2-1.21.1-1.1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=s390x&epoch=0", + "pkg:rpm/libnghttp2@1.21.1-1.1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=i686&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=s390x&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=s390x&epoch=0", + "pkg:rpm/libnghttp2@1.21.1-1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=i686&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=s390x&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/libnghttp2@1.21.1-1?arch=s390x&epoch=0", + "pkg:rpm/libnghttp2@1.21.1-1?arch=x86_64&epoch=0&upstream=libnghttp2-1.21.1-1.src.rpm", + "pkg:rpm/mystery-devel@19.67-1?arch=noarch&epoch=0&upstream=mystery-19.67-1.src.rpm", + "pkg:rpm/systemd@219-30?arch=i686&epoch=0&upstream=systemd-219-30.src.rpm", + "pkg:rpm/systemd@219-30?arch=s390x&epoch=0&upstream=systemd-219-30.src.rpm", + "pkg:rpm/systemd@219-30?arch=x86_64&epoch=0&upstream=systemd-219-30.src.rpm", + "pkg:rpm/systemd@219-30?arch=i686&epoch=0&upstream=systemd-219-30.src.rpm", + "pkg:rpm/systemd@219-30?arch=s390x&epoch=0&upstream=systemd-219-30.src.rpm", + "pkg:rpm/systemd@219-30?arch=s390x&epoch=0", + "pkg:rpm/systemd@219-30?arch=x86_64&epoch=0&upstream=systemd-219-30.src.rpm", + "pkg:rpm/systemd@233-3?arch=i686&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=s390x&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=x86_64&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=i686&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=s390x&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=s390x&epoch=0", + "pkg:rpm/systemd@233-3?arch=x86_64&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=i686&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=s390x&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/systemd@233-3?arch=s390x&epoch=0", + "pkg:rpm/systemd@233-3?arch=x86_64&epoch=0&upstream=systemd-233-3.src.rpm", + "pkg:rpm/tour@4-5?arch=noarch&epoch=0&upstream=tour-4-5.src.rpm", + "pkg:rpm/tour@4-6?arch=noarch&epoch=0&upstream=tour-4-6.src.rpm" + ] + }, + { + "name": "python-xgboost-0.90-2.oe1.src.rpm", + "purls": [ + "pkg:maven/commons-cli/commons-cli", + "pkg:maven/commons-io/commons-io", + "pkg:maven/commons-lang/commons-lang", + "pkg:maven/commons-logging/commons-logging", + "pkg:maven/com.google.guava/guava", + "pkg:maven/org.apache.hadoop/hadoop-annotations", + "pkg:maven/org.apache.hadoop/hadoop-common", + "pkg:maven/org.apache.hadoop/hadoop-yarn-api", + "pkg:maven/org.apache.hadoop/hadoop-yarn-client", + "pkg:maven/org.apache.hadoop/hadoop-yarn-common", + "pkg:maven/org.apache.hadoop/hadoop-yarn-server-nodemanager", + "pkg:maven/org.apache.hadoop/hadoop-yarn-server-resourcemanager", + "pkg:maven/org.apache.hadoop/hadoop-yarn-server-tests", + "pkg:maven/junit/junit", + "pkg:maven/log4j/log4j", + "pkg:pypi/xgboost@0.90" + ] + }, + { + "name": "fuse-python-0.2.1-24.oe1.src.rpm", + "purls": [ + "pkg:pypi/fuse-python@0.2.1" + ] + }, + { + "name": "python-extras-1.0.0-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/extras@1.0.0" + ] + }, + { + "name": "python-hypothesis-3.66.11-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/%r@x.", + "pkg:gem/ast@2.4.0", + "pkg:gem/diff-lcs@1.3", + "pkg:gem/docile@1.1.5", + "pkg:gem/helix_runtime@0.7.5", + "pkg:gem/json@2.1.0", + "pkg:gem/minitest@5.8.5", + "pkg:gem/parallel@1.12.1", + "pkg:gem/parser@2.5.1.0", + "pkg:gem/powerpack@0.1.1", + "pkg:gem/rainbow@2.2.2", + "pkg:gem/rake@12.3.1", + "pkg:gem/redcarpet@3.4.0", + "pkg:gem/rspec@3.7.0", + "pkg:gem/rspec-core@3.7.1", + "pkg:gem/rspec-expectations@3.7.0", + "pkg:gem/rspec-mocks@3.7.0", + "pkg:gem/rspec-support@3.7.1", + "pkg:gem/rubocop@0.51.0", + "pkg:gem/ruby-progressbar@1.9.0", + "pkg:gem/simplecov@0.15.1", + "pkg:gem/simplecov-html@0.10.2", + "pkg:gem/thor@0.20.0", + "pkg:gem/tomlrb@1.2.7", + "pkg:gem/unicode-display_width@1.3.2", + "pkg:gem/yard@0.9.12" + ] + }, + { + "name": "python-traceback2-1.4.0-19.oe1.src.rpm", + "purls": [ + "pkg:pypi/traceback2@1.4.0" + ] + }, + { + "name": "python-pytoml-0.1.18-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytest@3.0.7" + ] + }, + { + "name": "python-enum34-1.1.6-8.oe1.src.rpm", + "purls": [ + "pkg:pypi/enum34@1.1.6" + ] + }, + { + "name": "python-ethtool-0.14-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/ethtool@0.14" + ] + }, + { + "name": "pyliblzma-0.5.3-28.oe1.src.rpm", + "purls": [ + "pkg:pypi/pyliblzma@0.5.3" + ] + }, + { + "name": "python2-typing-3.6.2-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/typing@3.6.2" + ] + }, + { + "name": "golang-1.13-3.3.oe1.src.rpm", + "purls": [ + "pkg:golang/github.com/google/pprof@v0.0.0-20190515194954-54271f7e092f", + "pkg:golang/github.com/ianlancetaylor/demangle@v0.0.0-20180524225900-fc6590592b44", + "pkg:golang/golang.org/x/arch@v0.0.0-20190815191158-8a70ba74b3a1", + "pkg:golang/golang.org/x/crypto@v0.0.0-20190325154230-a5d413f7728c", + "pkg:golang/golang.org/x/crypto@v0.0.0-20190611184440-5c40567a22f8", + "pkg:golang/golang.org/x/net@v0.0.0-20190813141303-74dc4d7220e7", + "pkg:golang/golang.org/x/sys@v0.0.0-20190502175342-a43fa875dd82", + "pkg:golang/golang.org/x/sys@v0.0.0-20190529130038-5219a1e1c5f8", + "pkg:golang/golang.org/x/text@v0.3.2", + "pkg:golang/golang.org/x/tools@v0.0.0-20190611154301-25a4f137592f" + ] + }, + { + "name": "python-oauthlib-3.0.2-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/blinker@1.4", + "pkg:pypi/pyjwt@1.6.0" + ] + }, + { + "name": "python-cryptography-vectors-2.6.1-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/cryptography-vectors@2.6.1" + ] + }, + { + "name": "python-psycopg2-2.7.5-3.2.oe1.src.rpm", + "purls": [ + "pkg:pypi/psycopg2@2.7.5" + ] + }, + { + "name": "mercurial-5.1-2.oe1.src.rpm", + "purls": [ + "pkg:cargo/aho-corasick@0.5.3", + "pkg:cargo/aho-corasick@0.6.9", + "pkg:cargo/arrayvec@0.4.7", + "pkg:pypi/asn1crypto@0.24.0 ", + "pkg:pypi/astroid@1.6.6 ", + "pkg:pypi/astroid@2.2.5 ", + "pkg:cargo/autocfg@0.1.2", + "pkg:pypi/backports.functools-lru-cache@1.5 ", + "pkg:pypi/bcrypt@3.1.6 ", + "pkg:cargo/bitflags@1.0.4", + "pkg:cargo/bitflags@1.0.4", + "pkg:pypi/boto3@1.9.137 ", + "pkg:pypi/botocore@1.12.137 ", + "pkg:cargo/byteorder@1.2.6", + "pkg:cargo/byteorder@1.3.1", + "pkg:cargo/bytes@0.4.10", + "pkg:pypi/bzr@2.7.0", + "pkg:cargo/cc@1.0.25", + "pkg:pypi/certifi@2018.11.29 ", + "pkg:pypi/certifi@2019.3.9 ", + "pkg:pypi/cffi@1.12.3 ", + "pkg:cargo/cfg-if@0.1.5", + "pkg:pypi/chardet@3.0.4 ", + "pkg:cargo/chg@0.1.0", + "pkg:cargo/cloudabi@0.0.3", + "pkg:cargo/cloudabi@0.0.3", + "pkg:pypi/configparser@3.7.3 ", + "pkg:pypi/configparser@3.7.4 ", + "pkg:pypi/contextlib2@0.5.5 ", + "pkg:cargo/cpython@0.1.0", + "pkg:cargo/cpython@0.2.1", + "pkg:cargo/crossbeam-deque@0.6.1", + "pkg:cargo/crossbeam-epoch@0.5.2", + "pkg:cargo/crossbeam-utils@0.5.0", + "pkg:pypi/cryptography@2.6.1 ", + "pkg:pypi/docutils@0.14 ", + "pkg:pypi/docutils@0.14 ", + "pkg:pypi/docutils@0.14 ", + "pkg:pypi/docutils@0.14 ", + "pkg:pypi/docutils@0.14 ", + "pkg:pypi/dulwich@0.19.11 ", + "pkg:pypi/entrypoints@0.3 ", + "pkg:pypi/enum34@1.1.6 ", + "pkg:cargo/fuchsia-cprng@0.1.0", + "pkg:cargo/fuchsia-zircon@0.3.3", + "pkg:cargo/fuchsia-zircon-sys@0.3.3", + "pkg:pypi/funcsigs@1.0.2 ", + "pkg:cargo/futures@0.1.24", + "pkg:pypi/futures@3.2.0 ", + "pkg:pypi/fuzzywuzzy@0.17.0 ", + "pkg:pypi/fuzzywuzzy@0.17.0 ", + "pkg:cargo/hg-core@0.1.0", + "pkg:cargo/hg-cpython@0.1.0", + "pkg:cargo/hgcli@0.1.0", + "pkg:cargo/hgdirectffi@0.1.0", + "pkg:pypi/idna@2.8 ", + "pkg:pypi/idna@2.8 ", + "pkg:cargo/iovec@0.1.2", + "pkg:pypi/isort@4.3.17 ", + "pkg:pypi/isort@4.3.17 ", + "pkg:pypi/jmespath@0.9.4 ", + "pkg:cargo/kernel32-sys@0.2.2", + "pkg:cargo/kernel32-sys@0.2.2", + "pkg:pypi/keyring@18.0.1 ", + "pkg:pypi/lazy-object-proxy@1.3.1 ", + "pkg:pypi/lazy-object-proxy@1.3.1 ", + "pkg:cargo/lazy_static@1.1.0", + "pkg:cargo/lazy_static@1.3.0", + "pkg:cargo/lazycell@1.2.0", + "pkg:cargo/libc@0.2.43", + "pkg:cargo/libc@0.2.45", + "pkg:cargo/libc@0.2.45", + "pkg:cargo/lock_api@0.1.4", + "pkg:cargo/log@0.4.5", + "pkg:pypi/mccabe@0.6.1 ", + "pkg:pypi/mccabe@0.6.1 ", + "pkg:cargo/memchr@0.1.11", + "pkg:cargo/memchr@2.2.0", + "pkg:cargo/memoffset@0.2.1", + "pkg:cargo/mio@0.6.16", + "pkg:cargo/mio-named-pipes@0.1.6", + "pkg:cargo/mio-uds@0.6.7", + "pkg:cargo/miow@0.2.1", + "pkg:cargo/miow@0.3.3", + "pkg:pypi/mock@2.0.0 ", + "pkg:pypi/multidict@4.5.2 ", + "pkg:cargo/net2@0.2.33", + "pkg:cargo/nodrop@0.1.12", + "pkg:pypi/ntlm-auth@1.3.0 ", + "pkg:cargo/num-traits@0.1.43", + "pkg:cargo/num-traits@0.2.6", + "pkg:cargo/num-traits@0.2.6", + "pkg:cargo/num_cpus@1.8.0", + "pkg:cargo/owning_ref@0.3.3", + "pkg:pypi/paramiko@2.4.2 ", + "pkg:cargo/parking_lot@0.6.4", + "pkg:cargo/parking_lot_core@0.3.1", + "pkg:pypi/pbr@5.1.3 ", + "pkg:pypi/pyasn1@0.4.5 ", + "pkg:pypi/pycparser@2.19 ", + "pkg:pypi/pyflakes@2.1.1 ", + "pkg:pypi/pyflakes@2.1.1 ", + "pkg:pypi/pygments@2.3.1 ", + "pkg:pypi/pygments@2.3.1 ", + "pkg:pypi/pygments@2.3.1 ", + "pkg:pypi/pygments@2.3.1 ", + "pkg:pypi/pylint@1.9.4 ", + "pkg:pypi/pylint@2.3.1 ", + "pkg:pypi/pynacl@1.3.0 ", + "pkg:pypi/pypsrp@0.3.1 ", + "pkg:pypi/python-dateutil@2.8.0 ", + "pkg:pypi/python-levenshtein@0.12.0 ", + "pkg:pypi/python-levenshtein@0.12.0 ", + "pkg:cargo/python27-sys@0.1.2", + "pkg:cargo/python27-sys@0.2.1", + "pkg:cargo/python3-sys@0.2.1", + "pkg:pypi/pywin32-ctypes@0.2.0 ", + "pkg:pypi/pyyaml@5.1 ", + "pkg:pypi/pyyaml@5.1 ", + "pkg:cargo/rand@0.5.5", + "pkg:cargo/rand@0.6.5", + "pkg:cargo/rand_chacha@0.1.1", + "pkg:cargo/rand_core@0.2.1", + "pkg:cargo/rand_core@0.3.1", + "pkg:cargo/rand_core@0.4.0", + "pkg:cargo/rand_hc@0.1.0", + "pkg:cargo/rand_isaac@0.1.1", + "pkg:cargo/rand_jitter@0.1.2", + "pkg:cargo/rand_os@0.1.2", + "pkg:cargo/rand_pcg@0.1.1", + "pkg:cargo/rand_xorshift@0.1.1", + "pkg:cargo/rdrand@0.4.0", + "pkg:cargo/redox_syscall@0.1.40", + "pkg:cargo/regex@0.1.80", + "pkg:cargo/regex@1.1.0", + "pkg:cargo/regex-syntax@0.3.9", + "pkg:cargo/regex-syntax@0.6.4", + "pkg:pypi/requests@2.21.0 ", + "pkg:cargo/rustc_version@0.2.3", + "pkg:cargo/rustc_version@0.2.3", + "pkg:pypi/s3transfer@0.2.0 ", + "pkg:cargo/scopeguard@0.3.3", + "pkg:cargo/semver@0.9.0", + "pkg:cargo/semver@0.9.0", + "pkg:cargo/semver-parser@0.7.0", + "pkg:cargo/semver-parser@0.7.0", + "pkg:pypi/singledispatch@3.4.0.3 ", + "pkg:pypi/six@1.12.0 ", + "pkg:pypi/six@1.12.0 ", + "pkg:pypi/six@1.12.0 ", + "pkg:cargo/slab@0.4.1", + "pkg:cargo/smallvec@0.6.5", + "pkg:cargo/socket2@0.3.8", + "pkg:cargo/stable_deref_trait@1.1.1", + "pkg:cargo/thread-id@2.0.0", + "pkg:cargo/thread_local@0.2.7", + "pkg:cargo/thread_local@0.3.6", + "pkg:cargo/tokio@0.1.11", + "pkg:cargo/tokio-codec@0.1.1", + "pkg:cargo/tokio-current-thread@0.1.3", + "pkg:cargo/tokio-executor@0.1.5", + "pkg:cargo/tokio-fs@0.1.3", + "pkg:cargo/tokio-hglib@0.2.0", + "pkg:cargo/tokio-io@0.1.9", + "pkg:cargo/tokio-process@0.2.2", + "pkg:cargo/tokio-process@0.2.2", + "pkg:cargo/tokio-reactor@0.1.6", + "pkg:cargo/tokio-signal@0.2.5", + "pkg:cargo/tokio-tcp@0.1.2", + "pkg:cargo/tokio-threadpool@0.1.7", + "pkg:cargo/tokio-timer@0.2.7", + "pkg:cargo/tokio-udp@0.1.2", + "pkg:cargo/tokio-uds@0.2.2", + "pkg:pypi/typed-ast@1.3.4", + "pkg:cargo/ucd-util@0.1.3", + "pkg:cargo/unreachable@1.0.0", + "pkg:pypi/urllib3@1.24.1 ", + "pkg:pypi/urllib3@1.24.2 ", + "pkg:cargo/utf8-ranges@0.1.3", + "pkg:cargo/utf8-ranges@1.0.2", + "pkg:pypi/vcrpy@2.0.1 ", + "pkg:pypi/vcrpy@2.0.1 ", + "pkg:cargo/version_check@0.1.5", + "pkg:cargo/void@1.0.2", + "pkg:cargo/winapi@0.2.8", + "pkg:cargo/winapi@0.2.8", + "pkg:cargo/winapi@0.3.6", + "pkg:cargo/winapi@0.3.6", + "pkg:cargo/winapi-build@0.1.1", + "pkg:cargo/winapi-build@0.1.1", + "pkg:cargo/winapi-i686-pc-windows-gnu@0.4.0", + "pkg:cargo/winapi-i686-pc-windows-gnu@0.4.0", + "pkg:cargo/winapi-x86_64-pc-windows-gnu@0.4.0", + "pkg:cargo/winapi-x86_64-pc-windows-gnu@0.4.0", + "pkg:pypi/wrapt@1.11.1 ", + "pkg:pypi/wrapt@1.11.1 ", + "pkg:cargo/ws2_32-sys@0.2.1", + "pkg:pypi/yarl@1.3.0 " + ] + }, + { + "name": "python-py-1.5.4-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/apipkg@1.4", + "pkg:pypi/iniconfig@1.0.0", + "pkg:pypi/py@1.5.4" + ] + }, + { + "name": "python-ply-3.9-9.oe1.src.rpm", + "purls": [ + "pkg:pypi/ply@3.9" + ] + }, + { + "name": "python-singledispatch-3.4.0.3-14.oe1.src.rpm", + "purls": [ + "pkg:pypi/singledispatch@3.4.0.3" + ] + }, + { + "name": "pyelftools-0.25-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/pyelftools@0.25" + ] + }, + { + "name": "python-imagesize-1.0.0-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/imagesize@1.0.0" + ] + }, + { + "name": "python-setuptools-40.4.3-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/certifi@2016.9.26", + "pkg:pypi/setuptools@40.4.3", + "pkg:pypi/wincertstore@0.2" + ] + }, + { + "name": "python-PyMySQL-0.9.2-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/PyMySQL@0.9.2" + ] + }, + { + "name": "python-apipkg-1.5-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/apipkg@1.5" + ] + }, + { + "name": "python-ecdsa-0.14.1-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/ecdsa@0.14.1" + ] + }, + { + "name": "libwebp-1.0.0-5.oe1.src.rpm", + "purls": [ + "pkg:maven/gradle-wrapper/gradle-wrapper@2.13", + "pkg:maven/libwebp/libwebp" + ] + }, + { + "name": "authz-0.1-16.oe1.src.rpm", + "purls": [ + "pkg:golang/github.com/BurntSushi/toml@v0.3.1", + "pkg:golang/github.com/Microsoft/go-winio@v0.4.14", + "pkg:golang/github.com/containerd/continuity@v0.0.0-20190815185530-f2a389ac0a02", + "pkg:golang/github.com/davecgh/go-spew@v1.1.1", + "pkg:golang/github.com/docker/docker@v0.0.0-00010101000000-000000000000", + "pkg:golang/github.com/docker/engine@v0.0.0-20190717160951-456712c5b8d9", + "pkg:golang/github.com/docker/go-connections@v0.4.0", + "pkg:golang/github.com/docker/go-units@v0.4.0", + "pkg:golang/github.com/go-yaml/yaml@v2.1.0 incompatible", + "pkg:golang/github.com/golang/crypto@v0.0.0-20190701094942-4def268fd1a4", + "pkg:golang/github.com/golang/net@v0.0.0-20190813141303-74dc4d7220e7", + "pkg:golang/github.com/golang/sync@v0.0.0-20190423024810-112230192c58", + "pkg:golang/github.com/golang/sys@v0.0.0-20190813064441-fde4db37ae7a", + "pkg:golang/github.com/golang/text@v0.3.2", + "pkg:golang/github.com/golang/tools@v0.0.0-20190816200558-6889da9d5479", + "pkg:golang/github.com/golang/xerrors@v0.0.0-20190717185122-a985d3407aa7", + "pkg:golang/github.com/gorilla/mux@v1.7.3", + "pkg:golang/github.com/konsorten/go-windows-terminal-sequences@v1.0.1", + "pkg:golang/github.com/opencontainers/go-digest@v1.0.0-rc1", + "pkg:golang/github.com/opencontainers/image-spec@v1.0.1", + "pkg:golang/github.com/pkg/errors@v0.8.1", + "pkg:golang/github.com/pmezard/go-difflib@v1.0.0", + "pkg:golang/github.com/sirupsen/logrus@v1.4.1", + "pkg:golang/github.com/sirupsen/logrus@v1.4.2", + "pkg:golang/github.com/stretchr/objx@v0.1.1", + "pkg:golang/github.com/stretchr/testify@v1.2.2", + "pkg:golang/github.com/urfave/cli@v1.21.0", + "pkg:golang/golang.org/x/crypto@v0.0.0-20190308221718-c2843e01d9a2", + "pkg:golang/golang.org/x/sys@v0.0.0-20190422165155-953cdadca894", + "pkg:golang/golang.org/x/sys@v0.0.0-20190507160741-ecd444e8653b", + "pkg:golang/gopkg.in/yaml.v2@v2.2.2" + ] + }, + { + "name": "libidn-1.35-8.oe1.src.rpm", + "purls": [ + "pkg:maven/libidn/libidn@1.35" + ] + }, + { + "name": "python-jsonpointer-1.10-15.oe1.src.rpm", + "purls": [ + "pkg:pypi/jsonpointer@1.10" + ] + }, + { + "name": "babel-2.7.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/Babel@2.7.0" + ] + }, + { + "name": "python-idna-2.8-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/idna@2.8" + ] + }, + { + "name": "python-more-itertools-4.1.0-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/more-itertools@4.1.0" + ] + }, + { + "name": "google-noto-cjk-fonts-20170602-9.oe1.src.rpm", + "purls": [ + "pkg:rpm/google-noto-cjk-fonts@20170602-9.oe1?arch=noarch&epoch=0" + ] + }, + { + "name": "qt-4.8.7-47.oe1.src.rpm", + "purls": [ + "pkg:rpm/qt@4.8.7-47.oe1?arch=aarch64&epoch=1" + ] + }, + { + "name": "python-urwid-2.0.1-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/urwid@2.0.1" + ] + }, + { + "name": "python-constantly-15.1.0-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/constantly@15.1.0" + ] + }, + { + "name": "python-prettytable-0.7.2-18.oe1.src.rpm", + "purls": [ + "pkg:pypi/prettytable@0.7.2" + ] + }, + { + "name": "python-fixtures-3.0.0-12.oe1.src.rpm", + "purls": [ + "pkg:pypi/fixtures@3.0.0" + ] + }, + { + "name": "python-urlgrabber-4.0.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/urlgrabber@4.0.0" + ] + }, + { + "name": "kernel-4.19.90-2003.4.0.0036.oe1.src.rpm", + "purls": [ + "pkg:rpm/kernel@4.19.90-2003.4.0.0036.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "python-olefile-0.46-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/olefile@0.46" + ] + }, + { + "name": "python-six-1.12.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/six@1.12.0" + ] + }, + { + "name": "python-httpretty-0.9.5-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/httpretty@0.9.5", + "pkg:pypi/six@1.11.0" + ] + }, + { + "name": "pycairo-1.18.2-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/pycairo@1.18.2" + ] + }, + { + "name": "python-paste-2.0.3-10.oe1.src.rpm", + "purls": [ + "pkg:pypi/Paste@2.0.3" + ] + }, + { + "name": "libappstream-glib-0.7.14-3.oe1.src.rpm", + "purls": [ + "pkg:rpm/app@1-1.fc25?arch=i686&epoch=0&upstream=app-1-1.fc25.src.rpm", + "pkg:rpm/app@1-1.fc25?arch=x86_64&epoch=0&upstream=app-1-1.fc25.src.rpm", + "pkg:rpm/app-console@1-1.fc25?arch=noarch&epoch=0&upstream=app-1-1.fc25.src.rpm", + "pkg:rpm/app-extra@1-1.fc25?arch=noarch&epoch=0&upstream=app-1-1.fc25.src.rpm", + "pkg:rpm/composite@1-1.fc21?arch=x86_64&epoch=0&upstream=composite-1-1.fc21.src.rpm", + "pkg:rpm/driver@1-1.fc28?arch=noarch&epoch=0&upstream=driver-1-1.fc28.src.rpm", + "pkg:rpm/font@1-1.fc21?arch=noarch&epoch=0&upstream=font-1-1.fc21.src.rpm", + "pkg:rpm/font-serif@1-1.fc21?arch=noarch&epoch=0&upstream=font-1-1.fc21.src.rpm", + "pkg:rpm/test@0.1-1.fc21?arch=noarch&epoch=0&upstream=test-0.1-1.fc21.src.rpm" + ] + }, + { + "name": "fontforge-20170731-11.oe1.src.rpm", + "purls": [ + "pkg:npm/FontForgeBreakpadCrashAcceptor@0.0.1", + "pkg:rpm/libX11@1.3.6-30.5?arch=noarch&epoch=0&upstream=libX11-1.3.6-30.5.src.rpm" + ] + }, + { + "name": "texlive-base-20180414-28.oe1.src.rpm", + "purls": [ + "pkg:rpm/texlive-base@20180414-28.oe1?arch=aarch64&epoch=7" + ] + }, + { + "name": "python-ipaddress-1.0.18-9.oe1.src.rpm", + "purls": [ + "pkg:pypi/ipaddress@1.0.18" + ] + }, + { + "name": "mozjs60-60.2.2-4.oe1.src.rpm", + "purls": [ + "pkg:rpm/mozjs60@60.2.2-4.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "uthash-2.0.2-7.oe1.src.rpm", + "purls": [ + "pkg:npm/uthash@2.0.2" + ] + }, + { + "name": "docker-compose-1.22.0-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/:sys_platform", + "pkg:pypi/PySocks@1.6.7", + "pkg:pypi/PyYAML@3.12", + "pkg:pypi/backports.ssl-match-hostname@3.5.0.1", + "pkg:pypi/cached-property@1.3.0", + "pkg:pypi/certifi@2017.4.17", + "pkg:pypi/chardet@3.0.4", + "pkg:pypi/coverage@4.4.2", + "pkg:pypi/docker@3.4.1", + "pkg:pypi/docker-compose@1.22.0", + "pkg:pypi/docker-pycreds@0.3.0", + "pkg:pypi/dockerpty@0.4.1", + "pkg:pypi/docopt@0.6.2", + "pkg:pypi/enum34@1.1.6", + "pkg:pypi/flake8@3.5.0", + "pkg:pypi/functools32@3.2.3.post2", + "pkg:pypi/idna@2.5", + "pkg:pypi/ipaddress@1.0.18", + "pkg:pypi/jsonschema@2.6.0", + "pkg:pypi/pypiwin32@219", + "pkg:pypi/pypiwin32@220", + "pkg:pypi/pytest@2.9.2", + "pkg:pypi/pytest-cov@2.5.1", + "pkg:pypi/requests@2.18.4", + "pkg:pypi/six@1.10.0", + "pkg:pypi/texttable@0.9.1", + "pkg:pypi/urllib3@1.21.1", + "pkg:pypi/websocket-client@0.32.0" + ] + }, + { + "name": "linux-firmware-20190815-4.oe1.src.rpm", + "purls": [ + "pkg:rpm/linux-firmware@20190815-4.oe1?arch=noarch&epoch=0" + ] + }, + { + "name": "python-ruamel-yaml-clib-0.1.2-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/ruamel.yaml.clib@0.1.2" + ] + }, + { + "name": "rear-2.4-3.oe1.src.rpm", + "purls": [ + "pkg:rpm/rear@1.17.2-1.fc23?arch=x86_64&epoch=0&upstream=rear-1.17.2-1.fc23.src.rpm", + "pkg:rpm/rear@1.18-1.fc23?arch=x86_64&epoch=0&upstream=rear-1.18-1.fc23.src.rpm", + "pkg:rpm/rear@1.19-1.fc23?arch=x86_64&epoch=0&upstream=rear-1.19-1.fc23.src.rpm", + "pkg:rpm/rear@1.19-1.git201610111647.fc23?arch=x86_64&epoch=0&upstream=rear-1.19-1.git201610111647.fc23.src.rpm", + "pkg:rpm/rear@1.19-1.git201611300645.fc25?arch=x86_64&epoch=0&upstream=rear-1.19-1.git201611300645.fc25.src.rpm", + "pkg:rpm/rear@2.00-1.fc25?arch=x86_64&epoch=0&upstream=rear-2.00-1.fc25.src.rpm" + ] + }, + { + "name": "pyxattr-0.6.1-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/pyxattr@0.6.1" + ] + }, + { + "name": "docbook5-style-xsl-1.79.2-8.oe1.src.rpm", + "purls": [ + "pkg:maven/ant-contrib/ant-contrib@1.0b3", + "pkg:maven/org.antlr/antlr-runtime@3.1.3", + "pkg:maven/com.xmlcalabash.drivers.Main/calabash@1.0.2-93", + "pkg:maven/org.apache.commons.codec/commons-codec@1.3", + "pkg:maven/org.apache/commons-httpclient@3.1", + "pkg:maven/commons-logging/commons-logging@1.1.1", + "pkg:maven/org.jruby.extras/constantine@0.7", + "pkg:maven/isorelax/isorelax", + "pkg:maven/org.jruby.extras/jaffl@0.5.1", + "pkg:maven/org.jruby.extras/jffi@1.0.1", + "pkg:maven/com/thaiopensource/relaxng/util/Driver/jing", + "pkg:maven/jline/jline@0.9.95-SNAPSHOT", + "pkg:maven/org.jruby.extras/jnr-netdb@0.4", + "pkg:maven/org.jruby.ext.posix/jnr-posix@1.1.4", + "pkg:maven/org.python.util.jython/jython", + "pkg:maven/org.apache.lucene/lucene-analyzers@3.0.0", + "pkg:maven/org.apache.lucene/lucene-core@3.0.0", + "pkg:maven/com.icl.saxon.StyleSheet/saxon", + "pkg:maven/saxon65/saxon65", + "pkg:maven/saxon9-ant/saxon9-ant", + "pkg:maven/net.sf.saxon.Transform/saxon9he", + "pkg:maven/org.apache.xml.serializer/serializer@2.7.2", + "pkg:maven/org.ccil.cowan.tagsoup.CommandLine/tagsoup@1.2.1", + "pkg:maven/webhelpindexer/webhelpindexer", + "pkg:maven/org.apache.xalan/xalan@2.7.2", + "pkg:maven/xalan27/xalan27", + "pkg:maven/org.apache.xerces.impl.Version/xercesImpl@2.11.0", + "pkg:maven/org.w3c.dom.ls/xml-apis@1.4.01", + "pkg:maven/xmlresolver/xmlresolver@0.9.0", + "pkg:maven/org.apache.xalan.xsltc/xsltc@2.7.2" + ] + }, + { + "name": "brotli-1.0.5-3.oe1.src.rpm", + "purls": [ + "pkg:maven/org.brotli/dec@0.2.0-SNAPSHOT", + "pkg:maven/junit/junit@4.12" + ] + }, + { + "name": "qt5-doc-5.11.1-4.oe1.src.rpm", + "purls": [ + "pkg:rpm/qt5-doc@5.11.1-4.oe1?arch=noarch&epoch=0" + ] + }, + { + "name": "python-cryptography-2.6.1-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/cryptography@2.6.1", + "pkg:pypi/cryptography_vectors@{0" + ] + }, + { + "name": "python-beautifulsoup4-4.6.3-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/beautifulsoup4@4.6.3" + ] + }, + { + "name": "lxcfs-tools-0.3-16.oe1.src.rpm", + "purls": [ + "pkg:golang/github.com/BurntSushi/toml@v0.3.1", + "pkg:golang/github.com/containerd/console@v0.0.0-20181022165439-0650fd9eeb50", + "pkg:golang/github.com/coreos/go-systemd@v0.0.0-20190719114852-fd7a80b32e1f", + "pkg:golang/github.com/coreos/pkg@v0.0.0-20180928190104-399ea9e2e55f", + "pkg:golang/github.com/cyphar/filepath-securejoin@v0.2.2", + "pkg:golang/github.com/davecgh/go-spew@v1.1.1", + "pkg:golang/github.com/docker/docker@v0.0.0-00010101000000-000000000000", + "pkg:golang/github.com/docker/engine@v0.0.0-20181106193140-f5749085e9cb", + "pkg:golang/github.com/docker/go-units@v0.4.0", + "pkg:golang/github.com/go-yaml/yaml@v2.1.0 incompatible", + "pkg:golang/github.com/godbus/dbus@v4.1.0 incompatible", + "pkg:golang/github.com/golang/protobuf@v1.3.2", + "pkg:golang/github.com/golang/sys@v0.0.0-20190813064441-fde4db37ae7a", + "pkg:golang/github.com/konsorten/go-windows-terminal-sequences@v1.0.1", + "pkg:golang/github.com/mrunalp/fileutils@v0.0.0-20171103030105-7d4729fb3618", + "pkg:golang/github.com/opencontainers/runc@v1.0.0-rc6", + "pkg:golang/github.com/opencontainers/runtime-spec@v1.0.1", + "pkg:golang/github.com/opencontainers/selinux@v1.3.0", + "pkg:golang/github.com/pkg/errors@v0.8.1", + "pkg:golang/github.com/pmezard/go-difflib@v1.0.0", + "pkg:golang/github.com/seccomp/libseccomp-golang@v0.9.1", + "pkg:golang/github.com/sirupsen/logrus@v1.4.2", + "pkg:golang/github.com/stretchr/objx@v0.1.1", + "pkg:golang/github.com/stretchr/testify@v1.2.2", + "pkg:golang/github.com/syndtr/gocapability@v0.0.0-20180916011248-d98352740cb2", + "pkg:golang/github.com/urfave/cli@v1.21.0", + "pkg:golang/github.com/vishvananda/netlink@v1.0.0", + "pkg:golang/github.com/vishvananda/netns@v0.0.0-20190625233234-7109fa855b0f", + "pkg:golang/golang.org/x/sys@v0.0.0-20190422165155-953cdadca894", + "pkg:golang/gopkg.in/yaml.v2@v2.2.2" + ] + }, + { + "name": "protobuf-3.9.0-7.oe1.src.rpm", + "purls": [ + "pkg:maven/org.easymock/easymock", + "pkg:maven/org.easymock/easymock", + "pkg:maven/org.easymock/easymock", + "pkg:maven/org.easymock/easymockclassextension", + "pkg:maven/org.easymock/easymockclassextension", + "pkg:maven/org.easymock/easymockclassextension", + "pkg:maven/com.google.errorprone/error_prone_annotations@2.3.2", + "pkg:npm/google-protobuf@3.9.0", + "pkg:maven/com.google.code.gson/gson@2.7", + "pkg:maven/com.google.guava/guava", + "pkg:maven/com.google.guava/guava", + "pkg:maven/com.google.guava/guava", + "pkg:maven/com.google.guava/guava-testlib", + "pkg:maven/com.fasterxml.jackson.core/jackson-core@2.4.3", + "pkg:maven/org.jruby/jruby-complete@1.7.13", + "pkg:maven/junit/junit", + "pkg:maven/junit/junit", + "pkg:maven/junit/junit", + "pkg:maven/protobuf-java/protobuf-java", + "pkg:maven/com.google.protobuf/protobuf-java@3.0.0", + "pkg:maven/com.google.truth/truth" + ] + }, + { + "name": "pyOpenSSL-19.0.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/pyOpenSSL@19.0.0" + ] + }, + { + "name": "python-webob-1.8.2-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/WebOb@1.8.2" + ] + }, + { + "name": "containernetworking-plugins-0.8.2-3.git485be65.oe1.src.rpm", + "purls": [ + "pkg:golang/github.com/Microsoft/go-winio@v0.4.11", + "pkg:golang/github.com/Microsoft/hcsshim@v0.8.6", + "pkg:golang/github.com/alexflint/go-filemutex@v0.0.0-20171022225611-72bdc8eae2ae", + "pkg:golang/github.com/buger/jsonparser@v0.0.0-20180808090653-f4dd9f5a6b44", + "pkg:golang/github.com/containernetworking/cni@v0.7.0", + "pkg:golang/github.com/coreos/go-iptables@v0.4.2", + "pkg:golang/github.com/coreos/go-systemd@v0.0.0-20180511133405-39ca1b05acc7", + "pkg:golang/github.com/d2g/dhcp4@v0.0.0-20170904100407-a1d1b6c41b1c", + "pkg:golang/github.com/d2g/dhcp4client@v1.0.0", + "pkg:golang/github.com/d2g/dhcp4server@v0.0.0-20181031114812-7d4a0a7f59a5", + "pkg:golang/github.com/d2g/hardwareaddr@v0.0.0-20190221164911-e7d9fbe030e4", + "pkg:golang/github.com/godbus/dbus@v0.0.0-20180201030542-885f9cc04c9c", + "pkg:golang/github.com/golang/protobuf@v1.3.1", + "pkg:golang/github.com/j-keck/arping@v0.0.0-20160618110441-2cf9dc699c56", + "pkg:golang/github.com/juju/errors@v0.0.0-20180806074554-22422dad46e1", + "pkg:golang/github.com/juju/loggo@v0.0.0-20190526231331-6e530bcce5d8", + "pkg:golang/github.com/juju/testing@v0.0.0-20190613124551-e81189438503", + "pkg:golang/github.com/kr/pretty@v0.1.0", + "pkg:golang/github.com/mattn/go-shellwords@v1.0.3", + "pkg:golang/github.com/onsi/ginkgo@v0.0.0-20151202141238-7f8ab55aaf3b", + "pkg:golang/github.com/onsi/gomega@v0.0.0-20151007035656-2152b45fa28a", + "pkg:golang/github.com/safchain/ethtool@v0.0.0-20190326074333-42ed695e3de8", + "pkg:golang/github.com/sirupsen/logrus@v1.0.6", + "pkg:golang/github.com/stretchr/testify@v1.3.0", + "pkg:golang/github.com/vishvananda/netlink@v0.0.0-20181108222139-023a6dafdcdf", + "pkg:golang/github.com/vishvananda/netns@v0.0.0-20180720170159-13995c7128cc", + "pkg:golang/golang.org/x/crypto@v0.0.0-20181009213950-7c1a557ab941", + "pkg:golang/golang.org/x/net@v0.0.0-20181011144130-49bb7cea24b1", + "pkg:golang/golang.org/x/sys@v0.0.0-20190616124812-15dcb6c0061f", + "pkg:golang/gopkg.in/airbrake/gobrake.v2@v2.0.9", + "pkg:golang/gopkg.in/check.v1@v1.0.0-20180628173108-788fd7840127", + "pkg:golang/gopkg.in/gemnasium/logrus-airbrake-hook.v2@v2.1.2", + "pkg:golang/gopkg.in/mgo.v2@v2.0.0-20180705113604-9856a29383ce", + "pkg:golang/gopkg.in/yaml.v2@v2.2.2" + ] + }, + { + "name": "python-ldap-3.1.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/python-ldap@3.1.0" + ] + }, + { + "name": "mysql-8.0.17-3.oe1.src.rpm", + "purls": [ + "pkg:rpm/mysql@8.0.17-3.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "python-cffi-1.11.5-10.oe1.src.rpm", + "purls": [ + "pkg:pypi/cffi@1.11.5" + ] + }, + { + "name": "python-scikit-optimize-0.5.2-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/scikit-optimize@0.5.2" + ] + }, + { + "name": "python-ordered-set-2.0.2-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/ordered-set@2.0.2" + ] + }, + { + "name": "openvswitch-2.12.0-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/:sys_platform" + ] + }, + { + "name": "python-pretend-1.0.8-15.oe1.src.rpm", + "purls": [ + "pkg:pypi/pretend@1.0.8" + ] + }, + { + "name": "python-pygments-2.2.0-15.oe1.src.rpm", + "purls": [ + "pkg:pypi/Pygments@2.2.0" + ] + }, + { + "name": "python-contextlib2-0.5.5-9.oe1.src.rpm", + "purls": [ + "pkg:pypi/contextlib2@0.5.5" + ] + }, + { + "name": "python-paramiko-2.4.1-7.oe1.src.rpm", + "purls": [ + "pkg:pypi/flake8@2.6.2", + "pkg:pypi/pytest@3.2.1", + "pkg:pypi/pytest_relaxed@1.0.0", + "pkg:pypi/twine@1.9.1", + "pkg:pypi/wheel@0.24" + ] + }, + { + "name": "pygobject3-3.30.1-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/PyGObject@3.30.1" + ] + }, + { + "name": "python-websocket-client-0.47.0-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/unittest2@0.8.0", + "pkg:pypi/websocket-client@0.47.0" + ] + }, + { + "name": "python-parse-1.8.4-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/parse@1.8.4" + ] + }, + { + "name": "atune-0.2-0.1.oe1.src.rpm", + "purls": [ + "pkg:golang/cloud.google.com/go@v0.26.0", + "pkg:golang/github.com/BurntSushi/toml@v0.3.1", + "pkg:golang/github.com/antlr/antlr4@v0.0.0-20190726171924-e4737db19f4f", + "pkg:golang/github.com/bndr/gotabulate@v1.1.2", + "pkg:golang/github.com/caibirdme/yql@v0.0.0-20190801103415-238f3c90b514", + "pkg:golang/github.com/client9/misspell@v0.3.4", + "pkg:golang/github.com/cockroachdb/apd@v1.1.0", + "pkg:golang/github.com/coreos/go-systemd@v0.0.0-20190719114852-fd7a80b32e1f", + "pkg:golang/github.com/davecgh/go-spew@v1.1.1", + "pkg:golang/github.com/denisenkom/go-mssqldb@v0.0.0-20190707035753-2be1aa521ff4", + "pkg:golang/github.com/go-ini/ini@v1.42.0", + "pkg:golang/github.com/go-sql-driver/mysql@v1.4.1", + "pkg:golang/github.com/go-sql-driver/mysql@v1.4.1", + "pkg:golang/github.com/go-xorm/sqlfiddle@v0.0.0-20180821085327-62ce714f951a", + "pkg:golang/github.com/go-xorm/xorm@v0.7.4", + "pkg:golang/github.com/golang/glog@v0.0.0-20160126235308-23def4e6c14b", + "pkg:golang/github.com/golang/mock@v1.1.1", + "pkg:golang/github.com/golang/protobuf@v1.2.0", + "pkg:golang/github.com/golang/protobuf@v1.3.1", + "pkg:golang/github.com/google/go-cmp@v0.2.0", + "pkg:golang/github.com/jackc/fake@v0.0.0-20150926172116-812a484cc733", + "pkg:golang/github.com/jackc/pgx@v3.3.0 incompatible", + "pkg:golang/github.com/konsorten/go-windows-terminal-sequences@v1.0.1", + "pkg:golang/github.com/kr/pretty@v0.1.0", + "pkg:golang/github.com/lib/pq@v1.0.0", + "pkg:golang/github.com/mattn/go-sqlite3@v1.10.0", + "pkg:golang/github.com/mattn/go-sqlite3@v1.10.0", + "pkg:golang/github.com/mattn/go-sqlite3@v1.11.0", + "pkg:golang/github.com/mitchellh/mapstructure@v1.1.2", + "pkg:golang/github.com/pkg/errors@v0.8.1", + "pkg:golang/github.com/pmezard/go-difflib@v1.0.0", + "pkg:golang/github.com/satori/go.uuid@v1.2.0", + "pkg:golang/github.com/shopspring/decimal@v0.0.0-20180709203117-cd690d0c9e24", + "pkg:golang/github.com/sirupsen/logrus@v1.4.2", + "pkg:golang/github.com/smartystreets/goconvey@v0.0.0-20190731233626-505e41936337", + "pkg:golang/github.com/stretchr/objx@v0.1.1", + "pkg:golang/github.com/stretchr/testify@v1.2.2", + "pkg:golang/github.com/stretchr/testify@v1.3.0", + "pkg:golang/github.com/stretchr/testify@v1.3.0", + "pkg:golang/github.com/urfave/cli@v1.20.0", + "pkg:golang/github.com/ziutek/mymysql@v1.5.4", + "pkg:golang/golang.org/x/lint@v0.0.0-20190313153728-d0100b6bd8b3", + "pkg:golang/golang.org/x/net@v0.0.0-20190311183353-d8887717615a", + "pkg:golang/golang.org/x/net@v0.0.0-20190628185345-da137c7871d7", + "pkg:golang/golang.org/x/oauth2@v0.0.0-20180821212333-d2e6202438be", + "pkg:golang/golang.org/x/sys@v0.0.0-20190215142949-d0b11bdaac8a", + "pkg:golang/golang.org/x/sys@v0.0.0-20190422165155-953cdadca894", + "pkg:golang/golang.org/x/tools@v0.0.0-20190524140312-2c0ae7006135", + "pkg:golang/google.golang.org/appengine@v1.1.0", + "pkg:golang/google.golang.org/appengine@v1.4.0", + "pkg:golang/google.golang.org/genproto@v0.0.0-20180817151627-c66870c02cf8", + "pkg:golang/google.golang.org/grpc@v1.22.0", + "pkg:golang/gopkg.in/check.v1@v0.0.0-20161208181325-20d25e280405", + "pkg:golang/gopkg.in/ini.v1@v1.48.0", + "pkg:golang/gopkg.in/yaml.v2@v2.2.2", + "pkg:golang/honnef.co/go/tools@v0.0.0-20190523083050-ea95bdfd59fc", + "pkg:golang/xorm.io/builder@v0.3.5", + "pkg:golang/xorm.io/core@v0.6.3" + ] + }, + { + "name": "python-pytest-expect-1.1.0-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytest-expect@1.1.0" + ] + }, + { + "name": "python-genshi-0.7-23.oe1.src.rpm", + "purls": [ + "pkg:pypi/Genshi@0.7" + ] + }, + { + "name": "python-path-5.2-15.oe1.src.rpm", + "purls": [ + "pkg:pypi/path.py@5.2" + ] + }, + { + "name": "pyflakes-2.0.0-8.oe1.src.rpm", + "purls": [ + "pkg:pypi/pyflakes@2.0.0" + ] + }, + { + "name": "python-zope-interface-4.5.0-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/zope.interface@4.5.0" + ] + }, + { + "name": "python-productmd-1.22-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/productmd@1.22" + ] + }, + { + "name": "python-futures-3.1.1-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/futures@3.1.1" + ] + }, + { + "name": "python-backports_abc-0.5-9.oe1.src.rpm", + "purls": [ + "pkg:pypi/backports-abc@0.5" + ] + }, + { + "name": "fonttools-3.29.0-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/brotli@1.0.1", + "pkg:pypi/brotlipy@0.7.0", + "pkg:pypi/fonttools@3.29.0", + "pkg:pypi/munkres@1.0.10", + "pkg:pypi/unicodedata2@11.0.0", + "pkg:pypi/zopfli@0.1.4" + ] + }, + { + "name": "umoci-0.4.5-2.oe1.src.rpm", + "purls": [ + "pkg:golang/github.com/BurntSushi/toml@v0.3.1", + "pkg:golang/github.com/apex/log@v1.1.1", + "pkg:golang/github.com/aphistic/golf@v0.0.0-20180712155816-02c07f170c5a", + "pkg:golang/github.com/aphistic/sweet@v0.2.0", + "pkg:golang/github.com/aphistic/sweet@v0.3.0", + "pkg:golang/github.com/aws/aws-sdk-go@v1.20.6", + "pkg:golang/github.com/aws/aws-sdk-go@v1.23.21", + "pkg:golang/github.com/aybabtme/rgbterm@v0.0.0-20170906152045-cc83f3b3ce59", + "pkg:golang/github.com/cpuguy83/go-md2man/v2@v2.0.0-20190314233015-f79a8a8ca69d", + "pkg:golang/github.com/cyphar/filepath-securejoin@v0.2.2", + "pkg:golang/github.com/davecgh/go-spew@v1.1.1", + "pkg:golang/github.com/docker/go-units@v0.4.0", + "pkg:golang/github.com/fatih/color@v1.7.0", + "pkg:golang/github.com/go-logfmt/logfmt@v0.4.0", + "pkg:golang/github.com/golang/protobuf@v1.3.2", + "pkg:golang/github.com/google/uuid@v1.1.1", + "pkg:golang/github.com/jpillora/backoff@v0.0.0-20180909062703-3050d21c67d7", + "pkg:golang/github.com/klauspost/compress@v1.8.3", + "pkg:golang/github.com/klauspost/cpuid@v1.2.1", + "pkg:golang/github.com/klauspost/pgzip@v1.2.1", + "pkg:golang/github.com/konsorten/go-windows-terminal-sequences@v1.0.1", + "pkg:golang/github.com/konsorten/go-windows-terminal-sequences@v1.0.2", + "pkg:golang/github.com/kr/pretty@v0.1.0", + "pkg:golang/github.com/kr/pty@v1.1.8", + "pkg:golang/github.com/mattn/go-colorable@v0.1.2", + "pkg:golang/github.com/mattn/go-isatty@v0.0.8", + "pkg:golang/github.com/mattn/go-isatty@v0.0.9", + "pkg:golang/github.com/mohae/deepcopy@v0.0.0-20170929034955-c48cc78d4826", + "pkg:golang/github.com/onsi/ginkgo@v1.10.1", + "pkg:golang/github.com/onsi/gomega@v1.7.0", + "pkg:golang/github.com/opencontainers/go-digest@v1.0.0-rc1", + "pkg:golang/github.com/opencontainers/image-spec@v1.0.1", + "pkg:golang/github.com/opencontainers/runtime-spec@v1.0.1", + "pkg:golang/github.com/pkg/errors@v0.8.1", + "pkg:golang/github.com/pkg/errors@v0.8.1", + "pkg:golang/github.com/pmezard/go-difflib@v1.0.0", + "pkg:golang/github.com/rogpeppe/fastuuid@v1.1.0", + "pkg:golang/github.com/rogpeppe/fastuuid@v1.2.0", + "pkg:golang/github.com/rootless-containers/proto@v0.1.0", + "pkg:golang/github.com/sirupsen/logrus@v1.4.2", + "pkg:golang/github.com/smartystreets/go-aws-auth@v0.0.0-20180515143844-0c1422d1fdb9", + "pkg:golang/github.com/smartystreets/gunit@v1.0.0", + "pkg:golang/github.com/smartystreets/gunit@v1.0.4", + "pkg:golang/github.com/stretchr/objx@v0.1.1", + "pkg:golang/github.com/stretchr/objx@v0.2.0", + "pkg:golang/github.com/stretchr/testify@v1.2.2", + "pkg:golang/github.com/stretchr/testify@v1.3.0", + "pkg:golang/github.com/stretchr/testify@v1.4.0", + "pkg:golang/github.com/tj/assert@v0.0.0-20171129193455-018094318fb0", + "pkg:golang/github.com/tj/go-elastic@v0.0.0-20171221160941-36157cbbebc2", + "pkg:golang/github.com/tj/go-kinesis@v0.0.0-20171128231115-08b17f58cb1b", + "pkg:golang/github.com/tj/go-spin@v1.1.0", + "pkg:golang/github.com/urfave/cli@v1.22.1", + "pkg:golang/github.com/vbatts/go-mtree@v0.4.4", + "pkg:golang/golang.org/x/crypto@v0.0.0-20190911031432-227b76d455e7", + "pkg:golang/golang.org/x/net@v0.0.0-20190620200207-3b0461eec859", + "pkg:golang/golang.org/x/net@v0.0.0-20190912160710-24e19bdeb0f2", + "pkg:golang/golang.org/x/sync@v0.0.0-20190911185100-cd5d95a43a6e", + "pkg:golang/golang.org/x/sys@v0.0.0-20190422165155-953cdadca894", + "pkg:golang/golang.org/x/sys@v0.0.0-20190813064441-fde4db37ae7a", + "pkg:golang/golang.org/x/sys@v0.0.0-20190913121621-c3b328c6e5a7", + "pkg:golang/golang.org/x/text@v0.3.2", + "pkg:golang/golang.org/x/tools@v0.0.0-20190913181337-0240832f5c3d", + "pkg:golang/gopkg.in/check.v1@v1.0.0-20190902080502-41f04d3bba15", + "pkg:golang/gopkg.in/yaml.v2@v2.2.2" + ] + }, + { + "name": "python-nose-1.3.7-26.oe1.src.rpm", + "purls": [ + "pkg:pypi/Some-plugin@0.0.0", + "pkg:pypi/UNKNOWN@0.0.0", + "pkg:pypi/nose@1.3.7" + ] + }, + { + "name": "python-joblib-0.14.0-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/sphinx@1.6.3" + ] + }, + { + "name": "qt5-qtwebchannel-5.11.1-4.oe1.src.rpm", + "purls": [ + "pkg:npm/Chatclient@0.0.1", + "pkg:npm/qwclient@0.0.1" + ] + }, + { + "name": "texlive-2018-22.oe1.src.rpm", + "purls": [ + "pkg:rpm/texlive@2018-22.oe1?arch=noarch&epoch=8" + ] + }, + { + "name": "libvoikko-4.1.1-3.oe1.src.rpm", + "purls": [ + "pkg:maven/net.java.dev.jna/jna@4.2.2", + "pkg:maven/junit/junit@4.12" + ] + }, + { + "name": "python-testscenarios-0.5.0-14.oe1.src.rpm", + "purls": [ + "pkg:pypi/testscenarios@0.5.0" + ] + }, + { + "name": "python-sphinx-theme-alabaster-0.7.11-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/alabaster@0.7.11" + ] + }, + { + "name": "python-keyring-13.2.1-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/:sys_platform@linux", + "pkg:pypi/:sys_platform@win32", + "pkg:pypi/keyring@13.2.1" + ] + }, + { + "name": "python-pyudev-0.21.0-10.oe1.src.rpm", + "purls": [ + "pkg:pypi/pyudev@0.21.0" + ] + }, + { + "name": "python-incremental-17.5.0-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/incremental@17.5.0" + ] + }, + { + "name": "nototools-0-1.20190712.git9c4375f.oe1.src.rpm", + "purls": [ + "pkg:pypi/Pillow@4.0.0", + "pkg:pypi/booleanOperations@0.7.0", + "pkg:pypi/defcon@0.3.1", + "pkg:pypi/pyclipper@1.0.6", + "pkg:pypi/scour@0.37", + "pkg:pypi/ufoLib@2.0.0" + ] + }, + { + "name": "python-urllib3-1.24.3-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/PySocks@1.6.8", + "pkg:pypi/mock@2.0.0", + "pkg:pypi/pkginfo@1.4.2", + "pkg:pypi/pluggy@0.8.0", + "pkg:pypi/pytest@3.8.2", + "pkg:pypi/pytest-httpbin@0.3.0", + "pkg:pypi/pytest-timeout@1.3.1", + "pkg:pypi/tornado@5.1.1", + "pkg:pypi/tox@2.9.1", + "pkg:pypi/wheel@0.30.0" + ] + }, + { + "name": "mozjs52-52.9.0-5.oe1.src.rpm", + "purls": [ + "pkg:rpm/mozjs52@52.9.0-5.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "qt5-qtwebengine-5.11.1-7.oe1.src.rpm", + "purls": [ + "pkg:rpm/qt5-qtwebengine@5.11.1-7.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "python-polib-1.1.0-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/polib@1.1.0" + ] + }, + { + "name": "python-asn1crypto-0.24.0-8.oe1.src.rpm", + "purls": [ + "pkg:pypi/asn1crypto@0.24.0" + ] + }, + { + "name": "pytest-3.6.4-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/:sys_platform@win32", + "pkg:pypi/pytest@3.6.4", + "pkg:pypi/sphinx@1.4.*" + ] + }, + { + "name": "python-pandas-0.25.3-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/pandas@0.25.3" + ] + }, + { + "name": "python-backports-unittest_mock-1.2.1-7.oe1.src.rpm", + "purls": [ + "pkg:pypi/:python_version@2.7", + "pkg:pypi/backports.unittest-mock@1.2.1", + "pkg:pypi/python_version@2.6", + "pkg:pypi/python_version@3.2" + ] + }, + { + "name": "python-repoze-lru-0.7-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/repoze.lru@0.7" + ] + }, + { + "name": "python-itsdangerous-1.1.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/itsdangerous@1.1.0" + ] + }, + { + "name": "python-configparser-3.5.0b2-11.oe1.src.rpm", + "purls": [ + "pkg:pypi/configparser@3.5.0b2" + ] + }, + { + "name": "python-blinker-1.4-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/blinker@1.4" + ] + }, + { + "name": "python-docker-4.0.2-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/:sys_platform", + "pkg:pypi/appdirs@1.4.3", + "pkg:pypi/asn1crypto@0.22.0", + "pkg:pypi/backports.ssl-match-hostname@3.5.0.1", + "pkg:pypi/cffi@1.10.0", + "pkg:pypi/coverage@4.5.2", + "pkg:pypi/cryptography@2.3", + "pkg:pypi/docker@4.0.2", + "pkg:pypi/enum34@1.1.6", + "pkg:pypi/flake8@3.6.0", + "pkg:pypi/idna@2.5", + "pkg:pypi/ipaddress@1.0.18", + "pkg:pypi/mock@1.0.1", + "pkg:pypi/packaging@16.8", + "pkg:pypi/paramiko@2.4.2", + "pkg:pypi/pyOpenSSL@18.0.0", + "pkg:pypi/pycparser@2.17", + "pkg:pypi/pyparsing@2.2.0", + "pkg:pypi/pypiwin32@219", + "pkg:pypi/pypiwin32@219", + "pkg:pypi/pypiwin32@223", + "pkg:pypi/pypiwin32@223", + "pkg:pypi/pytest@4.1.0", + "pkg:pypi/pytest-cov@2.6.1", + "pkg:pypi/pytest-timeout@1.3.3", + "pkg:pypi/requests@2.20.0", + "pkg:pypi/six@1.10.0", + "pkg:pypi/urllib3@1.24.3", + "pkg:pypi/websocket-client@0.56.0" + ] + }, + { + "name": "python-sphinxcontrib-spelling-4.2.0-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/sphinxcontrib-spelling@4.2.0" + ] + }, + { + "name": "python-tempita-0.5.1-21.oe1.src.rpm", + "purls": [ + "pkg:pypi/Tempita@0.5.1" + ] + }, + { + "name": "pytz-2019.2-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytz@2019.2" + ] + }, + { + "name": "clang-7.0.0-5.oe1.src.rpm", + "purls": [ + "pkg:npm/vscode-clangd@0.0.6" + ] + }, + { + "name": "python-flask-1.0.4-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/Flask@1.0.4" + ] + }, + { + "name": "openvswitch-kmod-2.12.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/:sys_platform" + ] + }, + { + "name": "createrepo_c-0.15.0-4.oe1.src.rpm", + "purls": [ + "pkg:rpm/Archer@3.4.5-6?arch=x86_64&epoch=2&upstream=Archer-3.4.5-6.src.rpm", + "pkg:rpm/Archer@3.4.5-6?arch=x86_64&epoch=2&upstream=Archer-3.4.5-6.src.rpm", + "pkg:rpm/Rimmer@1.0.2-2?arch=x86_64&epoch=0&upstream=Rimmer-1.0.2-2.src.rpm", + "pkg:rpm/balicek-iso88591@1.1.1-1?arch=x86_64&epoch=0&upstream=balicek-iso88591-1.1.1-1.src.rpm", + "pkg:rpm/balicek-iso88592@1.1.1-1?arch=x86_64&epoch=0&upstream=balicek-iso88592-1.1.1-1.src.rpm", + "pkg:rpm/balicek-utf8@1.1.1-1?arch=x86_64&epoch=0&upstream=balicek-utf8-1.1.1-1.src.rpm", + "pkg:rpm/empty@0-0?arch=x86_64&epoch=0", + "pkg:rpm/empty@0-0?arch=x86_64&epoch=0&upstream=empty-0-0.src.rpm", + "pkg:rpm/fake_bash@1.1.1-1?arch=x86_64&epoch=0&upstream=fake_bash-1.1.1-1.src.rpm", + "pkg:rpm/fake_bash@1.1.1-1?arch=x86_64&epoch=0&upstream=fake_bash-1.1.1-1.src.rpm", + "pkg:rpm/super_kernel@6.0.1-2?arch=x86_64&epoch=0&upstream=super_kernel-6.0.1-2.src.rpm", + "pkg:rpm/super_kernel@6.0.1-2?arch=x86_64&epoch=0&upstream=super_kernel-6.0.1-2.src.rpm" + ] + }, + { + "name": "python-cached_property-1.5.1-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/coverage@4.4.2", + "pkg:pypi/freezegun@0.3.10", + "pkg:pypi/pytest@3.7.4", + "pkg:pypi/pytest-cov@2.6.0", + "pkg:pypi/twine@1.11.0", + "pkg:pypi/wheel@0.31.1" + ] + }, + { + "name": "python-markupsafe-1.0-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/MarkupSafe@1.0" + ] + }, + { + "name": "pyparsing-2.2.0-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/pyparsing@2.2.0" + ] + }, + { + "name": "python-funcsigs-1.0.2-13.oe1.src.rpm", + "purls": [ + "pkg:pypi/funcsigs@1.0.2" + ] + }, + { + "name": "docbook-style-xsl-1.79.2-9.oe1.src.rpm", + "purls": [ + "pkg:maven/ant-contrib/ant-contrib@1.0b3", + "pkg:maven/org.antlr/antlr-runtime@3.1.3", + "pkg:maven/com.xmlcalabash.drivers.Main/calabash@1.0.2-93", + "pkg:maven/org.apache.commons.codec/commons-codec@1.3", + "pkg:maven/org.apache/commons-httpclient@3.1", + "pkg:maven/commons-logging/commons-logging@1.1.1", + "pkg:maven/org.jruby.extras/constantine@0.7", + "pkg:maven/isorelax/isorelax", + "pkg:maven/org.jruby.extras/jaffl@0.5.1", + "pkg:maven/org.jruby.extras/jffi@1.0.1", + "pkg:maven/com/thaiopensource/relaxng/util/Driver/jing", + "pkg:maven/jline/jline@0.9.95-SNAPSHOT", + "pkg:maven/org.jruby.extras/jnr-netdb@0.4", + "pkg:maven/org.jruby.ext.posix/jnr-posix@1.1.4", + "pkg:maven/org.python.util.jython/jython", + "pkg:maven/org.apache.lucene/lucene-analyzers@3.0.0", + "pkg:maven/org.apache.lucene/lucene-core@3.0.0", + "pkg:maven/com.icl.saxon.StyleSheet/saxon", + "pkg:maven/saxon65/saxon65", + "pkg:maven/saxon9-ant/saxon9-ant", + "pkg:maven/net.sf.saxon.Transform/saxon9he", + "pkg:maven/org.apache.xml.serializer/serializer@2.7.2", + "pkg:maven/org.ccil.cowan.tagsoup.CommandLine/tagsoup@1.2.1", + "pkg:maven/webhelpindexer/webhelpindexer", + "pkg:maven/org.apache.xalan/xalan@2.7.2", + "pkg:maven/xalan27/xalan27", + "pkg:maven/org.w3c.dom.ls/xercesImpl@1.4.01", + "pkg:maven/org.xml.sax/xml-apis@1.4.01", + "pkg:maven/xmlresolver/xmlresolver@0.9.0", + "pkg:maven/org.apache.bcel/xsltc@2.7.2" + ] + }, + { + "name": "python-lit-0.7.0-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/lit@0.7.0" + ] + }, + { + "name": "python-bcrypt-3.1.4-7.oe1.src.rpm", + "purls": [ + "pkg:pypi/bcrypt@3.1.4" + ] + }, + { + "name": "python-netaddr-0.7.19-14.oe1.src.rpm", + "purls": [ + "pkg:pypi/netaddr@0.7.19" + ] + }, + { + "name": "freerdp-2.0.0-44.rc3.h4.oe1.src.rpm", + "purls": [ + "pkg:maven/gradle-wrapper/gradle-wrapper@2.8" + ] + }, + { + "name": "python-jsonpatch-1.21-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/jsonpatch@1.21" + ] + }, + { + "name": "python-jsonschema-2.6.0-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/:python_version@2.7", + "pkg:pypi/jsonschema@2.6.0" + ] + }, + { + "name": "python-mysqlclient-1.3.12-7.oe1.src.rpm", + "purls": [ + "pkg:pypi/mysqlclient@1.3.12" + ] + }, + { + "name": "python-linecache2-1.0.0-18.oe1.src.rpm", + "purls": [ + "pkg:pypi/linecache2@1.0.0" + ] + }, + { + "name": "grpc-1.22.0-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/certifi@2017.4.17", + "pkg:pypi/chardet@3.0.4", + "pkg:pypi/googleapis-common-protos@1.5.5", + "pkg:maven/gradle-wrapper/gradle-wrapper@2.10", + "pkg:maven/gradle-wrapper/gradle-wrapper@2.10", + "pkg:npm/grpc-examples@0.1.0", + "pkg:npm/grpc-examples@0.1.0", + "pkg:pypi/idna@2.7", + "pkg:pypi/oauth2client@4.1.0" + ] + }, + { + "name": "python-dns-1.15.0-10.oe1.src.rpm", + "purls": [ + "pkg:pypi/dnspython@1.15.0" + ] + }, + { + "name": "python-pytest-fixture-config-1.2.11-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytest-fixture-config@1.2.11" + ] + }, + { + "name": "nodejs-10.11.0-1.oe1.src.rpm", + "purls": [ + "pkg:npm/0-dns@1.0.0", + "pkg:npm/@types/node@10.3.5", + "pkg:npm/JSONStream@1.3.4", + "pkg:npm/abbrev@1.1.1", + "pkg:npm/acorn@5.5.3", + "pkg:npm/acorn@5.7.2", + "pkg:npm/agent-base@4.2.0", + "pkg:npm/agentkeepalive@3.4.1", + "pkg:npm/ajv@5.5.2", + "pkg:npm/ansi-align@2.0.0", + "pkg:npm/ansi-regex@2.1.1", + "pkg:npm/ansi-regex@3.0.0", + "pkg:npm/ansi-regex@3.0.0", + "pkg:npm/ansi-regex@3.0.0", + "pkg:npm/ansi-styles@3.2.1", + "pkg:npm/ansi-styles@3.2.1", + "pkg:npm/ansicolors@0.3.2", + "pkg:npm/ansistyles@0.1.3", + "pkg:npm/anymatch@2.0.0", + "pkg:npm/aproba@1.2.0", + "pkg:npm/archy@1.0.0", + "pkg:npm/are-we-there-yet@1.1.4", + "pkg:npm/argparse@1.0.10", + "pkg:npm/argparse@1.0.10", + "pkg:npm/arr-diff@2.0.0", + "pkg:npm/arr-flatten@1.1.0", + "pkg:npm/arr-union@3.1.0", + "pkg:npm/array-unique@0.2.1", + "pkg:npm/asap@2.0.6", + "pkg:npm/asn1@0.2.4", + "pkg:npm/assert-plus@1.0.0", + "pkg:npm/assign-symbols@1.0.0", + "pkg:npm/async@1.5.2", + "pkg:npm/async-each@1.0.1", + "pkg:npm/asynckit@0.4.0", + "pkg:npm/atob@2.1.2", + "pkg:npm/aws-sign2@0.7.0", + "pkg:npm/aws4@1.8.0", + "pkg:npm/bail@1.0.3", + "pkg:npm/bail@1.0.3", + "pkg:npm/balanced-match@1.0.0", + "pkg:npm/balanced-match@1.0.0", + "pkg:npm/balanced-match@1.0.0", + "pkg:npm/base@0.11.2", + "pkg:npm/bcrypt-pbkdf@1.0.2", + "pkg:npm/bin-links@1.1.2", + "pkg:npm/binary-extensions@1.11.0", + "pkg:npm/block-stream@0.0.9", + "pkg:npm/bluebird@3.5.1", + "pkg:npm/boolbase@1.0.0", + "pkg:npm/boxen@1.3.0", + "pkg:npm/brace-expansion@1.1.11", + "pkg:npm/brace-expansion@1.1.11", + "pkg:npm/brace-expansion@1.1.11", + "pkg:npm/braces@1.8.5", + "pkg:npm/buffer-from@1.0.0", + "pkg:npm/buffer-from@1.1.1", + "pkg:npm/builtin-modules@1.1.1", + "pkg:npm/builtin-modules@2.0.0", + "pkg:npm/builtins@1.0.3", + "pkg:npm/byline@5.0.0", + "pkg:npm/byte-size@4.0.3", + "pkg:npm/cacache@10.0.4", + "pkg:npm/cacache@11.2.0", + "pkg:npm/cache-base@1.0.1", + "pkg:npm/call-limit@1.1.0", + "pkg:npm/camelcase@3.0.0", + "pkg:npm/camelcase@4.1.0", + "pkg:npm/camelcase@5.0.0", + "pkg:npm/capture-stack-trace@1.0.0", + "pkg:npm/caseless@0.12.0", + "pkg:npm/ccount@1.0.3", + "pkg:npm/ccount@1.0.3", + "pkg:npm/chalk@2.4.1", + "pkg:npm/chalk@2.4.1", + "pkg:npm/character-entities@1.2.2", + "pkg:npm/character-entities@1.2.2", + "pkg:npm/character-entities-html4@1.1.2", + "pkg:npm/character-entities-html4@1.1.2", + "pkg:npm/character-entities-legacy@1.1.2", + "pkg:npm/character-entities-legacy@1.1.2", + "pkg:npm/character-reference-invalid@1.1.2", + "pkg:npm/character-reference-invalid@1.1.2", + "pkg:npm/chokidar@2.0.4", + "pkg:npm/chownr@1.0.1", + "pkg:npm/ci-info@1.4.0", + "pkg:npm/cidr-regex@2.0.9", + "pkg:npm/clang-format@1.2.3", + "pkg:npm/class-utils@0.3.6", + "pkg:npm/cli-boxes@1.0.0", + "pkg:npm/cli-columns@3.1.2", + "pkg:npm/cli-table3@0.5.0", + "pkg:npm/cliui@4.1.0", + "pkg:npm/clone@1.0.4", + "pkg:npm/cmd-shim@2.0.2", + "pkg:npm/co@3.1.0", + "pkg:npm/co@4.6.0", + "pkg:npm/code-point-at@1.1.0", + "pkg:npm/code-point-at@1.1.0", + "pkg:npm/collapse-white-space@1.0.4", + "pkg:npm/collapse-white-space@1.0.4", + "pkg:npm/collection-visit@1.0.0", + "pkg:npm/color-convert@1.9.1", + "pkg:npm/color-convert@1.9.3", + "pkg:npm/color-name@1.1.3", + "pkg:npm/color-name@1.1.3", + "pkg:npm/colors@1.1.2", + "pkg:npm/columnify@1.5.4", + "pkg:npm/combined-stream@1.0.6", + "pkg:npm/comma-separated-tokens@1.0.5", + "pkg:npm/component-emitter@1.2.1", + "pkg:npm/concat-map@0.0.1", + "pkg:npm/concat-map@0.0.1", + "pkg:npm/concat-map@0.0.1", + "pkg:npm/concat-stream@1.6.2", + "pkg:npm/concat-stream@1.6.2", + "pkg:npm/config-chain@1.1.11", + "pkg:npm/configstore@3.1.2", + "pkg:npm/console-control-strings@1.1.0", + "pkg:npm/copy-concurrently@1.0.5", + "pkg:npm/copy-descriptor@0.1.1", + "pkg:npm/core-util-is@1.0.2", + "pkg:npm/core-util-is@1.0.2", + "pkg:npm/create-error-class@3.0.2", + "pkg:npm/cross-spawn@5.1.0", + "pkg:npm/crypto-random-string@1.0.0", + "pkg:npm/css-selector-parser@1.3.0", + "pkg:npm/cyclist@0.2.2", + "pkg:npm/dashdash@1.14.1", + "pkg:npm/debug@2.6.9", + "pkg:npm/debug@2.6.9", + "pkg:npm/debug@3.1.0", + "pkg:npm/debuglog@1.0.1", + "pkg:npm/decamelize@1.2.0", + "pkg:npm/decode-uri-component@0.2.0", + "pkg:npm/decode-uri-component@0.2.0", + "pkg:npm/deep-extend@0.5.1", + "pkg:npm/deep-extend@0.6.0", + "pkg:npm/defaults@1.0.3", + "pkg:npm/define-properties@1.1.2", + "pkg:npm/define-property@2.0.2", + "pkg:npm/delayed-stream@1.0.0", + "pkg:npm/delegates@1.0.0", + "pkg:npm/detab@2.0.1", + "pkg:npm/detect-indent@5.0.0", + "pkg:npm/detect-newline@2.1.0", + "pkg:npm/dezalgo@1.0.3", + "pkg:npm/dot-prop@4.2.0", + "pkg:npm/dotenv@5.0.1", + "pkg:npm/duplexer3@0.1.4", + "pkg:npm/duplexify@3.6.0", + "pkg:npm/ecc-jsbn@0.1.2", + "pkg:npm/editor@1.0.0", + "pkg:npm/encoding@0.1.12", + "pkg:npm/end-of-stream@1.4.1", + "pkg:npm/err-code@1.1.2", + "pkg:npm/errno@0.1.7", + "pkg:npm/error-ex@1.3.2", + "pkg:npm/es6-promise@4.2.4", + "pkg:npm/es6-promisify@5.0.0", + "pkg:npm/escape-string-regexp@1.0.5", + "pkg:npm/escape-string-regexp@1.0.5", + "pkg:npm/esprima@4.0.0", + "pkg:npm/esprima@4.0.1", + "pkg:npm/estree-walker@0.5.1", + "pkg:npm/example@0.0.0", + "pkg:npm/example@0.0.0", + "pkg:npm/execa@0.7.0", + "pkg:npm/expand-brackets@0.1.5", + "pkg:npm/expand-range@1.8.2", + "pkg:npm/extend@3.0.1", + "pkg:npm/extend@3.0.2", + "pkg:npm/extend@3.0.2", + "pkg:npm/extend-shallow@3.0.2", + "pkg:npm/extglob@0.3.2", + "pkg:npm/extraneous-detected@0.0.0", + "pkg:npm/extraneous-dev-dep@0.0.0", + "pkg:npm/extsprintf@1.3.0", + "pkg:npm/fast-deep-equal@1.1.0", + "pkg:npm/fast-json-stable-stringify@2.0.0", + "pkg:npm/fault@1.0.2", + "pkg:npm/figgy-pudding@2.0.1", + "pkg:npm/figgy-pudding@3.4.1", + "pkg:npm/filename-regex@2.0.1", + "pkg:npm/fill-range@2.2.3", + "pkg:npm/find-npm-prefix@1.0.2", + "pkg:npm/find-up@2.1.0", + "pkg:npm/flush-write-stream@1.0.3", + "pkg:npm/fn-name@2.0.1", + "pkg:npm/for-in@1.0.2", + "pkg:npm/for-own@0.1.5", + "pkg:npm/foreach@2.0.5", + "pkg:npm/forever-agent@0.6.1", + "pkg:npm/form-data@2.3.2", + "pkg:npm/format@0.2.2", + "pkg:npm/fragment-cache@0.2.1", + "pkg:npm/from2@1.3.0", + "pkg:npm/from2@2.3.0", + "pkg:npm/fs-minipass@1.2.5", + "pkg:npm/fs-vacuum@1.2.10", + "pkg:npm/fs-write-stream-atomic@1.0.10", + "pkg:npm/fs.realpath@1.0.0", + "pkg:npm/fs.realpath@1.0.0", + "pkg:npm/fs.realpath@1.0.0", + "pkg:npm/fsevents@1.2.4", + "pkg:npm/fstream@1.0.11", + "pkg:npm/function-bind@1.1.1", + "pkg:npm/gauge@2.7.4", + "pkg:npm/genfun@4.0.1", + "pkg:npm/gentle-fs@2.0.1", + "pkg:npm/get-caller-file@1.0.2", + "pkg:npm/get-stream@3.0.0", + "pkg:npm/get-value@2.0.6", + "pkg:npm/getpass@0.1.7", + "pkg:npm/glob@7.1.2", + "pkg:npm/glob@7.1.2", + "pkg:npm/glob@7.1.3", + "pkg:npm/glob-base@0.3.0", + "pkg:npm/glob-parent@2.0.0", + "pkg:npm/global-dirs@0.1.1", + "pkg:npm/got@6.7.1", + "pkg:npm/graceful-fs@4.1.11", + "pkg:npm/graceful-fs@4.1.11", + "pkg:npm/har-schema@2.0.0", + "pkg:npm/har-validator@5.1.0", + "pkg:npm/has@1.0.3", + "pkg:npm/has-flag@3.0.0", + "pkg:npm/has-flag@3.0.0", + "pkg:npm/has-unicode@2.0.1", + "pkg:npm/has-value@1.0.0", + "pkg:npm/has-values@1.0.0", + "pkg:npm/hast-to-hyperscript@3.1.0", + "pkg:npm/hast-util-from-parse5@2.1.0", + "pkg:npm/hast-util-is-element@1.0.1", + "pkg:npm/hast-util-parse-selector@2.1.1", + "pkg:npm/hast-util-raw@2.0.2", + "pkg:npm/hast-util-sanitize@1.2.0", + "pkg:npm/hast-util-to-html@3.1.0", + "pkg:npm/hast-util-to-parse5@2.2.0", + "pkg:npm/hast-util-whitespace@1.0.1", + "pkg:npm/hastscript@3.1.0", + "pkg:npm/hosted-git-info@2.7.1", + "pkg:npm/html-void-elements@1.0.3", + "pkg:npm/http-cache-semantics@3.8.1", + "pkg:npm/http-proxy-agent@2.1.0", + "pkg:npm/http-signature@1.2.0", + "pkg:npm/https-proxy-agent@2.2.1", + "pkg:npm/humanize-ms@1.2.1", + "pkg:npm/iconv-lite@0.4.23", + "pkg:npm/iferr@0.1.5", + "pkg:npm/iferr@0.1.5", + "pkg:npm/iferr@0.1.5", + "pkg:npm/iferr@1.0.2", + "pkg:npm/ignore@3.3.10", + "pkg:npm/ignore-walk@3.0.1", + "pkg:npm/import-lazy@2.1.0", + "pkg:npm/imurmurhash@0.1.4", + "pkg:npm/inflight@1.0.6", + "pkg:npm/inflight@1.0.6", + "pkg:npm/inflight@1.0.6", + "pkg:npm/inherits@2.0.3", + "pkg:npm/inherits@2.0.3", + "pkg:npm/inherits@2.0.3", + "pkg:npm/inherits@2.0.3", + "pkg:npm/ini@1.3.5", + "pkg:npm/ini@1.3.5", + "pkg:npm/init-package-json@1.10.3", + "pkg:npm/invert-kv@1.0.0", + "pkg:npm/ip@1.1.5", + "pkg:npm/ip-regex@2.1.0", + "pkg:npm/irregular-plurals@2.0.0", + "pkg:npm/is-accessor-descriptor@0.1.6", + "pkg:npm/is-alphabetical@1.0.2", + "pkg:npm/is-alphabetical@1.0.2", + "pkg:npm/is-alphanumeric@1.0.0", + "pkg:npm/is-alphanumerical@1.0.2", + "pkg:npm/is-alphanumerical@1.0.2", + "pkg:npm/is-arrayish@0.2.1", + "pkg:npm/is-binary-path@1.0.1", + "pkg:npm/is-buffer@1.1.6", + "pkg:npm/is-buffer@2.0.3", + "pkg:npm/is-builtin-module@1.0.0", + "pkg:npm/is-ci@1.1.0", + "pkg:npm/is-cidr@2.0.6", + "pkg:npm/is-data-descriptor@0.1.4", + "pkg:npm/is-decimal@1.0.2", + "pkg:npm/is-decimal@1.0.2", + "pkg:npm/is-descriptor@0.1.6", + "pkg:npm/is-dotfile@1.0.3", + "pkg:npm/is-empty@1.2.0", + "pkg:npm/is-equal-shallow@0.1.3", + "pkg:npm/is-extendable@0.1.1", + "pkg:npm/is-extglob@1.0.0", + "pkg:npm/is-fullwidth-code-point@1.0.0", + "pkg:npm/is-fullwidth-code-point@2.0.0", + "pkg:npm/is-fullwidth-code-point@2.0.0", + "pkg:npm/is-glob@2.0.1", + "pkg:npm/is-hexadecimal@1.0.2", + "pkg:npm/is-hexadecimal@1.0.2", + "pkg:npm/is-hidden@1.1.1", + "pkg:npm/is-installed-globally@0.1.0", + "pkg:npm/is-module@1.0.0", + "pkg:npm/is-nan@1.2.1", + "pkg:npm/is-npm@1.0.0", + "pkg:npm/is-number@2.1.0", + "pkg:npm/is-obj@1.0.1", + "pkg:npm/is-object@1.0.1", + "pkg:npm/is-path-inside@1.0.1", + "pkg:npm/is-plain-obj@1.1.0", + "pkg:npm/is-plain-obj@1.1.0", + "pkg:npm/is-plain-object@2.0.4", + "pkg:npm/is-posix-bracket@0.1.1", + "pkg:npm/is-primitive@2.0.0", + "pkg:npm/is-redirect@1.0.0", + "pkg:npm/is-retry-allowed@1.1.0", + "pkg:npm/is-stream@1.1.0", + "pkg:npm/is-typedarray@1.0.0", + "pkg:npm/is-whitespace-character@1.0.2", + "pkg:npm/is-whitespace-character@1.0.2", + "pkg:npm/is-windows@1.0.2", + "pkg:npm/is-word-character@1.0.2", + "pkg:npm/is-word-character@1.0.2", + "pkg:npm/isarray@0.0.1", + "pkg:npm/isarray@1.0.0", + "pkg:npm/isarray@1.0.0", + "pkg:npm/isexe@2.0.0", + "pkg:npm/isobject@2.1.0", + "pkg:npm/isstream@0.1.2", + "pkg:npm/js-yaml@3.11.0", + "pkg:npm/js-yaml@3.12.0", + "pkg:npm/jsbn@0.1.1", + "pkg:npm/json-parse-better-errors@1.0.2", + "pkg:npm/json-parse-better-errors@1.0.2", + "pkg:npm/json-schema@0.2.3", + "pkg:npm/json-schema-traverse@0.3.1", + "pkg:npm/json-stringify-safe@5.0.1", + "pkg:npm/json5@1.0.1", + "pkg:npm/jsonparse@1.3.1", + "pkg:npm/jsprim@1.4.1", + "pkg:npm/kebab-case@1.0.0", + "pkg:npm/kind-of@3.2.2", + "pkg:npm/latest-version@3.1.0", + "pkg:npm/lazy-property@1.0.0", + "pkg:npm/lcid@1.0.0", + "pkg:npm/libcipm@2.0.2", + "pkg:npm/libnpmhook@4.0.1", + "pkg:npm/libnpx@10.2.0", + "pkg:npm/load-plugin@2.2.2", + "pkg:npm/locate-path@2.0.0", + "pkg:npm/lock-verify@2.0.2", + "pkg:npm/lockfile@1.0.4", + "pkg:npm/lodash._baseindexof@3.1.0", + "pkg:npm/lodash._baseuniq@4.6.0", + "pkg:npm/lodash._bindcallback@3.0.1", + "pkg:npm/lodash._cacheindexof@3.0.2", + "pkg:npm/lodash._createcache@3.1.2", + "pkg:npm/lodash._createset@4.0.3", + "pkg:npm/lodash._getnative@3.9.1", + "pkg:npm/lodash._root@3.0.1", + "pkg:npm/lodash.clonedeep@4.5.0", + "pkg:npm/lodash.debounce@4.0.8", + "pkg:npm/lodash.iteratee@4.7.0", + "pkg:npm/lodash.restparam@3.6.1", + "pkg:npm/lodash.union@4.6.0", + "pkg:npm/lodash.uniq@4.5.0", + "pkg:npm/lodash.without@4.4.0", + "pkg:npm/longest-streak@1.0.0", + "pkg:npm/longest-streak@2.0.2", + "pkg:npm/lowercase-keys@1.0.1", + "pkg:npm/lru-cache@4.1.3", + "pkg:npm/magic-string@0.22.5", + "pkg:npm/make-dir@1.3.0", + "pkg:npm/make-fetch-happen@3.0.0", + "pkg:npm/make-fetch-happen@4.0.1", + "pkg:npm/map-cache@0.2.2", + "pkg:npm/map-visit@1.0.0", + "pkg:npm/mapz@1.0.2", + "pkg:npm/markdown-escapes@1.0.2", + "pkg:npm/markdown-escapes@1.0.2", + "pkg:npm/markdown-extensions@1.1.1", + "pkg:npm/markdown-table@0.4.0", + "pkg:npm/markdown-table@1.1.2", + "pkg:npm/mdast-comment-marker@1.0.3", + "pkg:npm/mdast-comment-marker@1.0.3", + "pkg:npm/mdast-util-compact@1.0.2", + "pkg:npm/mdast-util-definitions@1.2.2", + "pkg:npm/mdast-util-heading-style@1.0.4", + "pkg:npm/mdast-util-to-hast@3.0.1", + "pkg:npm/mdast-util-to-string@1.0.5", + "pkg:npm/mdurl@1.0.1", + "pkg:npm/meant@1.0.1", + "pkg:npm/mem@1.1.0", + "pkg:npm/micromatch@2.3.11", + "pkg:npm/mime-db@1.35.0", + "pkg:npm/mime-types@2.1.19", + "pkg:npm/mimic-fn@1.2.0", + "pkg:npm/minimatch@3.0.4", + "pkg:npm/minimatch@3.0.4", + "pkg:npm/minimatch@3.0.4", + "pkg:npm/minimist@0.0.8", + "pkg:npm/minimist@1.2.0", + "pkg:npm/minimist@1.2.0", + "pkg:npm/minipass@2.3.3", + "pkg:npm/minizlib@1.1.0", + "pkg:npm/mississippi@2.0.0", + "pkg:npm/mississippi@3.0.0", + "pkg:npm/mixin-deep@1.3.1", + "pkg:npm/mkdirp@0.5.1", + "pkg:npm/module-stub@1.1.12", + "pkg:npm/move-concurrently@1.0.1", + "pkg:npm/ms@2.0.0", + "pkg:npm/ms@2.0.0", + "pkg:npm/ms@2.0.0", + "pkg:npm/ms@2.1.1", + "pkg:npm/mute-stream@0.0.7", + "pkg:npm/nan@2.11.0", + "pkg:npm/nanomatch@1.2.13", + "pkg:npm/node-core-clang-format@1.0.0", + "pkg:npm/node-doc-generator@0.0.0", + "pkg:npm/node-fetch-npm@2.0.2", + "pkg:npm/node-gyp@3.8.0", + "pkg:npm/node-inspect@1.11.5", + "pkg:npm/node-lint-md-cli-rollup@1.0.0", + "pkg:npm/nopt@3.0.6", + "pkg:npm/nopt@4.0.1", + "pkg:npm/normalize-package-data@2.4.0", + "pkg:npm/normalize-path@2.1.1", + "pkg:npm/npm@6.4.1", + "pkg:npm/npm-audit-report@1.3.1", + "pkg:npm/npm-bundled@1.0.5", + "pkg:npm/npm-cache-filename@1.0.2", + "pkg:npm/npm-init@0.0.0", + "pkg:npm/npm-install-checks@3.0.0", + "pkg:npm/npm-lifecycle@2.1.0", + "pkg:npm/npm-logical-tree@1.2.1", + "pkg:npm/npm-package-arg@6.1.0", + "pkg:npm/npm-packlist@1.1.11", + "pkg:npm/npm-pick-manifest@2.1.0", + "pkg:npm/npm-prefix@1.2.0", + "pkg:npm/npm-profile@3.0.2", + "pkg:npm/npm-registry-client@8.6.0", + "pkg:npm/npm-registry-fetch@1.1.0", + "pkg:npm/npm-registry-fetch@3.1.1", + "pkg:npm/npm-run-path@2.0.2", + "pkg:npm/npm-user-validate@1.0.0", + "pkg:npm/npmlog@4.1.2", + "pkg:npm/nth-check@1.0.1", + "pkg:npm/number-is-nan@1.0.1", + "pkg:npm/number-is-nan@1.0.1", + "pkg:npm/oauth-sign@0.9.0", + "pkg:npm/object-assign@4.1.1", + "pkg:npm/object-assign@4.1.1", + "pkg:npm/object-copy@0.1.0", + "pkg:npm/object-keys@1.0.12", + "pkg:npm/object-visit@1.0.1", + "pkg:npm/object.omit@2.0.1", + "pkg:npm/object.pick@1.3.0", + "pkg:npm/once@1.4.0", + "pkg:npm/once@1.4.0", + "pkg:npm/once@1.4.0", + "pkg:npm/once@1.4.0", + "pkg:npm/opener@1.5.0", + "pkg:npm/os-homedir@1.0.2", + "pkg:npm/os-homedir@1.0.2", + "pkg:npm/os-locale@2.1.0", + "pkg:npm/os-tmpdir@1.0.2", + "pkg:npm/osenv@0.1.5", + "pkg:npm/p-finally@1.0.0", + "pkg:npm/p-limit@1.2.0", + "pkg:npm/p-locate@2.0.0", + "pkg:npm/p-try@1.0.0", + "pkg:npm/package-json@4.0.1", + "pkg:npm/package-name@1.2.3", + "pkg:npm/package-name@1.2.3", + "pkg:npm/pacote@8.1.6", + "pkg:npm/parallel-transform@1.1.0", + "pkg:npm/parse-entities@1.1.2", + "pkg:npm/parse-entities@1.1.2", + "pkg:npm/parse-glob@3.0.4", + "pkg:npm/parse-json@4.0.0", + "pkg:npm/parse5@3.0.3", + "pkg:npm/pascalcase@0.1.1", + "pkg:npm/path-dirname@1.0.2", + "pkg:npm/path-exists@3.0.0", + "pkg:npm/path-is-absolute@1.0.1", + "pkg:npm/path-is-absolute@1.0.1", + "pkg:npm/path-is-absolute@1.0.1", + "pkg:npm/path-is-inside@1.0.2", + "pkg:npm/path-key@2.0.1", + "pkg:npm/path-parse@1.0.5", + "pkg:npm/path-parse@1.0.6", + "pkg:npm/performance-now@2.1.0", + "pkg:npm/pify@3.0.0", + "pkg:npm/plur@3.0.1", + "pkg:npm/posix-character-classes@0.1.1", + "pkg:npm/prepend-http@1.0.4", + "pkg:npm/preserve@0.2.0", + "pkg:npm/process-nextick-args@2.0.0", + "pkg:npm/process-nextick-args@2.0.0", + "pkg:npm/promise-inflight@1.0.1", + "pkg:npm/promise-retry@1.1.1", + "pkg:npm/promzard@0.3.0", + "pkg:npm/property-information@3.2.0", + "pkg:npm/proto-list@1.2.4", + "pkg:npm/protoduck@5.0.0", + "pkg:npm/prr@1.0.1", + "pkg:npm/pseudomap@1.0.2", + "pkg:npm/psl@1.1.29", + "pkg:npm/pump@2.0.1", + "pkg:npm/pump@2.0.1", + "pkg:npm/pump@3.0.0", + "pkg:npm/pumpify@1.5.1", + "pkg:npm/punycode@1.4.1", + "pkg:npm/qrcode-terminal@0.12.0", + "pkg:npm/qs@6.5.2", + "pkg:npm/query-string@6.1.0", + "pkg:npm/qw@1.0.1", + "pkg:npm/randomatic@1.1.7", + "pkg:npm/rc@1.2.7", + "pkg:npm/rc@1.2.8", + "pkg:npm/read@1.0.7", + "pkg:npm/read-cmd-shim@1.0.1", + "pkg:npm/read-installed@1.0.0", + "pkg:npm/read-installed@4.0.3", + "pkg:npm/read-package-json@2.0.13", + "pkg:npm/read-package-tree@5.2.1", + "pkg:npm/readable-stream@1.1.14", + "pkg:npm/readable-stream@2.3.6", + "pkg:npm/readable-stream@2.3.6", + "pkg:npm/readdir-scoped-modules@1.0.2", + "pkg:npm/readdirp@2.1.0", + "pkg:npm/regex-cache@0.4.4", + "pkg:npm/regex-not@1.0.2", + "pkg:npm/registry-auth-token@3.3.2", + "pkg:npm/registry-url@3.1.0", + "pkg:npm/rehype-raw@2.0.0", + "pkg:npm/rehype-stringify@3.0.0", + "pkg:npm/remark@5.1.0", + "pkg:npm/remark@8.0.0", + "pkg:npm/remark-html@7.0.0", + "pkg:npm/remark-lint@6.0.2", + "pkg:npm/remark-lint@6.0.2", + "pkg:npm/remark-lint-blockquote-indentation@1.0.2", + "pkg:npm/remark-lint-checkbox-character-style@1.0.2", + "pkg:npm/remark-lint-checkbox-content-indent@1.0.2", + "pkg:npm/remark-lint-code-block-style@1.0.2", + "pkg:npm/remark-lint-definition-spacing@1.0.2", + "pkg:npm/remark-lint-fenced-code-flag@1.0.2", + "pkg:npm/remark-lint-fenced-code-marker@1.0.2", + "pkg:npm/remark-lint-file-extension@1.0.2", + "pkg:npm/remark-lint-final-definition@1.0.2", + "pkg:npm/remark-lint-final-newline@1.0.2", + "pkg:npm/remark-lint-first-heading-level@1.1.2", + "pkg:npm/remark-lint-hard-break-spaces@1.0.3", + "pkg:npm/remark-lint-heading-style@1.0.2", + "pkg:npm/remark-lint-maximum-line-length@1.1.0", + "pkg:npm/remark-lint-no-auto-link-without-protocol@1.0.2", + "pkg:npm/remark-lint-no-blockquote-without-caret@1.0.0", + "pkg:npm/remark-lint-no-duplicate-definitions@1.0.2", + "pkg:npm/remark-lint-no-file-name-articles@1.0.2", + "pkg:npm/remark-lint-no-file-name-consecutive-dashes@1.0.2", + "pkg:npm/remark-lint-no-file-name-outer-dashes@1.0.3", + "pkg:npm/remark-lint-no-heading-content-indent@1.0.2", + "pkg:npm/remark-lint-no-heading-indent@1.0.2", + "pkg:npm/remark-lint-no-inline-padding@1.0.2", + "pkg:npm/remark-lint-no-multiple-toplevel-headings@1.0.2", + "pkg:npm/remark-lint-no-shell-dollars@1.0.2", + "pkg:npm/remark-lint-no-shortcut-reference-image@1.0.2", + "pkg:npm/remark-lint-no-table-indentation@1.0.2", + "pkg:npm/remark-lint-no-tabs@1.0.2", + "pkg:npm/remark-lint-no-unused-definitions@1.0.2", + "pkg:npm/remark-lint-prohibited-strings@1.0.3", + "pkg:npm/remark-lint-rule-style@1.0.2", + "pkg:npm/remark-lint-strong-marker@1.0.2", + "pkg:npm/remark-lint-table-cell-padding@1.0.2", + "pkg:npm/remark-lint-table-pipes@1.0.2", + "pkg:npm/remark-message-control@4.1.0", + "pkg:npm/remark-message-control@4.1.0", + "pkg:npm/remark-parse@4.0.0", + "pkg:npm/remark-parse@5.0.0", + "pkg:npm/remark-preset-lint-node@1.0.2", + "pkg:npm/remark-preset-lint-node@file:remark-preset-lint-node", + "pkg:npm/remark-rehype@3.0.0", + "pkg:npm/remark-stringify@1.1.0", + "pkg:npm/remark-stringify@4.0.0", + "pkg:npm/remove-trailing-separator@1.1.0", + "pkg:npm/repeat-element@1.1.2", + "pkg:npm/repeat-string@1.6.1", + "pkg:npm/repeat-string@1.6.1", + "pkg:npm/replace-ext@1.0.0", + "pkg:npm/replace-ext@1.0.0", + "pkg:npm/request@2.88.0", + "pkg:npm/require-directory@2.1.1", + "pkg:npm/require-main-filename@1.0.1", + "pkg:npm/resolve@1.7.1", + "pkg:npm/resolve@1.8.1", + "pkg:npm/resolve-from@4.0.0", + "pkg:npm/resolve-from@4.0.0", + "pkg:npm/resolve-url@0.2.1", + "pkg:npm/ret@0.1.15", + "pkg:npm/retry@0.10.1", + "pkg:npm/retry@0.10.1", + "pkg:npm/retry@0.12.0", + "pkg:npm/rimraf@2.6.2", + "pkg:npm/rollup@0.55.5", + "pkg:npm/rollup-plugin-commonjs@8.4.1", + "pkg:npm/rollup-plugin-json@2.3.1", + "pkg:npm/rollup-plugin-node-resolve@3.4.0", + "pkg:npm/rollup-pluginutils@2.0.1", + "pkg:npm/run-queue@1.0.3", + "pkg:npm/safe-buffer@5.1.2", + "pkg:npm/safe-buffer@5.1.2", + "pkg:npm/safe-regex@1.1.0", + "pkg:npm/safer-buffer@2.1.2", + "pkg:npm/semver@5.3.0", + "pkg:npm/semver@5.5.0", + "pkg:npm/semver-diff@2.1.0", + "pkg:npm/set-blocking@2.0.0", + "pkg:npm/set-immediate-shim@1.0.1", + "pkg:npm/set-value@2.0.0", + "pkg:npm/sha@2.0.1", + "pkg:npm/shebang-command@1.2.0", + "pkg:npm/shebang-regex@1.0.0", + "pkg:npm/shellsubstitute@1.2.0", + "pkg:npm/signal-exit@3.0.2", + "pkg:npm/slash@1.0.0", + "pkg:npm/sliced@1.0.1", + "pkg:npm/slide@1.1.6", + "pkg:npm/smart-buffer@1.1.15", + "pkg:npm/smart-buffer@4.0.1", + "pkg:npm/snapdragon@0.8.2", + "pkg:npm/snapdragon-node@2.1.1", + "pkg:npm/snapdragon-util@3.0.1", + "pkg:npm/socks@1.1.10", + "pkg:npm/socks@2.2.0", + "pkg:npm/socks-proxy-agent@3.0.1", + "pkg:npm/socks-proxy-agent@4.0.1", + "pkg:npm/sorted-object@2.0.1", + "pkg:npm/sorted-union-stream@2.1.3", + "pkg:npm/source-map@0.5.7", + "pkg:npm/source-map-resolve@0.5.2", + "pkg:npm/source-map-url@0.4.0", + "pkg:npm/space-separated-tokens@1.1.2", + "pkg:npm/spdx-correct@3.0.0", + "pkg:npm/spdx-exceptions@2.1.0", + "pkg:npm/spdx-expression-parse@3.0.0", + "pkg:npm/spdx-license-ids@3.0.0", + "pkg:npm/split-string@3.1.0", + "pkg:npm/sprintf-js@1.0.3", + "pkg:npm/sprintf-js@1.0.3", + "pkg:npm/sshpk@1.14.2", + "pkg:npm/ssri@5.3.0", + "pkg:npm/ssri@5.3.0", + "pkg:npm/ssri@6.0.0", + "pkg:npm/state-toggle@1.0.1", + "pkg:npm/state-toggle@1.0.1", + "pkg:npm/static-extend@0.1.2", + "pkg:npm/stream-each@1.2.2", + "pkg:npm/stream-iterate@1.2.0", + "pkg:npm/stream-shift@1.0.0", + "pkg:npm/strict-uri-encode@2.0.0", + "pkg:npm/string-width@1.0.2", + "pkg:npm/string-width@1.0.2", + "pkg:npm/string-width@1.0.2", + "pkg:npm/string-width@2.1.1", + "pkg:npm/string-width@2.1.1", + "pkg:npm/string_decoder@0.10.31", + "pkg:npm/string_decoder@1.1.1", + "pkg:npm/string_decoder@1.1.1", + "pkg:npm/stringify-entities@1.3.2", + "pkg:npm/stringify-entities@1.3.2", + "pkg:npm/stringify-package@1.0.0", + "pkg:npm/strip-ansi@3.0.1", + "pkg:npm/strip-ansi@4.0.0", + "pkg:npm/strip-ansi@4.0.0", + "pkg:npm/strip-ansi@4.0.0", + "pkg:npm/strip-eof@1.0.0", + "pkg:npm/strip-json-comments@2.0.1", + "pkg:npm/strip-json-comments@2.0.1", + "pkg:npm/supports-color@5.4.0", + "pkg:npm/supports-color@5.5.0", + "pkg:npm/tar@2.2.1", + "pkg:npm/tar@4.4.6", + "pkg:npm/term-size@1.2.0", + "pkg:npm/text-table@0.2.0", + "pkg:npm/text-table@0.2.0", + "pkg:npm/through@2.3.8", + "pkg:npm/through2@2.0.3", + "pkg:npm/timed-out@4.0.1", + "pkg:npm/tiny-relative-date@1.3.0", + "pkg:npm/to-object-path@0.3.0", + "pkg:npm/to-regex@3.0.2", + "pkg:npm/to-regex-range@2.1.1", + "pkg:npm/to-vfile@4.0.0", + "pkg:npm/to-vfile@5.0.0", + "pkg:npm/tough-cookie@2.4.3", + "pkg:npm/trim@0.0.1", + "pkg:npm/trim@0.0.1", + "pkg:npm/trim@0.0.1", + "pkg:npm/trim-lines@1.1.1", + "pkg:npm/trim-trailing-lines@1.1.1", + "pkg:npm/trim-trailing-lines@1.1.1", + "pkg:npm/trough@1.0.2", + "pkg:npm/trough@1.0.3", + "pkg:npm/tunnel-agent@0.6.0", + "pkg:npm/tweetnacl@0.14.5", + "pkg:npm/typedarray@0.0.6", + "pkg:npm/typedarray@0.0.6", + "pkg:npm/uid-number@0.0.6", + "pkg:npm/umask@1.1.0", + "pkg:npm/unherit@1.1.1", + "pkg:npm/unherit@1.1.1", + "pkg:npm/unified@6.2.0", + "pkg:npm/unified@7.0.0", + "pkg:npm/unified-args@6.0.0", + "pkg:npm/unified-engine@5.1.0", + "pkg:npm/unified-lint-rule@1.0.3", + "pkg:npm/unified-message-control@1.0.4", + "pkg:npm/unified-message-control@1.0.4", + "pkg:npm/union-value@1.0.0", + "pkg:npm/unique-filename@1.1.0", + "pkg:npm/unique-slug@2.0.0", + "pkg:npm/unique-string@1.0.0", + "pkg:npm/unist-builder@1.0.2", + "pkg:npm/unist-util-find@1.0.1", + "pkg:npm/unist-util-generated@1.1.2", + "pkg:npm/unist-util-generated@1.1.2", + "pkg:npm/unist-util-inspect@4.1.3", + "pkg:npm/unist-util-is@2.1.2", + "pkg:npm/unist-util-is@2.1.2", + "pkg:npm/unist-util-is@2.1.2", + "pkg:npm/unist-util-position@3.0.1", + "pkg:npm/unist-util-position@3.0.1", + "pkg:npm/unist-util-remove-position@1.1.2", + "pkg:npm/unist-util-remove-position@1.1.2", + "pkg:npm/unist-util-select@1.5.0", + "pkg:npm/unist-util-stringify-position@1.1.2", + "pkg:npm/unist-util-stringify-position@1.1.2", + "pkg:npm/unist-util-stringify-position@1.1.2", + "pkg:npm/unist-util-visit@1.3.1", + "pkg:npm/unist-util-visit@1.4.0", + "pkg:npm/unist-util-visit@1.4.0", + "pkg:npm/unist-util-visit-parents@2.0.1", + "pkg:npm/unist-util-visit-parents@2.0.1", + "pkg:npm/unpipe@1.0.0", + "pkg:npm/unset-value@1.0.0", + "pkg:npm/untildify@2.1.0", + "pkg:npm/unzip-response@2.0.1", + "pkg:npm/upath@1.1.0", + "pkg:npm/update-notifier@2.5.0", + "pkg:npm/urix@0.1.0", + "pkg:npm/url-parse-lax@1.0.0", + "pkg:npm/use@3.1.1", + "pkg:npm/util-deprecate@1.0.2", + "pkg:npm/util-deprecate@1.0.2", + "pkg:npm/util-extend@1.0.3", + "pkg:npm/uuid@3.3.2", + "pkg:npm/validate-npm-package-license@3.0.4", + "pkg:npm/validate-npm-package-name@3.0.0", + "pkg:npm/verror@1.10.0", + "pkg:npm/vfile@2.3.0", + "pkg:npm/vfile@3.0.0", + "pkg:npm/vfile-location@2.0.3", + "pkg:npm/vfile-location@2.0.3", + "pkg:npm/vfile-location@2.0.3", + "pkg:npm/vfile-message@1.0.1", + "pkg:npm/vfile-message@1.0.1", + "pkg:npm/vfile-reporter@5.0.0", + "pkg:npm/vfile-statistics@1.1.1", + "pkg:npm/vlq@0.2.3", + "pkg:npm/wcwidth@1.0.1", + "pkg:npm/web-namespaces@1.1.2", + "pkg:npm/which@1.3.1", + "pkg:npm/which-module@2.0.0", + "pkg:npm/wide-align@1.1.2", + "pkg:npm/widest-line@2.0.0", + "pkg:npm/worker-farm@1.6.0", + "pkg:npm/wrap-ansi@2.1.0", + "pkg:npm/wrapped@1.0.1", + "pkg:npm/wrappy@1.0.2", + "pkg:npm/wrappy@1.0.2", + "pkg:npm/wrappy@1.0.2", + "pkg:npm/wrappy@1.0.2", + "pkg:npm/write-file-atomic@2.3.0", + "pkg:npm/x-is-array@0.1.0", + "pkg:npm/x-is-function@1.0.4", + "pkg:npm/x-is-string@0.1.0", + "pkg:npm/x-is-string@0.1.0", + "pkg:npm/xdg-basedir@3.0.0", + "pkg:npm/xtend@4.0.1", + "pkg:npm/xtend@4.0.1", + "pkg:npm/xtend@4.0.1", + "pkg:npm/xtend@4.0.1", + "pkg:npm/y18n@3.2.1", + "pkg:npm/y18n@4.0.0", + "pkg:npm/yallist@2.1.2", + "pkg:npm/yallist@3.0.2", + "pkg:npm/yallist@3.0.2", + "pkg:npm/yargs@11.0.0", + "pkg:npm/yargs-parser@9.0.2", + "pkg:npm/zwitch@1.0.3" + ] + }, + { + "name": "dnf-plugins-core-4.0.11-5.oe1.src.rpm", + "purls": [ + "pkg:rpm/bar@4-6?arch=noarch&epoch=0&upstream=bar-4-6.src.rpm", + "pkg:rpm/foo@4-6?arch=noarch&epoch=0&upstream=foo-4-6.src.rpm", + "pkg:rpm/foo@4-6?arch=noarch&epoch=0&upstream=foo-4-6.src.rpm", + "pkg:rpm/foo@4-6?arch=noarch&epoch=0", + "pkg:rpm/foo@4-7?arch=noarch&epoch=0", + "pkg:rpm/foo@4-8?arch=noarch&epoch=0", + "pkg:rpm/foo@4-6?arch=noarch&epoch=0&upstream=foo-4-6.src.rpm", + "pkg:rpm/foo@4-7?arch=noarch&epoch=0&upstream=foo-4-7.src.rpm", + "pkg:rpm/foo@4-8?arch=noarch&epoch=0&upstream=foo-4-8.src.rpm", + "pkg:rpm/tour@4-6?arch=noarch&epoch=0" + ] + }, + { + "name": "python-virtualenv-16.0.0-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/virtualenv@16.0.0" + ] + }, + { + "name": "python-construct-2.5.1-19.oe1.src.rpm", + "purls": [ + "pkg:pypi/construct@2.5.1" + ] + }, + { + "name": "mongodb-4.0.1-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/PyYAML@3.11", + "pkg:pypi/boto3@1.5.27", + "pkg:pypi/cheetah3@3.0.0", + "pkg:pypi/concurrencytest@0.1.2", + "pkg:pypi/cryptography@1.7.2", + "pkg:pypi/jinja2@2.10", + "pkg:pypi/jira@1.0.10", + "pkg:pypi/mock@2.0.0", + "pkg:pypi/mock@2.0.0", + "pkg:pypi/mypy@0.580", + "pkg:pypi/psutil@5.4.3", + "pkg:pypi/pydocstyle@2.1.1", + "pkg:pypi/pyjwt@1.5.3", + "pkg:pypi/pylint@1.8.3", + "pkg:pypi/pypiwin32@219", + "pkg:pypi/pypiwin32@223", + "pkg:pypi/python-subunit@0.0.16", + "pkg:pypi/pyyaml@3.11", + "pkg:pypi/scons@2.5.0", + "pkg:pypi/testscenarios@0.4", + "pkg:pypi/typing@3.6.1", + "pkg:pypi/unittest-xml-reporting@2.1.0", + "pkg:pypi/yapf@0.21.0" + ] + }, + { + "name": "python-execnet-1.5.0-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/execnet@1.5.0" + ] + }, + { + "name": "rpm-4.15.1-12.oe1.src.rpm", + "purls": [ + "pkg:rpm/capstest@1.0-1?arch=noarch&epoch=0&upstream=capstest-1.0-1.src.rpm", + "pkg:rpm/foo@1.0-1?arch=noarch&epoch=0", + "pkg:rpm/foo@1.0-1?arch=noarch&epoch=0&upstream=foo-1.0-1.src.rpm", + "pkg:rpm/hello@1.0-1?arch=i386&epoch=0", + "pkg:rpm/hello@1.0-1?arch=i386&epoch=0&upstream=hello-1.0-1.src.rpm", + "pkg:rpm/hello@1.0-1?arch=ppc64&epoch=0&upstream=hello-1.0-1.src.rpm", + "pkg:rpm/hello@2.0-1?arch=i686&epoch=0&upstream=hello-2.0-1.src.rpm", + "pkg:rpm/hello@2.0-1?arch=x86_64&epoch=0&upstream=hello-2.0-1.src.rpm", + "pkg:rpm/hello@2.0-1?arch=x86_64&epoch=0&upstream=hello-2.0-1.src.rpm" + ] + }, + { + "name": "python-gevent-1.3.6-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/gevent@1.3.6" + ] + }, + { + "name": "python-hyperlink-18.0.0-8.oe1.src.rpm", + "purls": [ + "pkg:pypi/coverage@4.4.1", + "pkg:pypi/hyperlink@18.0.0", + "pkg:pypi/idna@2.5", + "pkg:pypi/pytest@2.9.2", + "pkg:pypi/pytest-cov@2.3.0", + "pkg:pypi/tox@2.6.0" + ] + }, + { + "name": "python-importlib-metadata-0.23-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/importlib-metadata@0.23" + ] + }, + { + "name": "python-lxml-4.2.3-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/lxml@4.2.3" + ] + }, + { + "name": "python-werkzeug-0.14.1-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/Werkzeug@0.14.1" + ] + }, + { + "name": "python-pysocks-1.7.0-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/PySocks@1.7.0" + ] + }, + { + "name": "python-pid-2.1.1-12.oe1.src.rpm", + "purls": [ + "pkg:pypi/pid@2.1.1" + ] + }, + { + "name": "python-pytest-shutil-1.2.6-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytest-shutil@1.2.6" + ] + }, + { + "name": "python-sure-1.4.11-4.oe1.src.rpm", + "purls": [ + "pkg:pypi/mock@2.0.0", + "pkg:pypi/six@1.10.0", + "pkg:pypi/sure@1.4.11" + ] + }, + { + "name": "SDL2-2.0.8-9.oe1.src.rpm", + "purls": [ + "pkg:maven/gradle-wrapper/gradle-wrapper@2.10" + ] + }, + { + "name": "python-cherrypy-3.5.0-12.oe1.src.rpm", + "purls": [ + "pkg:pypi/CherryPy@3.5.0" + ] + }, + { + "name": "python-iso8601-0.1.11-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/iso8601@0.1.11" + ] + }, + { + "name": "python-sphinx_rtd_theme-0.4.1-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/sphinx-rtd-theme@0.4.1" + ] + }, + { + "name": "dbus-python-1.2.8-8.oe1.src.rpm", + "purls": [ + "pkg:pypi/dbus-python@1.2.8" + ] + }, + { + "name": "python-docker-pycreds-0.4.0-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/docker-pycreds@0.4.0", + "pkg:pypi/flake8@2.4.1", + "pkg:pypi/pytest@3.0.2", + "pkg:pypi/pytest-cov@2.3.1" + ] + }, + { + "name": "librepo-1.11.0-2.oe1.src.rpm", + "purls": [ + "pkg:rpm/Archer@3.4.5-6?arch=x86_64&epoch=2&upstream=Archer-3.4.5-6.src.rpm", + "pkg:rpm/empty@0-0?arch=x86_64&epoch=0", + "pkg:rpm/filesystem@2.4.44-1.fc16?arch=i686&epoch=0&upstream=filesystem-2.4.44-1.fc16.src.rpm" + ] + }, + { + "name": "python-jwt-1.7.1-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/PyJWT@1.7.1" + ] + }, + { + "name": "firefox-62.0.3-4.oe1.src.rpm", + "purls": [ + "pkg:rpm/firefox@62.0.3-4.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "kata-containers-v1.7.0-18.oe1.src.rpm", + "purls": [ + "pkg:rpm/kata-containers@v1.7.0-18.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "syscontainer-tools-v0.9-36.oe1.src.rpm", + "purls": [ + "pkg:golang/github.com/BurntSushi/toml@v0.3.1", + "pkg:golang/github.com/Microsoft/go-winio@v0.4.14", + "pkg:golang/github.com/coreos/go-systemd@v0.0.0-20161114122254-48702e0da86b", + "pkg:golang/github.com/coreos/pkg@v0.0.0-20180928190104-399ea9e2e55f", + "pkg:golang/github.com/davecgh/go-spew@v1.1.1", + "pkg:golang/github.com/docker/docker@v1.13.1", + "pkg:golang/github.com/docker/go-units@v0.4.0", + "pkg:golang/github.com/docker/libnetwork@v0.5.6", + "pkg:golang/github.com/go-yaml/yaml@v2.1.0 incompatible", + "pkg:golang/github.com/godbus/dbus@v4.1.0 incompatible", + "pkg:golang/github.com/golang/crypto@v0.0.0-20190701094942-4def268fd1a4", + "pkg:golang/github.com/golang/net@v0.0.0-20190813141303-74dc4d7220e7", + "pkg:golang/github.com/golang/protobuf@v1.3.2", + "pkg:golang/github.com/golang/sync@v0.0.0-20190423024810-112230192c58", + "pkg:golang/github.com/golang/sys@v0.0.0-20190813064441-fde4db37ae7a", + "pkg:golang/github.com/golang/text@v0.3.2", + "pkg:golang/github.com/golang/tools@v0.0.0-20190815235612-5b08f89bfc0c", + "pkg:golang/github.com/golang/xerrors@v0.0.0-20190717185122-a985d3407aa7", + "pkg:golang/github.com/konsorten/go-windows-terminal-sequences@v1.0.1", + "pkg:golang/github.com/mrunalp/fileutils@v0.0.0-20171103030105-7d4729fb3618", + "pkg:golang/github.com/opencontainers/runc@v1.0.0-rc3", + "pkg:golang/github.com/opencontainers/runtime-spec@v1.0.0-rc5", + "pkg:golang/github.com/pkg/errors@v0.8.1", + "pkg:golang/github.com/pmezard/go-difflib@v1.0.0", + "pkg:golang/github.com/seccomp/libseccomp-golang@v0.9.1", + "pkg:golang/github.com/sirupsen/logrus@v1.4.1", + "pkg:golang/github.com/sirupsen/logrus@v1.4.2", + "pkg:golang/github.com/stretchr/objx@v0.1.1", + "pkg:golang/github.com/stretchr/testify@v1.2.2", + "pkg:golang/github.com/syndtr/gocapability@v0.0.0-20180916011248-d98352740cb2", + "pkg:golang/github.com/urfave/cli@v1.21.0", + "pkg:golang/github.com/vishvananda/netlink@v1.0.0", + "pkg:golang/github.com/vishvananda/netns@v0.0.0-20190625233234-7109fa855b0f", + "pkg:golang/golang.org/x/sys@v0.0.0-20190422165155-953cdadca894", + "pkg:golang/golang.org/x/sys@v0.0.0-20190507160741-ecd444e8653b", + "pkg:golang/golang.org/x/sys@v0.0.0-20190507160741-ecd444e8653b", + "pkg:golang/gopkg.in/yaml.v2@v2.2.2" + ] + }, + { + "name": "python-pbr-4.1.1-3.oe1.src.rpm", + "purls": [ + "pkg:pypi/pbr@4.1.1" + ] + }, + { + "name": "python-testtools-2.3.0-11.oe1.src.rpm", + "purls": [ + "pkg:pypi/testtools@2.3.0" + ] + }, + { + "name": "python-coverage-4.5.3-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/coverage@4.5.3" + ] + }, + { + "name": "python2-2.7.16-15.oe1.src.rpm", + "purls": [ + "pkg:pypi/wsgiref@0.1.2" + ] + }, + { + "name": "python-simplegeneric-0.8.1-11.oe1.src.rpm", + "purls": [ + "pkg:pypi/simplegeneric@0.8.1" + ] + }, + { + "name": "scipy-1.2.2-2.oe1.src.rpm", + "purls": [ + "pkg:npm/MathJax-grunt-cleaner@0.1.0" + ] + }, + { + "name": "nss-3.40.1-11.oe1.src.rpm", + "purls": [ + "pkg:npm/decision-task@0.0.1" + ] + }, + { + "name": "python-html5lib-1.0.1-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/pytest@3.2.5" + ] + }, + { + "name": "librsvg2-2.44.15-1.oe1.src.rpm", + "purls": [ + "pkg:cargo/aho-corasick@0.6.8", + "pkg:cargo/alga@0.7.2", + "pkg:cargo/ansi_term@0.11.0", + "pkg:cargo/approx@0.3.0", + "pkg:cargo/arrayvec@0.4.7", + "pkg:cargo/atty@0.2.11", + "pkg:cargo/backtrace@0.3.9", + "pkg:cargo/backtrace-sys@0.1.24", + "pkg:cargo/bitflags@0.9.1", + "pkg:cargo/bitflags@1.0.4", + "pkg:cargo/byteorder@1.2.6", + "pkg:cargo/c_vec@1.3.2", + "pkg:cargo/cairo-rs@0.4.1", + "pkg:cargo/cairo-sys-rs@0.6.0", + "pkg:cargo/cast@0.2.2", + "pkg:cargo/cc@1.0.25", + "pkg:cargo/cfg-if@0.1.5", + "pkg:cargo/chrono@0.4.6", + "pkg:cargo/clap@2.32.0", + "pkg:cargo/cloudabi@0.0.3", + "pkg:cargo/criterion@0.2.5", + "pkg:cargo/criterion-plot@0.2.5", + "pkg:cargo/criterion-stats@0.2.5", + "pkg:cargo/crossbeam-deque@0.2.0", + "pkg:cargo/crossbeam-epoch@0.3.1", + "pkg:cargo/crossbeam-utils@0.2.2", + "pkg:cargo/cssparser@0.24.0", + "pkg:cargo/cssparser-macros@0.3.4", + "pkg:cargo/csv@1.0.2", + "pkg:cargo/csv-core@0.1.4", + "pkg:cargo/downcast-rs@1.0.3", + "pkg:cargo/dtoa@0.4.3", + "pkg:cargo/dtoa-short@0.3.2", + "pkg:cargo/either@1.5.0", + "pkg:cargo/failure@0.1.2", + "pkg:cargo/failure_derive@0.1.2", + "pkg:cargo/float-cmp@0.4.0", + "pkg:cargo/fuchsia-zircon@0.3.3", + "pkg:cargo/fuchsia-zircon-sys@0.3.3", + "pkg:cargo/gdk-pixbuf@0.4.0", + "pkg:cargo/gdk-pixbuf-sys@0.6.0", + "pkg:cargo/generic-array@0.11.1", + "pkg:cargo/gio@0.4.1", + "pkg:cargo/gio-sys@0.6.0", + "pkg:cargo/glib@0.5.0", + "pkg:cargo/glib-sys@0.6.0", + "pkg:cargo/gobject-sys@0.6.0", + "pkg:cargo/handlebars@0.32.4", + "pkg:cargo/itertools@0.7.8", + "pkg:cargo/itertools-num@0.1.2", + "pkg:cargo/itoa@0.4.3", + "pkg:cargo/kernel32-sys@0.2.2", + "pkg:cargo/language-tags@0.2.2", + "pkg:cargo/lazy_static@0.2.11", + "pkg:cargo/lazy_static@1.1.0", + "pkg:cargo/libc@0.2.43", + "pkg:cargo/libm@0.1.2", + "pkg:cargo/locale_config@0.2.2", + "pkg:cargo/log@0.4.5", + "pkg:cargo/matches@0.1.8", + "pkg:cargo/matrixmultiply@0.1.14", + "pkg:cargo/memchr@2.1.0", + "pkg:cargo/memoffset@0.2.1", + "pkg:cargo/nalgebra@0.16.4", + "pkg:cargo/nodrop@0.1.12", + "pkg:cargo/num-complex@0.2.0", + "pkg:cargo/num-integer@0.1.39", + "pkg:cargo/num-traits@0.2.6", + "pkg:cargo/num_cpus@1.8.0", + "pkg:cargo/owning_ref@0.3.3", + "pkg:cargo/pango@0.4.0", + "pkg:cargo/pango-sys@0.6.0", + "pkg:cargo/pangocairo@0.5.0", + "pkg:cargo/pangocairo-sys@0.7.0", + "pkg:cargo/pest@1.0.6", + "pkg:cargo/pest_derive@1.0.8", + "pkg:cargo/phf@0.7.23", + "pkg:cargo/phf_codegen@0.7.23", + "pkg:cargo/phf_generator@0.7.23", + "pkg:cargo/phf_shared@0.7.23", + "pkg:cargo/pkg-config@0.3.14", + "pkg:cargo/proc-macro2@0.4.19", + "pkg:cargo/procedural-masquerade@0.1.6", + "pkg:cargo/quick-error@1.2.2", + "pkg:cargo/quote@0.3.15", + "pkg:cargo/quote@0.6.8", + "pkg:cargo/rand@0.4.3", + "pkg:cargo/rand@0.5.5", + "pkg:cargo/rand_core@0.2.2", + "pkg:cargo/rand_core@0.3.0", + "pkg:cargo/rawpointer@0.1.0", + "pkg:cargo/rayon@1.0.2", + "pkg:cargo/rayon-core@1.4.1", + "pkg:cargo/redox_syscall@0.1.40", + "pkg:cargo/redox_termios@0.1.1", + "pkg:cargo/regex@0.2.11", + "pkg:cargo/regex@1.0.5", + "pkg:cargo/regex-syntax@0.5.6", + "pkg:cargo/regex-syntax@0.6.2", + "pkg:cargo/rsvg_internals@0.0.1", + "pkg:cargo/rustc-demangle@0.1.9", + "pkg:cargo/ryu@0.2.6", + "pkg:cargo/same-file@1.0.3", + "pkg:cargo/scopeguard@0.3.3", + "pkg:cargo/serde@1.0.79", + "pkg:cargo/serde_derive@1.0.79", + "pkg:cargo/serde_json@1.0.31", + "pkg:cargo/simplelog@0.5.2", + "pkg:cargo/siphasher@0.2.3", + "pkg:cargo/smallvec@0.6.5", + "pkg:cargo/stable_deref_trait@1.1.1", + "pkg:cargo/strsim@0.7.0", + "pkg:cargo/syn@0.11.11", + "pkg:cargo/syn@0.14.9", + "pkg:cargo/syn@0.15.7", + "pkg:cargo/synom@0.11.3", + "pkg:cargo/synstructure@0.9.0", + "pkg:cargo/term@0.5.1", + "pkg:cargo/termion@1.5.1", + "pkg:cargo/textwrap@0.10.0", + "pkg:cargo/thread-scoped@1.0.2", + "pkg:cargo/thread_local@0.3.6", + "pkg:cargo/time@0.1.40", + "pkg:cargo/typenum@1.10.0", + "pkg:cargo/ucd-util@0.1.1", + "pkg:cargo/unicode-width@0.1.5", + "pkg:cargo/unicode-xid@0.0.4", + "pkg:cargo/unicode-xid@0.1.0", + "pkg:cargo/unreachable@1.0.0", + "pkg:cargo/utf8-ranges@1.0.1", + "pkg:cargo/vec_map@0.8.1", + "pkg:cargo/version_check@0.1.5", + "pkg:cargo/void@1.0.2", + "pkg:cargo/walkdir@2.2.5", + "pkg:cargo/winapi@0.2.8", + "pkg:cargo/winapi@0.3.6", + "pkg:cargo/winapi-build@0.1.1", + "pkg:cargo/winapi-i686-pc-windows-gnu@0.4.0", + "pkg:cargo/winapi-util@0.1.1", + "pkg:cargo/winapi-x86_64-pc-windows-gnu@0.4.0" + ] + }, + { + "name": "uboot-tools-2018.09-8.oe1.src.rpm", + "purls": [ + "pkg:pypi/Sphinx@1.4.9", + "pkg:pypi/docutils@0.12" + ] + }, + { + "name": "python-dict2xml-1.6.1-1.oe1.src.rpm", + "purls": [ + "pkg:pypi/dict2xml@1.6.1" + ] + }, + { + "name": "overpass-fonts-3.0.3-4.oe1.src.rpm", + "purls": [ + "pkg:npm/overpass@3.0.3" + ] + }, + { + "name": "kiwi-9.19.15-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/generateDS@2.29.24", + "pkg:pypi/kiwi@9.19.15", + "pkg:pypi/xattr@0.9.3" + ] + }, + { + "name": "suitesparse-4.4.6-17.oe1.src.rpm", + "purls": [ + "pkg:rpm/suitesparse@4.4.6-17.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "clamav-0.101.4-5.oe1.src.rpm", + "purls": [ + "pkg:rpm/clamav@0.101.4-5.oe1?arch=aarch64&epoch=0" + ] + }, + { + "name": "python-rsa-3.4.2-11.oe1.src.rpm", + "purls": [ + "pkg:pypi/rsa@3.4.2" + ] + }, + { + "name": "python-jinja2-2.10-10.oe1.src.rpm", + "purls": [ + "pkg:pypi/Jinja2@2.10" + ] + }, + { + "name": "ruby-2.5.1-104.oe1.src.rpm", + "purls": [ + "pkg:gem/bar@0.0.2", + "pkg:gem/diff-lcs@1.2.5", + "pkg:gem/foo@0.0.1", + "pkg:gem/rake@10.4.2", + "pkg:gem/rspec@2.14.1", + "pkg:gem/rspec-core@2.14.8", + "pkg:gem/rspec-expectations@2.14.5", + "pkg:gem/rspec-mocks@2.14.6" + ] + }, + { + "name": "python-requests-2.21.0-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/certifi@2018.4.16", + "pkg:pypi/chardet@3.0.4", + "pkg:pypi/e1839a8", + "pkg:pypi/idna@2.6", + "pkg:pypi/pysocks@1.6.8", + "pkg:pypi/urllib3@1.22" + ] + }, + { + "name": "python3-mallard-ducktype-0.3-5.oe1.src.rpm", + "purls": [ + "pkg:pypi/mallard-ducktype@0.3" + ] + }, + { + "name": "python-cheetah-3.1.0-7.oe1.src.rpm", + "purls": [ + "pkg:pypi/Cheetah3@3.1.0" + ] + }, + { + "name": "python-sqlalchemy-1.2.11-2.oe1.src.rpm", + "purls": [ + "pkg:pypi/SQLAlchemy@1.2.11" + ] + }, + { + "name": "python-sphinx-1.7.6-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/:sys_platform@win32", + "pkg:pypi/Sphinx@1.7.6" + ] + }, + { + "name": "ceph-12.2.8-6.oe1.src.rpm", + "purls": [ + "pkg:pypi/Sphinx@1.6.3", + "pkg:gem/activesupport@4.2.7", + "pkg:gem/addressable@2.4.0", + "pkg:pypi/ceph-brag@0.1", + "pkg:gem/coffee-script@2.4.1", + "pkg:gem/coffee-script-source@1.10.0", + "pkg:gem/colorator@1.1.0", + "pkg:npm/duk-debug@0.1.0", + "pkg:gem/ethon@0.9.1", + "pkg:gem/execjs@2.7.0", + "pkg:gem/faraday@0.9.2", + "pkg:gem/ffi@1.9.14", + "pkg:pypi/flake8@3.0.4", + "pkg:pypi/flake8@3.0.4", + "pkg:gem/forwardable-extended@2.6.0", + "pkg:gem/gemoji@2.1.0", + "pkg:gem/github-pages@104", + "pkg:gem/github-pages-health-check@1.2.0", + "pkg:gem/html-pipeline@2.4.2", + "pkg:gem/i18n@0.7.0", + "pkg:gem/jekyll@3.3.0", + "pkg:gem/jekyll-avatar@0.4.2", + "pkg:gem/jekyll-coffeescript@1.0.1", + "pkg:gem/jekyll-feed@0.8.0", + "pkg:gem/jekyll-gist@1.4.0", + "pkg:gem/jekyll-github-metadata@2.2.0", + "pkg:gem/jekyll-mentions@1.2.0", + "pkg:gem/jekyll-paginate@1.1.0", + "pkg:gem/jekyll-redirect-from@0.11.0", + "pkg:gem/jekyll-sass-converter@1.3.0", + "pkg:gem/jekyll-seo-tag@2.1.0", + "pkg:gem/jekyll-sitemap@0.12.0", + "pkg:gem/jekyll-swiss@0.4.0", + "pkg:gem/jekyll-watch@1.5.0", + "pkg:gem/jemoji@0.7.0", + "pkg:gem/json@1.8.3", + "pkg:gem/kramdown@1.11.1", + "pkg:gem/liquid@3.0.6", + "pkg:gem/listen@3.0.6", + "pkg:gem/mercenary@0.3.6", + "pkg:gem/mini_portile2@2.1.0", + "pkg:gem/minima@2.0.0", + "pkg:gem/minitest@5.9.1", + "pkg:gem/multipart-post@2.0.0", + "pkg:gem/net-dns@0.8.0", + "pkg:gem/nokogiri@1.6.8.1", + "pkg:gem/octokit@4.4.1", + "pkg:gem/pathutil@0.14.0", + "pkg:gem/public_suffix@1.5.3", + "pkg:npm/rapidjson@1.0.4", + "pkg:gem/rb-fsevent@0.9.8", + "pkg:gem/rb-inotify@0.9.7", + "pkg:gem/rouge@1.11.1", + "pkg:gem/safe_yaml@1.0.4", + "pkg:gem/sass@3.4.22", + "pkg:gem/sawyer@0.7.0", + "pkg:gem/terminal-table@1.7.3", + "pkg:gem/thread_safe@0.3.5", + "pkg:gem/typhoeus@0.8.0", + "pkg:gem/tzinfo@1.2.2", + "pkg:gem/unicode-display_width@1.1.1" + ] + } + ] +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/examples/one_package_purls.json b/ci/tools/openeuler-purl/examples/one_package_purls.json new file mode 100644 index 0000000000000000000000000000000000000000..d3f5801d7cdbbb9ce9d537331716a15af38ab724 --- /dev/null +++ b/ci/tools/openeuler-purl/examples/one_package_purls.json @@ -0,0 +1,932 @@ +{ + "name": "389-ds-base-1.4.0.31-2.oe1.src.rpm", + "purls": [ + "pkg:npm/389-console@1.0.0", + "pkg:npm/%40babel/code-frame@7.0.0", + "pkg:npm/%40babel/core@7.1.2", + "pkg:npm/%40babel/generator@7.1.3", + "pkg:npm/%40babel/helper-annotate-as-pure@7.0.0", + "pkg:npm/%40babel/helper-builder-binary-assignment-operator-visitor@7.1.0", + "pkg:npm/%40babel/helper-builder-react-jsx@7.0.0", + "pkg:npm/%40babel/helper-call-delegate@7.1.0", + "pkg:npm/%40babel/helper-create-class-features-plugin@7.4.4", + "pkg:npm/%40babel/helper-define-map@7.1.0", + "pkg:npm/%40babel/helper-explode-assignable-expression@7.1.0", + "pkg:npm/%40babel/helper-function-name@7.1.0", + "pkg:npm/%40babel/helper-get-function-arity@7.0.0", + "pkg:npm/%40babel/helper-hoist-variables@7.0.0", + "pkg:npm/%40babel/helper-member-expression-to-functions@7.0.0", + "pkg:npm/%40babel/helper-module-imports@7.0.0", + "pkg:npm/%40babel/helper-module-transforms@7.1.0", + "pkg:npm/%40babel/helper-optimise-call-expression@7.0.0", + "pkg:npm/%40babel/helper-plugin-utils@7.0.0", + "pkg:npm/%40babel/helper-regex@7.0.0", + "pkg:npm/%40babel/helper-remap-async-to-generator@7.1.0", + "pkg:npm/%40babel/helper-replace-supers@7.1.0", + "pkg:npm/%40babel/helper-simple-access@7.1.0", + "pkg:npm/%40babel/helper-split-export-declaration@7.0.0", + "pkg:npm/%40babel/helper-wrap-function@7.1.0", + "pkg:npm/%40babel/helpers@7.1.2", + "pkg:npm/%40babel/highlight@7.0.0", + "pkg:npm/%40babel/parser@7.1.3", + "pkg:npm/%40babel/plugin-proposal-async-generator-functions@7.1.0", + "pkg:npm/%40babel/plugin-proposal-class-properties@7.4.4", + "pkg:npm/%40babel/plugin-proposal-json-strings@7.0.0", + "pkg:npm/%40babel/plugin-proposal-object-rest-spread@7.0.0", + "pkg:npm/%40babel/plugin-proposal-optional-catch-binding@7.0.0", + "pkg:npm/%40babel/plugin-proposal-unicode-property-regex@7.0.0", + "pkg:npm/%40babel/plugin-syntax-async-generators@7.0.0", + "pkg:npm/%40babel/plugin-syntax-json-strings@7.0.0", + "pkg:npm/%40babel/plugin-syntax-jsx@7.0.0", + "pkg:npm/%40babel/plugin-syntax-object-rest-spread@7.0.0", + "pkg:npm/%40babel/plugin-syntax-optional-catch-binding@7.0.0", + "pkg:npm/%40babel/plugin-transform-arrow-functions@7.0.0", + "pkg:npm/%40babel/plugin-transform-async-to-generator@7.1.0", + "pkg:npm/%40babel/plugin-transform-block-scoped-functions@7.0.0", + "pkg:npm/%40babel/plugin-transform-block-scoping@7.0.0", + "pkg:npm/%40babel/plugin-transform-classes@7.1.0", + "pkg:npm/%40babel/plugin-transform-computed-properties@7.0.0", + "pkg:npm/%40babel/plugin-transform-destructuring@7.1.3", + "pkg:npm/%40babel/plugin-transform-dotall-regex@7.0.0", + "pkg:npm/%40babel/plugin-transform-duplicate-keys@7.0.0", + "pkg:npm/%40babel/plugin-transform-exponentiation-operator@7.1.0", + "pkg:npm/%40babel/plugin-transform-for-of@7.0.0", + "pkg:npm/%40babel/plugin-transform-function-name@7.1.0", + "pkg:npm/%40babel/plugin-transform-literals@7.0.0", + "pkg:npm/%40babel/plugin-transform-modules-amd@7.1.0", + "pkg:npm/%40babel/plugin-transform-modules-commonjs@7.1.0", + "pkg:npm/%40babel/plugin-transform-modules-systemjs@7.1.3", + "pkg:npm/%40babel/plugin-transform-modules-umd@7.1.0", + "pkg:npm/%40babel/plugin-transform-new-target@7.0.0", + "pkg:npm/%40babel/plugin-transform-object-super@7.1.0", + "pkg:npm/%40babel/plugin-transform-parameters@7.1.0", + "pkg:npm/%40babel/plugin-transform-react-display-name@7.0.0", + "pkg:npm/%40babel/plugin-transform-react-jsx@7.0.0", + "pkg:npm/%40babel/plugin-transform-react-jsx-self@7.0.0", + "pkg:npm/%40babel/plugin-transform-react-jsx-source@7.0.0", + "pkg:npm/%40babel/plugin-transform-regenerator@7.0.0", + "pkg:npm/%40babel/plugin-transform-shorthand-properties@7.0.0", + "pkg:npm/%40babel/plugin-transform-spread@7.0.0", + "pkg:npm/%40babel/plugin-transform-sticky-regex@7.0.0", + "pkg:npm/%40babel/plugin-transform-template-literals@7.0.0", + "pkg:npm/%40babel/plugin-transform-typeof-symbol@7.0.0", + "pkg:npm/%40babel/plugin-transform-unicode-regex@7.0.0", + "pkg:npm/%40babel/preset-env@7.1.0", + "pkg:npm/%40babel/preset-react@7.0.0", + "pkg:npm/%40babel/runtime@7.2.0", + "pkg:npm/%40babel/runtime-corejs2@7.2.0", + "pkg:npm/%40babel/template@7.1.2", + "pkg:npm/%40babel/traverse@7.1.4", + "pkg:npm/%40babel/types@7.1.3", + "pkg:npm/%40emotion/babel-utils@0.6.10", + "pkg:npm/%40emotion/hash@0.6.6", + "pkg:npm/%40emotion/memoize@0.6.6", + "pkg:npm/%40emotion/serialize@0.9.1", + "pkg:npm/%40emotion/stylis@0.7.1", + "pkg:npm/%40emotion/unitless@0.6.7", + "pkg:npm/%40emotion/utils@0.8.2", + "pkg:npm/%40fortawesome/fontawesome-common-types@0.2.19", + "pkg:npm/%40fortawesome/free-brands-svg-icons@5.9.0", + "pkg:npm/%40patternfly/react-core@3.58.1", + "pkg:npm/%40patternfly/react-icons@3.10.13", + "pkg:npm/%40patternfly/react-styles@3.4.6", + "pkg:npm/%40patternfly/react-tokens@2.6.5", + "pkg:npm/%40tippy.js/react@1.1.1", + "pkg:npm/%40types/c3@0.6.4", + "pkg:npm/%40types/d3@4.13.2", + "pkg:npm/%40types/d3-array@1.2.7", + "pkg:npm/%40types/d3-axis@1.0.12", + "pkg:npm/%40types/d3-brush@1.0.10", + "pkg:npm/%40types/d3-chord@1.0.9", + "pkg:npm/%40types/d3-collection@1.0.8", + "pkg:npm/%40types/d3-color@1.2.2", + "pkg:npm/%40types/d3-dispatch@1.0.7", + "pkg:npm/%40types/d3-drag@1.2.3", + "pkg:npm/%40types/d3-dsv@1.0.36", + "pkg:npm/%40types/d3-ease@1.0.8", + "pkg:npm/%40types/d3-force@1.2.1", + "pkg:npm/%40types/d3-format@1.3.1", + "pkg:npm/%40types/d3-geo@1.11.1", + "pkg:npm/%40types/d3-hierarchy@1.1.6", + "pkg:npm/%40types/d3-interpolate@1.3.1", + "pkg:npm/%40types/d3-path@1.0.8", + "pkg:npm/%40types/d3-polygon@1.0.7", + "pkg:npm/%40types/d3-quadtree@1.0.7", + "pkg:npm/%40types/d3-queue@3.0.8", + "pkg:npm/%40types/d3-random@1.1.2", + "pkg:npm/%40types/d3-request@1.0.5", + "pkg:npm/%40types/d3-scale@1.0.14", + "pkg:npm/%40types/d3-selection@1.4.1", + "pkg:npm/%40types/d3-shape@1.3.1", + "pkg:npm/%40types/d3-time@1.0.10", + "pkg:npm/%40types/d3-time-format@2.1.1", + "pkg:npm/%40types/d3-timer@1.0.9", + "pkg:npm/%40types/d3-transition@1.1.4", + "pkg:npm/%40types/d3-voronoi@1.1.9", + "pkg:npm/%40types/d3-zoom@1.7.4", + "pkg:npm/%40types/geojson@7946.0.7", + "pkg:npm/%40types/prop-types@15.5.7", + "pkg:npm/%40types/react@16.7.13", + "pkg:npm/%40webassemblyjs/ast@1.7.8", + "pkg:npm/%40webassemblyjs/floating-point-hex-parser@1.7.8", + "pkg:npm/%40webassemblyjs/helper-api-error@1.7.8", + "pkg:npm/%40webassemblyjs/helper-buffer@1.7.8", + "pkg:npm/%40webassemblyjs/helper-code-frame@1.7.8", + "pkg:npm/%40webassemblyjs/helper-fsm@1.7.8", + "pkg:npm/%40webassemblyjs/helper-module-context@1.7.8", + "pkg:npm/%40webassemblyjs/helper-wasm-bytecode@1.7.8", + "pkg:npm/%40webassemblyjs/helper-wasm-section@1.7.8", + "pkg:npm/%40webassemblyjs/ieee754@1.7.8", + "pkg:npm/%40webassemblyjs/leb128@1.7.8", + "pkg:npm/%40webassemblyjs/utf8@1.7.8", + "pkg:npm/%40webassemblyjs/wasm-edit@1.7.8", + "pkg:npm/%40webassemblyjs/wasm-gen@1.7.8", + "pkg:npm/%40webassemblyjs/wasm-opt@1.7.8", + "pkg:npm/%40webassemblyjs/wasm-parser@1.7.8", + "pkg:npm/%40webassemblyjs/wast-parser@1.7.8", + "pkg:npm/%40webassemblyjs/wast-printer@1.7.8", + "pkg:npm/%40xtuc/ieee754@1.2.0", + "pkg:npm/%40xtuc/long@4.2.1", + "pkg:npm/abab@2.0.0", + "pkg:npm/abbrev@1.1.1", + "pkg:npm/acorn@5.7.3", + "pkg:npm/acorn-dynamic-import@3.0.0", + "pkg:npm/acorn-globals@4.3.2", + "pkg:npm/acorn-jsx@4.1.1", + "pkg:npm/acorn-walk@6.2.0", + "pkg:npm/ajv@6.5.4", + "pkg:npm/ajv-errors@1.0.1", + "pkg:npm/ajv-keywords@3.2.0", + "pkg:npm/amdefine@1.0.1", + "pkg:npm/ansi-colors@1.1.0", + "pkg:npm/ansi-cyan@0.1.1", + "pkg:npm/ansi-escapes@3.1.0", + "pkg:npm/ansi-gray@0.1.1", + "pkg:npm/ansi-red@0.1.1", + "pkg:npm/ansi-regex@2.1.1", + "pkg:npm/ansi-styles@2.2.1", + "pkg:npm/ansi-wrap@0.1.0", + "pkg:npm/anymatch@2.0.0", + "pkg:npm/aproba@1.2.0", + "pkg:npm/are-we-there-yet@1.1.5", + "pkg:npm/argparse@1.0.10", + "pkg:npm/arr-diff@4.0.0", + "pkg:npm/arr-flatten@1.1.0", + "pkg:npm/arr-union@3.1.0", + "pkg:npm/array-equal@1.0.0", + "pkg:npm/array-find-index@1.0.2", + "pkg:npm/array-includes@3.0.3", + "pkg:npm/array-slice@0.2.3", + "pkg:npm/array-union@1.0.2", + "pkg:npm/array-uniq@1.0.3", + "pkg:npm/array-unique@0.3.2", + "pkg:npm/arrify@1.0.1", + "pkg:npm/asap@2.0.6", + "pkg:npm/asn1@0.2.4", + "pkg:npm/asn1.js@4.10.1", + "pkg:npm/assert@1.4.1", + "pkg:npm/assert-plus@1.0.0", + "pkg:npm/assign-symbols@1.0.0", + "pkg:npm/async@2.6.1", + "pkg:npm/async-each@1.0.1", + "pkg:npm/async-foreach@0.1.3", + "pkg:npm/async-limiter@1.0.0", + "pkg:npm/asynckit@0.4.0", + "pkg:npm/atob@2.1.2", + "pkg:npm/audit-ci@1.7.0", + "pkg:npm/aws-sign2@0.7.0", + "pkg:npm/aws4@1.8.0", + "pkg:npm/babel-code-frame@6.26.0", + "pkg:npm/babel-core@6.26.3", + "pkg:npm/babel-eslint@9.0.0", + "pkg:npm/babel-generator@6.26.1", + "pkg:npm/babel-helper-builder-react-jsx@6.26.0", + "pkg:npm/babel-helper-call-delegate@6.24.1", + "pkg:npm/babel-helper-define-map@6.26.0", + "pkg:npm/babel-helper-function-name@6.24.1", + "pkg:npm/babel-helper-get-function-arity@6.24.1", + "pkg:npm/babel-helper-hoist-variables@6.24.1", + "pkg:npm/babel-helper-optimise-call-expression@6.24.1", + "pkg:npm/babel-helper-replace-supers@6.24.1", + "pkg:npm/babel-helpers@6.24.1", + "pkg:npm/babel-loader@8.0.4", + "pkg:npm/babel-messages@6.23.0", + "pkg:npm/babel-plugin-check-es2015-constants@6.22.0", + "pkg:npm/babel-plugin-emotion@9.2.11", + "pkg:npm/babel-plugin-macros@2.6.1", + "pkg:npm/babel-plugin-syntax-class-properties@6.13.0", + "pkg:npm/babel-plugin-syntax-flow@6.18.0", + "pkg:npm/babel-plugin-syntax-jsx@6.18.0", + "pkg:npm/babel-plugin-syntax-object-rest-spread@6.13.0", + "pkg:npm/babel-plugin-syntax-trailing-function-commas@6.22.0", + "pkg:npm/babel-plugin-transform-class-properties@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-arrow-functions@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-block-scoped-functions@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-block-scoping@6.26.0", + "pkg:npm/babel-plugin-transform-es2015-classes@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-computed-properties@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-destructuring@6.23.0", + "pkg:npm/babel-plugin-transform-es2015-for-of@6.23.0", + "pkg:npm/babel-plugin-transform-es2015-function-name@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-literals@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-modules-commonjs@6.26.2", + "pkg:npm/babel-plugin-transform-es2015-object-super@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-parameters@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-shorthand-properties@6.24.1", + "pkg:npm/babel-plugin-transform-es2015-spread@6.22.0", + "pkg:npm/babel-plugin-transform-es2015-template-literals@6.22.0", + "pkg:npm/babel-plugin-transform-es3-member-expression-literals@6.22.0", + "pkg:npm/babel-plugin-transform-es3-property-literals@6.22.0", + "pkg:npm/babel-plugin-transform-flow-strip-types@6.22.0", + "pkg:npm/babel-plugin-transform-object-rest-spread@6.26.0", + "pkg:npm/babel-plugin-transform-react-display-name@6.25.0", + "pkg:npm/babel-plugin-transform-react-jsx@6.24.1", + "pkg:npm/babel-plugin-transform-strict-mode@6.24.1", + "pkg:npm/babel-preset-fbjs@2.3.0", + "pkg:npm/babel-register@6.26.0", + "pkg:npm/babel-runtime@6.26.0", + "pkg:npm/babel-template@6.26.0", + "pkg:npm/babel-traverse@6.26.0", + "pkg:npm/babel-types@6.26.0", + "pkg:npm/babylon@6.18.0", + "pkg:npm/balanced-match@1.0.0", + "pkg:npm/base@0.11.2", + "pkg:npm/base64-js@1.3.0", + "pkg:npm/bcrypt-pbkdf@1.0.2", + "pkg:npm/big.js@3.2.0", + "pkg:npm/binary-extensions@1.12.0", + "pkg:npm/block-stream@0.0.9", + "pkg:npm/bluebird@3.5.2", + "pkg:npm/bn.js@4.11.8", + "pkg:npm/bootstrap@4.3.1", + "pkg:npm/bootstrap-datepicker@1.9.0", + "pkg:npm/bootstrap-sass@3.4.1", + "pkg:npm/bootstrap-select@1.12.2", + "pkg:npm/bootstrap-slider@9.10.0", + "pkg:npm/bootstrap-slider-without-jquery@10.0.0", + "pkg:npm/bootstrap-switch@3.3.4", + "pkg:npm/bootstrap-touchspin@3.1.1", + "pkg:npm/brace-expansion@1.1.11", + "pkg:npm/braces@2.3.2", + "pkg:npm/breakjs@1.0.0", + "pkg:npm/brorand@1.1.0", + "pkg:npm/browser-process-hrtime@0.1.3", + "pkg:npm/browserify-aes@1.2.0", + "pkg:npm/browserify-cipher@1.0.1", + "pkg:npm/browserify-des@1.0.2", + "pkg:npm/browserify-rsa@4.0.1", + "pkg:npm/browserify-sign@4.0.4", + "pkg:npm/browserify-zlib@0.2.0", + "pkg:npm/browserslist@4.3.3", + "pkg:npm/buffer@4.9.1", + "pkg:npm/buffer-from@1.1.1", + "pkg:npm/buffer-xor@1.0.3", + "pkg:npm/builtin-modules@1.1.1", + "pkg:npm/builtin-status-codes@3.0.0", + "pkg:npm/byline@5.0.0", + "pkg:npm/c3@0.4.23", + "pkg:npm/cacache@10.0.4", + "pkg:npm/cache-base@1.0.1", + "pkg:npm/caller-callsite@2.0.0", + "pkg:npm/caller-path@0.1.0", + "pkg:npm/callsites@0.2.0", + "pkg:npm/camel-case@3.0.0", + "pkg:npm/camelcase@2.1.1", + "pkg:npm/camelcase-keys@2.1.0", + "pkg:npm/caniuse-lite@1.0.30000898", + "pkg:npm/caseless@0.12.0", + "pkg:npm/chalk@1.1.3", + "pkg:npm/change-emitter@0.1.6", + "pkg:npm/chardet@0.7.0", + "pkg:npm/chokidar@2.0.4", + "pkg:npm/chownr@1.1.1", + "pkg:npm/chrome-remote-interface@0.25.7", + "pkg:npm/chrome-trace-event@1.0.0", + "pkg:npm/cipher-base@1.0.4", + "pkg:npm/circular-json@0.3.3", + "pkg:npm/class-utils@0.3.6", + "pkg:npm/classnames@2.2.6", + "pkg:npm/cli-cursor@2.1.0", + "pkg:npm/cli-width@2.2.0", + "pkg:npm/cliui@3.2.0", + "pkg:npm/clone-deep@2.0.2", + "pkg:npm/code-point-at@1.1.0", + "pkg:npm/collection-visit@1.0.0", + "pkg:npm/color-convert@1.9.3", + "pkg:npm/color-name@1.1.3", + "pkg:npm/color-support@1.1.3", + "pkg:npm/combined-stream@1.0.7", + "pkg:npm/commander@2.11.0", + "pkg:npm/commondir@1.0.1", + "pkg:npm/component-emitter@1.2.1", + "pkg:npm/compression-webpack-plugin@1.1.12", + "pkg:npm/concat-map@0.0.1", + "pkg:npm/concat-stream@1.6.2", + "pkg:npm/console-browserify@1.1.0", + "pkg:npm/console-control-strings@1.1.0", + "pkg:npm/constants-browserify@1.0.0", + "pkg:npm/contains-path@0.1.0", + "pkg:npm/convert-source-map@1.6.0", + "pkg:npm/copy-concurrently@1.0.5", + "pkg:npm/copy-descriptor@0.1.1", + "pkg:npm/copy-webpack-plugin@4.5.4", + "pkg:npm/core-js@2.6.0", + "pkg:npm/core-util-is@1.0.2", + "pkg:npm/cosmiconfig@5.2.1", + "pkg:npm/create-ecdh@4.0.3", + "pkg:npm/create-emotion@9.2.12", + "pkg:npm/create-emotion-server@9.2.12", + "pkg:npm/create-hash@1.2.0", + "pkg:npm/create-hmac@1.1.7", + "pkg:npm/create-react-context@0.2.3", + "pkg:npm/cross-spawn@3.0.1", + "pkg:npm/crypto-browserify@3.12.0", + "pkg:npm/css@2.2.4", + "pkg:npm/css-element-queries@1.2.0", + "pkg:npm/css-loader@2.1.1", + "pkg:npm/cssesc@3.0.0", + "pkg:npm/cssom@0.3.8", + "pkg:npm/cssstyle@0.3.1", + "pkg:npm/csstype@2.5.8", + "pkg:npm/currently-unhandled@0.4.1", + "pkg:npm/cyclist@0.2.2", + "pkg:npm/d3@3.5.17", + "pkg:npm/dashdash@1.14.1", + "pkg:npm/data-urls@1.1.0", + "pkg:npm/datatables.net@1.10.19", + "pkg:npm/datatables.net-bs@1.10.19", + "pkg:npm/datatables.net-colreorder@1.5.1", + "pkg:npm/datatables.net-colreorder-bs@1.3.3", + "pkg:npm/datatables.net-select@1.2.7", + "pkg:npm/date-now@0.1.4", + "pkg:npm/debug@3.2.6", + "pkg:npm/decamelize@1.2.0", + "pkg:npm/decode-uri-component@0.2.0", + "pkg:npm/deep-is@0.1.3", + "pkg:npm/define-properties@1.1.3", + "pkg:npm/define-property@2.0.2", + "pkg:npm/del@2.2.2", + "pkg:npm/delayed-stream@1.0.0", + "pkg:npm/delegates@1.0.0", + "pkg:npm/des.js@1.0.0", + "pkg:npm/detect-indent@4.0.0", + "pkg:npm/diffie-hellman@5.0.3", + "pkg:npm/dir-glob@2.0.0", + "pkg:npm/doctrine@2.1.0", + "pkg:npm/dom-helpers@3.4.0", + "pkg:npm/domain-browser@1.2.0", + "pkg:npm/domexception@1.0.1", + "pkg:npm/drmonty-datatables-colvis@1.1.2", + "pkg:npm/duplexer2@0.1.4", + "pkg:npm/duplexify@3.6.1", + "pkg:npm/ecc-jsbn@0.1.2", + "pkg:npm/electron-to-chromium@1.3.81", + "pkg:npm/elliptic@6.4.1", + "pkg:npm/emojis-list@2.1.0", + "pkg:npm/emotion@9.2.12", + "pkg:npm/emotion-server@9.2.12", + "pkg:npm/encoding@0.1.12", + "pkg:npm/end-of-stream@1.4.1", + "pkg:npm/enhanced-resolve@4.1.0", + "pkg:npm/eonasdan-bootstrap-datetimepicker@4.17.47", + "pkg:npm/errno@0.1.7", + "pkg:npm/error-ex@1.3.2", + "pkg:npm/es-abstract@1.12.0", + "pkg:npm/es-to-primitive@1.2.0", + "pkg:npm/escape-string-regexp@1.0.5", + "pkg:npm/escodegen@1.11.1", + "pkg:npm/eslint@5.7.0", + "pkg:npm/eslint-config-standard@11.0.0", + "pkg:npm/eslint-config-standard-jsx@5.0.0", + "pkg:npm/eslint-config-standard-react@6.0.0", + "pkg:npm/eslint-import-resolver-node@0.3.2", + "pkg:npm/eslint-loader@2.1.1", + "pkg:npm/eslint-module-utils@2.2.0", + "pkg:npm/eslint-plugin-es@1.3.1", + "pkg:npm/eslint-plugin-flowtype@2.50.3", + "pkg:npm/eslint-plugin-import@2.14.0", + "pkg:npm/eslint-plugin-node@7.0.1", + "pkg:npm/eslint-plugin-promise@4.0.1", + "pkg:npm/eslint-plugin-react@7.11.1", + "pkg:npm/eslint-plugin-standard@3.1.0", + "pkg:npm/eslint-scope@3.7.1", + "pkg:npm/eslint-utils@1.4.2", + "pkg:npm/eslint-visitor-keys@1.0.0", + "pkg:npm/espree@4.0.0", + "pkg:npm/esprima@4.0.1", + "pkg:npm/esquery@1.0.1", + "pkg:npm/esrecurse@4.2.1", + "pkg:npm/estraverse@4.2.0", + "pkg:npm/esutils@2.0.2", + "pkg:npm/events@1.1.1", + "pkg:npm/evp_bytestokey@1.0.3", + "pkg:npm/execa@0.10.0", + "pkg:npm/exenv@1.2.2", + "pkg:npm/expand-brackets@2.1.4", + "pkg:npm/extend@3.0.2", + "pkg:npm/extend-shallow@3.0.2", + "pkg:npm/external-editor@3.0.3", + "pkg:npm/extglob@2.0.4", + "pkg:npm/extract-text-webpack-plugin@4.0.0-beta.0", + "pkg:npm/extsprintf@1.3.0", + "pkg:npm/fancy-log@1.3.3", + "pkg:npm/fast-deep-equal@2.0.1", + "pkg:npm/fast-json-stable-stringify@2.0.0", + "pkg:npm/fast-levenshtein@2.0.6", + "pkg:npm/fbjs@0.8.17", + "pkg:npm/fbjs-scripts@0.8.3", + "pkg:npm/figures@2.0.0", + "pkg:npm/file-entry-cache@2.0.0", + "pkg:npm/file-loader@4.1.0", + "pkg:npm/fill-range@4.0.0", + "pkg:npm/find-cache-dir@1.0.0", + "pkg:npm/find-root@1.1.0", + "pkg:npm/find-up@1.1.2", + "pkg:npm/flat-cache@1.3.0", + "pkg:npm/flush-write-stream@1.0.3", + "pkg:npm/focus-trap@3.0.0", + "pkg:npm/focus-trap-react@4.0.1", + "pkg:npm/font-awesome@4.7.0", + "pkg:npm/font-awesome-sass@4.7.0", + "pkg:npm/for-in@1.0.2", + "pkg:npm/for-own@1.0.0", + "pkg:npm/forever-agent@0.6.1", + "pkg:npm/form-data@2.3.3", + "pkg:npm/fragment-cache@0.2.1", + "pkg:npm/from2@2.3.0", + "pkg:npm/fs-extra@6.0.1", + "pkg:npm/fs-write-stream-atomic@1.0.10", + "pkg:npm/fs.realpath@1.0.0", + "pkg:npm/fsevents@1.2.9", + "pkg:npm/fstream@1.0.12", + "pkg:npm/function-bind@1.1.1", + "pkg:npm/functional-red-black-tree@1.0.1", + "pkg:npm/gauge@2.7.4", + "pkg:npm/gaze@1.1.3", + "pkg:npm/get-caller-file@1.0.3", + "pkg:npm/get-stdin@4.0.1", + "pkg:npm/get-stream@3.0.0", + "pkg:npm/get-value@2.0.6", + "pkg:npm/getpass@0.1.7", + "pkg:npm/glob@7.1.3", + "pkg:npm/glob-parent@3.1.0", + "pkg:npm/global-modules-path@2.3.0", + "pkg:npm/globals@11.8.0", + "pkg:npm/globby@7.1.1", + "pkg:npm/globule@1.2.1", + "pkg:npm/google-code-prettify@1.0.5", + "pkg:npm/graceful-fs@4.1.11", + "pkg:npm/gud@1.0.0", + "pkg:npm/handlebars@4.5.2", + "pkg:npm/har-schema@2.0.0", + "pkg:npm/har-validator@5.1.3", + "pkg:npm/has@1.0.3", + "pkg:npm/has-ansi@2.0.0", + "pkg:npm/has-flag@3.0.0", + "pkg:npm/has-symbols@1.0.0", + "pkg:npm/has-unicode@2.0.1", + "pkg:npm/has-value@1.0.0", + "pkg:npm/has-values@1.0.0", + "pkg:npm/hash-base@3.0.4", + "pkg:npm/hash.js@1.1.5", + "pkg:npm/hmac-drbg@1.0.1", + "pkg:npm/hoist-non-react-statics@2.5.5", + "pkg:npm/home-or-tmp@2.0.0", + "pkg:npm/hosted-git-info@2.7.1", + "pkg:npm/html-encoding-sniffer@1.0.2", + "pkg:npm/html-tokenize@2.0.0", + "pkg:npm/htmlparser@1.7.7", + "pkg:npm/http-signature@1.2.0", + "pkg:npm/https-browserify@1.0.0", + "pkg:npm/iconv-lite@0.4.24", + "pkg:npm/icss-replace-symbols@1.1.0", + "pkg:npm/icss-utils@4.1.0", + "pkg:npm/ieee754@1.1.12", + "pkg:npm/iferr@0.1.5", + "pkg:npm/ignore@3.3.10", + "pkg:npm/import-fresh@2.0.0", + "pkg:npm/import-local@2.0.0", + "pkg:npm/imurmurhash@0.1.4", + "pkg:npm/in-publish@2.0.0", + "pkg:npm/indent-string@2.1.0", + "pkg:npm/indexes-of@1.0.1", + "pkg:npm/indexof@0.0.1", + "pkg:npm/inflight@1.0.6", + "pkg:npm/inherits@2.0.3", + "pkg:npm/inquirer@6.2.0", + "pkg:npm/interpret@1.1.0", + "pkg:npm/invariant@2.2.4", + "pkg:npm/invert-kv@1.0.0", + "pkg:npm/ip-regex@2.1.0", + "pkg:npm/is-accessor-descriptor@0.1.6", + "pkg:npm/is-arrayish@0.2.1", + "pkg:npm/is-binary-path@1.0.1", + "pkg:npm/is-buffer@1.1.6", + "pkg:npm/is-builtin-module@1.0.0", + "pkg:npm/is-callable@1.1.4", + "pkg:npm/is-data-descriptor@0.1.4", + "pkg:npm/is-date-object@1.0.1", + "pkg:npm/is-descriptor@0.1.6", + "pkg:npm/is-directory@0.3.1", + "pkg:npm/is-extendable@0.1.1", + "pkg:npm/is-extglob@2.1.1", + "pkg:npm/is-finite@1.0.2", + "pkg:npm/is-fullwidth-code-point@1.0.0", + "pkg:npm/is-glob@4.0.0", + "pkg:npm/is-number@3.0.0", + "pkg:npm/is-path-cwd@1.0.0", + "pkg:npm/is-path-in-cwd@1.0.1", + "pkg:npm/is-path-inside@1.0.1", + "pkg:npm/is-plain-object@2.0.4", + "pkg:npm/is-promise@2.1.0", + "pkg:npm/is-regex@1.0.4", + "pkg:npm/is-resolvable@1.1.0", + "pkg:npm/is-stream@1.1.0", + "pkg:npm/is-symbol@1.0.2", + "pkg:npm/is-typedarray@1.0.0", + "pkg:npm/is-utf8@0.2.1", + "pkg:npm/is-windows@1.0.2", + "pkg:npm/isarray@1.0.0", + "pkg:npm/isexe@2.0.0", + "pkg:npm/isobject@3.0.1", + "pkg:npm/isomorphic-fetch@2.2.1", + "pkg:npm/isstream@0.1.2", + "pkg:npm/jed@1.1.1", + "pkg:npm/jquery@3.4.1", + "pkg:npm/jquery-match-height@0.7.2", + "pkg:npm/js-base64@2.4.9", + "pkg:npm/js-levenshtein@1.1.4", + "pkg:npm/js-tokens@4.0.0", + "pkg:npm/js-yaml@3.13.1", + "pkg:npm/jsbn@0.1.1", + "pkg:npm/jsdom@15.1.1", + "pkg:npm/jsesc@2.5.1", + "pkg:npm/json-parse-better-errors@1.0.2", + "pkg:npm/json-schema@0.2.3", + "pkg:npm/json-schema-traverse@0.4.1", + "pkg:npm/json-stable-stringify-without-jsonify@1.0.1", + "pkg:npm/json-stringify-safe@5.0.1", + "pkg:npm/json5@0.5.1", + "pkg:npm/jsonfile@4.0.0", + "pkg:npm/jsprim@1.4.1", + "pkg:npm/jsx-ast-utils@2.0.1", + "pkg:npm/keycode@2.2.0", + "pkg:npm/kind-of@6.0.2", + "pkg:npm/lcid@1.0.0", + "pkg:npm/levn@0.3.0", + "pkg:npm/load-json-file@1.1.0", + "pkg:npm/loader-fs-cache@1.0.1", + "pkg:npm/loader-runner@2.3.1", + "pkg:npm/loader-utils@1.1.0", + "pkg:npm/locate-path@2.0.0", + "pkg:npm/lodash@4.17.14", + "pkg:npm/lodash.assign@4.2.0", + "pkg:npm/lodash.clonedeep@4.5.0", + "pkg:npm/lodash.debounce@4.0.8", + "pkg:npm/lodash.mergewith@4.6.2", + "pkg:npm/lodash.sortby@4.7.0", + "pkg:npm/lodash.tail@4.1.1", + "pkg:npm/loose-envify@1.4.0", + "pkg:npm/loud-rejection@1.6.0", + "pkg:npm/lower-case@1.1.4", + "pkg:npm/lru-cache@4.1.3", + "pkg:npm/make-dir@1.3.0", + "pkg:npm/map-age-cleaner@0.1.2", + "pkg:npm/map-cache@0.2.2", + "pkg:npm/map-obj@1.0.1", + "pkg:npm/map-visit@1.0.0", + "pkg:npm/md5.js@1.3.5", + "pkg:npm/mem@4.0.0", + "pkg:npm/memory-fs@0.4.1", + "pkg:npm/meow@3.7.0", + "pkg:npm/micromatch@3.1.10", + "pkg:npm/miller-rabin@4.0.1", + "pkg:npm/mime@2.4.4", + "pkg:npm/mime-db@1.37.0", + "pkg:npm/mime-types@2.1.21", + "pkg:npm/mimic-fn@1.2.0", + "pkg:npm/minimalistic-assert@1.0.1", + "pkg:npm/minimalistic-crypto-utils@1.0.1", + "pkg:npm/minimatch@3.0.4", + "pkg:npm/minimist@1.2.0", + "pkg:npm/mississippi@2.0.0", + "pkg:npm/mixin-deep@1.3.2", + "pkg:npm/mixin-object@2.0.1", + "pkg:npm/mkdirp@0.5.1", + "pkg:npm/moment@2.24.0", + "pkg:npm/moment-timezone@0.4.1", + "pkg:npm/move-concurrently@1.0.1", + "pkg:npm/ms@2.1.1", + "pkg:npm/multipipe@1.0.2", + "pkg:npm/mute-stream@0.0.7", + "pkg:npm/nan@2.11.1", + "pkg:npm/nanomatch@1.2.13", + "pkg:npm/natural-compare@1.4.0", + "pkg:npm/neo-async@2.6.0", + "pkg:npm/nice-try@1.0.5", + "pkg:npm/no-case@2.3.2", + "pkg:npm/node-fetch@1.7.3", + "pkg:npm/node-gyp@3.8.0", + "pkg:npm/node-libs-browser@2.1.0", + "pkg:npm/node-releases@1.0.0-alpha.15", + "pkg:npm/node-sass@4.11.0", + "pkg:npm/nopt@3.0.6", + "pkg:npm/normalize-package-data@2.4.0", + "pkg:npm/normalize-path@2.1.1", + "pkg:npm/npm-run-path@2.0.2", + "pkg:npm/npmlog@4.1.2", + "pkg:npm/number-is-nan@1.0.1", + "pkg:npm/nwsapi@2.1.4", + "pkg:npm/oauth-sign@0.9.0", + "pkg:npm/object-assign@4.1.1", + "pkg:npm/object-copy@0.1.0", + "pkg:npm/object-hash@1.3.0", + "pkg:npm/object-keys@1.0.12", + "pkg:npm/object-visit@1.0.1", + "pkg:npm/object.getownpropertydescriptors@2.0.3", + "pkg:npm/object.pick@1.3.0", + "pkg:npm/once@1.4.0", + "pkg:npm/onetime@2.0.1", + "pkg:npm/optimist@0.6.1", + "pkg:npm/optionator@0.8.2", + "pkg:npm/os-browserify@0.3.0", + "pkg:npm/os-homedir@1.0.2", + "pkg:npm/os-locale@1.4.0", + "pkg:npm/os-tmpdir@1.0.2", + "pkg:npm/osenv@0.1.5", + "pkg:npm/p-defer@1.0.0", + "pkg:npm/p-finally@1.0.0", + "pkg:npm/p-is-promise@1.1.0", + "pkg:npm/p-limit@1.3.0", + "pkg:npm/p-locate@2.0.0", + "pkg:npm/p-try@1.0.0", + "pkg:npm/pako@1.0.6", + "pkg:npm/parallel-transform@1.1.0", + "pkg:npm/parse-asn1@5.1.1", + "pkg:npm/parse-json@2.2.0", + "pkg:npm/parse-node-version@1.0.1", + "pkg:npm/parse5@5.1.0", + "pkg:npm/pascalcase@0.1.1", + "pkg:npm/path-browserify@0.0.0", + "pkg:npm/path-dirname@1.0.2", + "pkg:npm/path-exists@2.1.0", + "pkg:npm/path-is-absolute@1.0.1", + "pkg:npm/path-is-inside@1.0.2", + "pkg:npm/path-key@2.0.1", + "pkg:npm/path-parse@1.0.6", + "pkg:npm/path-type@1.1.0", + "pkg:npm/patternfly@3.59.3", + "pkg:npm/patternfly-bootstrap-combobox@1.1.7", + "pkg:npm/patternfly-bootstrap-treeview@2.1.8", + "pkg:npm/patternfly-react@2.34.3", + "pkg:npm/pbkdf2@3.0.17", + "pkg:npm/performance-now@0.2.0", + "pkg:npm/pify@2.3.0", + "pkg:npm/pinkie@2.0.4", + "pkg:npm/pinkie-promise@2.0.1", + "pkg:npm/pkg-dir@2.0.0", + "pkg:npm/plugin-error@0.1.2", + "pkg:npm/pluralize@7.0.0", + "pkg:npm/pn@1.1.0", + "pkg:npm/popper.js@1.15.0", + "pkg:npm/posix-character-classes@0.1.1", + "pkg:npm/postcss@7.0.16", + "pkg:npm/postcss-modules-extract-imports@2.0.0", + "pkg:npm/postcss-modules-local-by-default@2.0.6", + "pkg:npm/postcss-modules-scope@2.1.0", + "pkg:npm/postcss-modules-values@2.0.0", + "pkg:npm/postcss-selector-parser@6.0.2", + "pkg:npm/postcss-value-parser@3.3.1", + "pkg:npm/prelude-ls@1.1.2", + "pkg:npm/private@0.1.8", + "pkg:npm/process@0.11.10", + "pkg:npm/process-nextick-args@2.0.0", + "pkg:npm/progress@2.0.1", + "pkg:npm/promise@7.3.1", + "pkg:npm/promise-inflight@1.0.1", + "pkg:npm/prop-types@15.6.2", + "pkg:npm/prop-types-extra@1.1.0", + "pkg:npm/prr@1.0.1", + "pkg:npm/pseudomap@1.0.2", + "pkg:npm/psl@1.1.31", + "pkg:npm/public-encrypt@4.0.3", + "pkg:npm/pump@2.0.1", + "pkg:npm/pumpify@1.5.1", + "pkg:npm/punycode@1.4.1", + "pkg:npm/qs@6.5.2", + "pkg:npm/querystring@0.2.0", + "pkg:npm/querystring-es3@0.2.1", + "pkg:npm/raf@3.4.1", + "pkg:npm/randombytes@2.0.6", + "pkg:npm/randomfill@1.0.4", + "pkg:npm/react@16.6.1", + "pkg:npm/react-bootstrap@0.32.4", + "pkg:npm/react-bootstrap-switch@15.5.3", + "pkg:npm/react-bootstrap-typeahead@3.2.4", + "pkg:npm/react-c3js@0.1.20", + "pkg:npm/react-click-outside@3.0.1", + "pkg:npm/react-collapse@4.0.3", + "pkg:npm/react-debounce-input@3.2.0", + "pkg:npm/react-dom@16.6.1", + "pkg:npm/react-ellipsis-with-tooltip@1.0.8", + "pkg:npm/react-fontawesome@1.6.1", + "pkg:npm/react-is@16.6.3", + "pkg:npm/react-lifecycles-compat@3.0.4", + "pkg:npm/react-motion@0.5.2", + "pkg:npm/react-onclickoutside@6.7.1", + "pkg:npm/react-overlays@0.8.3", + "pkg:npm/react-popper@1.3.0", + "pkg:npm/react-prop-types@0.4.0", + "pkg:npm/react-switch@5.0.0", + "pkg:npm/react-transition-group@2.5.1", + "pkg:npm/reactabular-table@8.14.0", + "pkg:npm/read-pkg@1.1.0", + "pkg:npm/read-pkg-up@1.0.1", + "pkg:npm/readable-stream@2.3.6", + "pkg:npm/readdirp@2.2.1", + "pkg:npm/recompose@0.30.0", + "pkg:npm/redent@1.0.0", + "pkg:npm/regenerate@1.4.0", + "pkg:npm/regenerate-unicode-properties@7.0.0", + "pkg:npm/regenerator-runtime@0.12.1", + "pkg:npm/regenerator-transform@0.13.3", + "pkg:npm/regex-not@1.0.2", + "pkg:npm/regexpp@2.0.1", + "pkg:npm/regexpu-core@4.2.0", + "pkg:npm/regjsgen@0.4.0", + "pkg:npm/regjsparser@0.3.0", + "pkg:npm/relative@3.0.2", + "pkg:npm/remove-trailing-separator@1.1.0", + "pkg:npm/repeat-element@1.1.3", + "pkg:npm/repeat-string@1.6.1", + "pkg:npm/repeating@2.0.1", + "pkg:npm/request@2.88.0", + "pkg:npm/request-promise-core@1.1.2", + "pkg:npm/request-promise-native@1.0.7", + "pkg:npm/require-directory@2.1.1", + "pkg:npm/require-main-filename@1.0.1", + "pkg:npm/require-uncached@1.0.3", + "pkg:npm/resolve@1.8.1", + "pkg:npm/resolve-cwd@2.0.0", + "pkg:npm/resolve-from@1.0.1", + "pkg:npm/resolve-url@0.2.1", + "pkg:npm/restore-cursor@2.0.0", + "pkg:npm/ret@0.1.15", + "pkg:npm/rimraf@2.6.2", + "pkg:npm/ripemd160@2.0.2", + "pkg:npm/run-async@2.3.0", + "pkg:npm/run-queue@1.0.3", + "pkg:npm/rxjs@6.3.3", + "pkg:npm/safe-buffer@5.1.2", + "pkg:npm/safe-regex@1.1.0", + "pkg:npm/safer-buffer@2.1.2", + "pkg:npm/sass-graph@2.2.4", + "pkg:npm/sass-loader@7.1.0", + "pkg:npm/saxes@3.1.11", + "pkg:npm/scheduler@0.11.3", + "pkg:npm/schema-utils@0.4.7", + "pkg:npm/scss-tokenizer@0.2.3", + "pkg:npm/semver@5.6.0", + "pkg:npm/serialize-javascript@1.5.0", + "pkg:npm/set-blocking@2.0.0", + "pkg:npm/set-value@2.0.1", + "pkg:npm/setimmediate@1.0.5", + "pkg:npm/sha.js@2.4.11", + "pkg:npm/shallow-clone@1.0.0", + "pkg:npm/shebang-command@1.2.0", + "pkg:npm/shebang-regex@1.0.0", + "pkg:npm/signal-exit@3.0.2", + "pkg:npm/sizzle@2.3.3", + "pkg:npm/slash@1.0.0", + "pkg:npm/slice-ansi@1.0.0", + "pkg:npm/snapdragon@0.8.2", + "pkg:npm/snapdragon-node@2.1.1", + "pkg:npm/snapdragon-util@3.0.1", + "pkg:npm/sortabular@1.6.0", + "pkg:npm/source-list-map@2.0.1", + "pkg:npm/source-map@0.4.4", + "pkg:npm/source-map-resolve@0.5.2", + "pkg:npm/source-map-support@0.4.18", + "pkg:npm/source-map-url@0.4.0", + "pkg:npm/spdx-correct@3.0.2", + "pkg:npm/spdx-exceptions@2.2.0", + "pkg:npm/spdx-expression-parse@3.0.0", + "pkg:npm/spdx-license-ids@3.0.1", + "pkg:npm/split-string@3.1.0", + "pkg:npm/sprintf-js@1.0.3", + "pkg:npm/sshpk@1.16.0", + "pkg:npm/ssri@5.3.0", + "pkg:npm/static-extend@0.1.2", + "pkg:npm/stdio@0.2.7", + "pkg:npm/stdout-stream@1.4.1", + "pkg:npm/stealthy-require@1.1.1", + "pkg:npm/stream-browserify@2.0.1", + "pkg:npm/stream-each@1.2.3", + "pkg:npm/stream-http@2.8.3", + "pkg:npm/stream-shift@1.0.0", + "pkg:npm/string-width@1.0.2", + "pkg:npm/string_decoder@1.1.1", + "pkg:npm/strip-ansi@3.0.1", + "pkg:npm/strip-bom@2.0.0", + "pkg:npm/strip-eof@1.0.0", + "pkg:npm/strip-indent@1.0.1", + "pkg:npm/strip-json-comments@2.0.1", + "pkg:npm/style-loader@0.23.1", + "pkg:npm/stylis@3.5.4", + "pkg:npm/stylis-rule-sheet@0.0.10", + "pkg:npm/supports-color@2.0.0", + "pkg:npm/symbol-observable@1.2.0", + "pkg:npm/symbol-tree@3.2.4", + "pkg:npm/tabbable@3.1.2", + "pkg:npm/table@5.1.0", + "pkg:npm/table-resolver@4.1.1", + "pkg:npm/tapable@1.1.0", + "pkg:npm/tar@2.2.2", + "pkg:npm/text-table@0.2.0", + "pkg:npm/through@2.3.8", + "pkg:npm/through2@2.0.3", + "pkg:npm/time-stamp@1.1.0", + "pkg:npm/timers-browserify@2.0.10", + "pkg:npm/tippy.js@3.4.1", + "pkg:npm/tmp@0.0.33", + "pkg:npm/to-arraybuffer@1.0.1", + "pkg:npm/to-fast-properties@2.0.0", + "pkg:npm/to-object-path@0.3.0", + "pkg:npm/to-regex@3.0.2", + "pkg:npm/to-regex-range@2.1.1", + "pkg:npm/touch@2.0.2", + "pkg:npm/tough-cookie@2.4.3", + "pkg:npm/tr46@1.0.1", + "pkg:npm/trim-newlines@1.0.0", + "pkg:npm/trim-right@1.0.1", + "pkg:npm/true-case-path@1.0.3", + "pkg:npm/tslib@1.9.3", + "pkg:npm/tty-browserify@0.0.0", + "pkg:npm/tunnel-agent@0.6.0", + "pkg:npm/tweetnacl@0.14.5", + "pkg:npm/type-check@0.3.2", + "pkg:npm/typed-styles@0.0.5", + "pkg:npm/typedarray@0.0.6", + "pkg:npm/typescript@3.4.5", + "pkg:npm/ua-parser-js@0.7.19", + "pkg:npm/uglify-es@3.3.9", + "pkg:npm/uglify-js@3.6.9", + "pkg:npm/uglifyjs-webpack-plugin@1.3.0", + "pkg:npm/ultron@1.1.1", + "pkg:npm/uncontrollable@5.1.0", + "pkg:npm/unicode-canonical-property-names-ecmascript@1.0.4", + "pkg:npm/unicode-match-property-ecmascript@1.0.4", + "pkg:npm/unicode-match-property-value-ecmascript@1.0.2", + "pkg:npm/unicode-property-aliases-ecmascript@1.0.4", + "pkg:npm/union-value@1.0.1", + "pkg:npm/uniq@1.0.1", + "pkg:npm/unique-filename@1.1.1", + "pkg:npm/unique-slug@2.0.1", + "pkg:npm/universalify@0.1.2", + "pkg:npm/unset-value@1.0.0", + "pkg:npm/upath@1.1.0", + "pkg:npm/upper-case@1.1.3", + "pkg:npm/uri-js@4.2.2", + "pkg:npm/urix@0.1.0", + "pkg:npm/url@0.11.0", + "pkg:npm/url-loader@2.1.0", + "pkg:npm/use@3.1.1", + "pkg:npm/util@0.10.4", + "pkg:npm/util-deprecate@1.0.2", + "pkg:npm/util.promisify@1.0.0", + "pkg:npm/uuid@3.3.2", + "pkg:npm/v8-compile-cache@2.0.2", + "pkg:npm/validate-npm-package-license@3.0.4", + "pkg:npm/verror@1.10.0", + "pkg:npm/vm-browserify@0.0.4", + "pkg:npm/w3c-hr-time@1.0.1", + "pkg:npm/w3c-xmlserializer@1.1.2", + "pkg:npm/warning@3.0.0", + "pkg:npm/watchpack@1.6.0", + "pkg:npm/webidl-conversions@4.0.2", + "pkg:npm/webpack@4.22.0", + "pkg:npm/webpack-cli@3.1.2", + "pkg:npm/webpack-sources@1.3.0", + "pkg:npm/whatwg-encoding@1.0.5", + "pkg:npm/whatwg-fetch@3.0.0", + "pkg:npm/whatwg-mimetype@2.3.0", + "pkg:npm/whatwg-url@7.0.0", + "pkg:npm/which@1.3.1", + "pkg:npm/which-module@1.0.0", + "pkg:npm/wide-align@1.1.3", + "pkg:npm/wordwrap@1.0.0", + "pkg:npm/worker-farm@1.6.0", + "pkg:npm/wrap-ansi@2.1.0", + "pkg:npm/wrappy@1.0.2", + "pkg:npm/write@0.2.1", + "pkg:npm/ws@3.3.3", + "pkg:npm/xml-name-validator@3.0.0", + "pkg:npm/xmlchars@2.1.1", + "pkg:npm/xregexp@4.0.0", + "pkg:npm/xtend@4.0.1", + "pkg:npm/y18n@3.2.1", + "pkg:npm/yallist@2.1.2", + "pkg:npm/yargs@7.1.0", + "pkg:npm/yargs-parser@5.0.0" + ] +} diff --git a/ci/tools/openeuler-purl/purl.json.tmpl b/ci/tools/openeuler-purl/purl.json.tmpl new file mode 100644 index 0000000000000000000000000000000000000000..bbc7fb067e9b2795256e48ff639edf0f531f80fa --- /dev/null +++ b/ci/tools/openeuler-purl/purl.json.tmpl @@ -0,0 +1,10 @@ +{ + "name": "{{.Source.Target | osBase}}", + "purls": [ + {{- $artifactLength := len .Artifacts -}} + {{- range $index, $value := .Artifacts}} + {{$pos := add $index 1 -}} + "{{$value.PURL -}}"{{if lt $pos $artifactLength}},{{else}}{{break}}{{end}} + {{- end}} + ] +} diff --git a/ci/tools/openeuler-purl/requirements.txt b/ci/tools/openeuler-purl/requirements.txt new file mode 100644 index 0000000000000000000000000000000000000000..c7cea64ca3083ccf11c67b77a671ad6093a5546d --- /dev/null +++ b/ci/tools/openeuler-purl/requirements.txt @@ -0,0 +1,31 @@ +aiodns==3.0.0 +aiofiles==0.8.0 +aiohttp==3.8.1 +aiohttp-retry==2.8.3 +aiosignal==1.2.0 +async-retrying==0.2.2 +async-timeout==4.0.2 +attrs==22.1.0 +beautifulsoup4==4.11.1 +cchardet==2.1.7 +certifi==2022.6.15 +cffi==1.15.1 +charset-normalizer==2.1.0 +colorama==0.4.5 +decorator==5.1.1 +frozenlist==1.3.1 +idna==3.3 +loguru==0.6.0 +multidict==6.0.2 +py==1.11.0 +pycares==4.2.1 +pycparser==2.21 +python-utils==3.3.3 +requests==2.28.1 +retry==0.9.2 +six==1.16.0 +soupsieve==2.3.2.post1 +tqdm==4.64.0 +urllib3==1.26.11 +win32-setctime==1.1.0 +yarl==1.8.1 diff --git a/ci/tools/openeuler-purl/syft-dev/.bouncer.yaml b/ci/tools/openeuler-purl/syft-dev/.bouncer.yaml new file mode 100644 index 0000000000000000000000000000000000000000..fe3f9713f14de7c9e5d72f3bf7b4c7384eb46cbc --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.bouncer.yaml @@ -0,0 +1,57 @@ +permit: + - BSD.* + - CC0.* + - MIT.* + - Apache.* + - MPL.* + - ISC + - WTFPL + +ignore-packages: + # packageurl-go is released under the MIT license located in the root of the repo at /mit.LICENSE + - github.com/anchore/packageurl-go + + # crypto/internal/boring is released under the openSSL license as a part of the Golang Standard Libary + - crypto/internal/boring + + # from: https://github.com/spdx/tools-golang/blob/main/LICENSE.code + # The tools-golang source code is provided and may be used, at your option, + # under either: + # * Apache License, version 2.0 (Apache-2.0), OR + # * GNU General Public License, version 2.0 or later (GPL-2.0-or-later). + # (we choose Apache-2.0) + - github.com/spdx/tools-golang + + # from: https://github.com/xi2/xz/blob/master/LICENSE + # All these files have been put into the public domain. + # You can do whatever you want with these files. + - github.com/xi2/xz + + # from: https://gitlab.com/cznic/sqlite/-/blob/v1.15.4/LICENSE + # This is a BSD-3-Clause license + - modernc.org/libc + - modernc.org/libc/errno + - modernc.org/libc/fcntl + - modernc.org/libc/fts + - modernc.org/libc/grp + - modernc.org/libc/langinfo + - modernc.org/libc/limits + - modernc.org/libc/netdb + - modernc.org/libc/netinet/in + - modernc.org/libc/poll + - modernc.org/libc/pthread + - modernc.org/libc/pwd + - modernc.org/libc/signal + - modernc.org/libc/stdio + - modernc.org/libc/stdlib + - modernc.org/libc/sys/socket + - modernc.org/libc/sys/stat + - modernc.org/libc/sys/types + - modernc.org/libc/termios + - modernc.org/libc/time + - modernc.org/libc/unistd + - modernc.org/libc/utime + - modernc.org/libc/uuid/uuid + - modernc.org/libc/wctype + - modernc.org/mathutil + - modernc.org/memory diff --git a/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/bug_report.md b/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/bug_report.md new file mode 100644 index 0000000000000000000000000000000000000000..85918aa1abc3ef32f8f190a56450438ff996c567 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/bug_report.md @@ -0,0 +1,20 @@ +--- +name: Bug report +about: Create a report to help us improve +title: '' +labels: bug +assignees: '' + +--- + +**What happened**: + +**What you expected to happen**: + +**How to reproduce it (as minimally and precisely as possible)**: + +**Anything else we need to know?**: + +**Environment**: +- Output of `syft version`: +- OS (e.g: `cat /etc/os-release` or similar): diff --git a/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/config.yml b/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/config.yml new file mode 100644 index 0000000000000000000000000000000000000000..edd71d50485a04996552d2bad9044799e16272cd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/config.yml @@ -0,0 +1,6 @@ +contact_links: + + - name: Join the Slack community 💬 + # link to our community Slack registration page + url: https://anchore.com/slack + about: 'Come chat with us! Ask for help, join our software development efforts, or just give us feedback!' diff --git a/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/feature_request.md b/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/feature_request.md new file mode 100644 index 0000000000000000000000000000000000000000..d07c5f15113ab17e74dcd9330d0cfb11aaca29d7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/ISSUE_TEMPLATE/feature_request.md @@ -0,0 +1,15 @@ +--- +name: Feature request +about: Suggest an idea for this project +title: '' +labels: enhancement +assignees: '' + +--- + +**What would you like to be added**: + +**Why is this needed**: + +**Additional context**: + diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/.gitignore b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..301ab6fe60e428c9ef2eb2ab4418308ea3f0aa95 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/.gitignore @@ -0,0 +1,3 @@ +dev-pki +log +signing-identity.txt diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/cleanup.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/cleanup.sh new file mode 100755 index 0000000000000000000000000000000000000000..80b1beba4d2465cf6b5b5a056091a00f373415f8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/cleanup.sh @@ -0,0 +1,11 @@ +#!/usr/bin/env bash +set -eu + +# grab utilities +SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd ) +. "$SCRIPT_DIR"/utils.sh + +# cleanup any dev certs left behind +. "$SCRIPT_DIR"/setup-import-cert.sh # defines KEYCHAIN_NAME and KEYCHAIN_PATH +. "$SCRIPT_DIR"/setup-dev.sh +cleanup_dev_signing diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/notarize.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/notarize.sh new file mode 100755 index 0000000000000000000000000000000000000000..0df1d96f0d569c0ca67eed4b5400495bca0f94b6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/notarize.sh @@ -0,0 +1,53 @@ +#!/usr/bin/env bash + +set +xu +if [ -z "$AC_USERNAME" ]; then + exit_with_error "AC_USERNAME not set" +fi + +if [ -z "$AC_PASSWORD" ]; then + exit_with_error "AC_PASSWORD not set" +fi +set -u + + +# notarize [archive-path] +# +notarize() { + binary_path=$1 + archive_path=${binary_path}-archive-for-notarization.zip + + title "archiving release binary into ${archive_path}" + + parent=$(dirname "$binary_path") + ( + cd "${parent}" && zip "${archive_path}" "$(basename ${binary_path})" + ) + + if [ ! -f "$archive_path" ]; then + exit_with_error "cannot find payload for notarization: $archive_path" + fi + + # install gon + which gon || (go install github.com/mitchellh/gon/cmd/gon@latest) + + # create config (note: json via stdin with gon is broken, can only use HCL from file) + hcl_file=$(mktemp).hcl + + cat < "$hcl_file" +notarize { + path = "$archive_path" + bundle_id = "com.anchore.toolbox.syft" +} + +apple_id { + username = "$AC_USERNAME" + password = "@env:AC_PASSWORD" +} +EOF + + gon -log-level info "$hcl_file" + + rm "${hcl_file}" "${archive_path}" +} + diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-dev.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-dev.sh new file mode 100755 index 0000000000000000000000000000000000000000..bfc0fe8c747cf2ccf3d080160b4c984db7e15a9f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-dev.sh @@ -0,0 +1,128 @@ +#!/usr/bin/env bash +set -eu + +NAME=syft-dev +SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd ) +DIR=$SCRIPT_DIR/dev-pki +FILE_PREFIX=$DIR/$NAME +IDENTITY=${NAME}-id-415d8c69793 + +## OpenSSL material + +KEY_PASSWORD="letthedevin" +P12_PASSWORD="popeofnope" + +KEY_FILE=$FILE_PREFIX-key.pem +CSR_FILE=$FILE_PREFIX-csr.pem +CERT_FILE=$FILE_PREFIX-cert.pem +EXT_FILE=$FILE_PREFIX-ext.cnf +P12_FILE=$FILE_PREFIX.p12 + +EXT_SECTION=codesign_reqext + +# setup_signing +# +# preps the MAC_SIGNING_IDENTITY env var for use in the signing process, using ephemeral developer certificate material +# +function setup_signing() { + # check to see if this has already been done... if so, bail! + set +ue + if security find-identity -p codesigning "$KEYCHAIN_PATH" | grep $IDENTITY ; then + export MAC_SIGNING_IDENTITY=$IDENTITY + commentary "skipping creating dev certificate material (already exists)" + commentary "setting MAC_SIGNING_IDENTITY=${IDENTITY}" + return 0 + fi + set -ue + + title "setting up developer certificate material" + + mkdir -p "${DIR}" + + # configure the openssl extensions + cat << EOF > "$EXT_FILE" + [ req ] + default_bits = 2048 # RSA key size + encrypt_key = yes # Protect private key + default_md = sha256 # MD to use + utf8 = yes # Input is UTF-8 + string_mask = utf8only # Emit UTF-8 strings + prompt = yes # Prompt for DN + distinguished_name = codesign_dn # DN template + req_extensions = $EXT_SECTION # Desired extensions + + [ codesign_dn ] + commonName = $IDENTITY + commonName_max = 64 + + [ $EXT_SECTION ] + keyUsage = critical,digitalSignature + extendedKeyUsage = critical,codeSigning + subjectKeyIdentifier = hash +EOF + + title "create the private key" + openssl genrsa \ + -des3 \ + -out "$KEY_FILE" \ + -passout "pass:$KEY_PASSWORD" \ + 2048 + + title "create the csr" + openssl req \ + -new \ + -key "$KEY_FILE" \ + -out "$CSR_FILE" \ + -passin "pass:$KEY_PASSWORD" \ + -config "$EXT_FILE" \ + -subj "/CN=$IDENTITY" + + commentary "verify the csr: we should see X509 v3 extensions for codesigning in the CSR" + openssl req -in "$CSR_FILE" -noout -text | grep -A1 "X509v3" || exit_with_error "could not find x509 extensions in CSR" + + title "create the certificate" + # note: Extensions in certificates are not transferred to certificate requests and vice versa. This means that + # just because the CSR has x509 v3 extensions doesn't mean that you'll see these extensions in the cert output. + # To prove this do: + # openssl x509 -text -noout -in server.crt | grep -A10 "X509v3 extensions:" + # ... and you will see no output (if -extensions is not used). (see https://www.openssl.org/docs/man1.1.0/man1/x509.html#BUGS) + # To get the extensions, use "-extensions codesign_reqext" when creating the cert. The codesign_reqext value matches + # the section name in the ext file used in CSR / cert creation (-extfile and -config). + openssl x509 \ + -req \ + -days 10000 \ + -in "$CSR_FILE" \ + -signkey "$KEY_FILE" \ + -out "$CERT_FILE" \ + -extfile "$EXT_FILE" \ + -passin "pass:$KEY_PASSWORD" \ + -extensions $EXT_SECTION + + commentary "verify the certificate: we should see our extensions" + openssl x509 -text -noout -in "$CERT_FILE" | grep -A1 'X509v3' || exit_with_error "could not find x509 extensions in certificate" + + title "export cert and private key to .p12 file" + # note: this step may be entirely optional, however, I found it useful to follow the prod path which goes the route of using a p12 + openssl pkcs12 \ + -export \ + -out "$P12_FILE" \ + -inkey "$KEY_FILE" \ + -in "$CERT_FILE" \ + -passin "pass:$KEY_PASSWORD" \ + -passout "pass:$P12_PASSWORD" + + # delete the keychain if it already exists + if [ -f "${KEYCHAIN_PATH}" ]; then + cleanup_dev_signing + fi + + import_signing_certificate "$P12_FILE" "$P12_PASSWORD" "$IDENTITY" +} + +function cleanup_dev_signing() { + title "delete the dev keychain and all certificate material" + set -xue + security delete-keychain "$KEYCHAIN_NAME" || true + rm -f "$KEYCHAIN_PATH" || true + rm -rf "${DIR}" || true +} diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-import-cert.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-import-cert.sh new file mode 100755 index 0000000000000000000000000000000000000000..518e88b1115c4ed2e80b0fd231e871adc03b9c78 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-import-cert.sh @@ -0,0 +1,55 @@ +#!/usr/bin/env bash +set -eu + +KEYCHAIN_NAME="syft-ephemeral-keychain" +KEYCHAIN_PATH="$HOME/Library/Keychains/${KEYCHAIN_NAME}-db" + +# import_signing_certificate +# +# imports a cert from a p12 file into a keychain used for codesigning +# +function import_signing_certificate() { + p12_file=$1 + p12_password=$2 + identity=$3 + + keychain_password="$(openssl rand -base64 100)" + + title "create the a new keychain" + + security create-keychain -p "$keychain_password" "$KEYCHAIN_NAME" + security set-keychain-settings -lut 21600 "$KEYCHAIN_PATH" + security unlock-keychain -p "$keychain_password" "$KEYCHAIN_PATH" + + if [ ! -f "$KEYCHAIN_PATH" ]; then + exit_with_error "cannot find keychain '$KEYCHAIN_PATH'" + fi + + set +e + if ! security verify-cert -k "$KEYCHAIN_PATH" -c "$p12_file" &> /dev/null; then + set -e + title "import the cert into the new keychain if it is not already trusted by the system" + + # '-t cert' is vital since it side-steps the need for user interaction with "security add-trusted-cert" (which has wider security implications) + security import "$p12_file" -P "$p12_password" -t cert -f pkcs12 -k "$KEYCHAIN_PATH" -T /usr/bin/codesign + + # note: set the partition list for this certificate's private key to include "apple-tool:" and "apple:" allows the codesign command to access this keychain item without an interactive user prompt. + security set-key-partition-list -S "apple-tool:,apple:,codesign:" -s -k "$keychain_password" "$KEYCHAIN_PATH" + else + set -e + commentary "...cert has already been imported onto the new keychain" + fi + + commentary "make certain there are identities that can be used for code signing" + security find-identity -p codesigning "$KEYCHAIN_PATH" | grep -C 30 "$identity" || exit_with_error "could not find identity that can be used with codesign" + + title "add the new keychain to the search path for codesign" + add_keychain "$KEYCHAIN_NAME" + + commentary "verify the new keychain can be found by the security sub-system" + security list-keychains | grep "$KEYCHAIN_NAME" || exit_with_error "could not find new keychain" + + export MAC_SIGNING_IDENTITY=$identity + commentary "setting MAC_SIGNING_IDENTITY=${identity}" + +} diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-prod.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-prod.sh new file mode 100755 index 0000000000000000000000000000000000000000..8a9c2853945b1bc6c2e6cb84a09fdb59309d48f5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup-prod.sh @@ -0,0 +1,32 @@ +#!/usr/bin/env bash +set -eu + +assert_in_ci + +IDENTITY="Developer ID Application: ANCHORE, INC. (9MJHKYX5AT)" + +set +xu +if [ -z "$APPLE_DEVELOPER_ID_CERT" ]; then + exit_with_error "APPLE_DEVELOPER_ID_CERT not set" +fi + +if [ -z "$APPLE_DEVELOPER_ID_CERT_PASS" ]; then + exit_with_error "APPLE_DEVELOPER_ID_CERT_PASS not set" +fi + +# setup_signing +# +# preps the MAC_SIGNING_IDENTITY env var for use in the signing process, using production certificate material +# +setup_signing() { + title "setting up production certificate material" + + # Write signing certificate to disk from environment variable. + p12_file="$HOME/developer_id_certificate.p12" + echo -n "$APPLE_DEVELOPER_ID_CERT" | base64 --decode > "$p12_file" + + import_signing_certificate "$p12_file" "$APPLE_DEVELOPER_ID_CERT_PASS" "$IDENTITY" + + # Make this new keychain the user's default keychain, so that codesign will be able to find this certificate when we specify it during signing. + security default-keychain -d "user" -s "${KEYCHAIN_PATH}" +} diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup.sh new file mode 100755 index 0000000000000000000000000000000000000000..937e037b08e9df758c022885e24d3dc1c60a68fb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/setup.sh @@ -0,0 +1,48 @@ +#!/usr/bin/env bash +set -eu -o pipefail + +IS_SNAPSHOT="$1" + +## grab utilities +SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd ) +. "$SCRIPT_DIR"/utils.sh +mkdir -p "$SCRIPT_DIR/log" + +main() { + # defines KEYCHAIN_NAME and KEYCHAIN_PATH + . "$SCRIPT_DIR"/setup-import-cert.sh + + case "$IS_SNAPSHOT" in + + "1" | "true" | "yes") + commentary "assuming development setup..." + . "$SCRIPT_DIR"/setup-dev.sh + ;; + + "0" | "false" | "no") + commentary "assuming production setup..." + . "$SCRIPT_DIR"/setup-prod.sh + ;; + + *) + exit_with_error "could not determine if this was a production build (isSnapshot='$IS_SNAPSHOT')" + ;; + esac + + # load up all signing material into a keychain (note: this should set the MAC_SIGNING_IDENTITY env var) + setup_signing + + # write out identity to a file + echo -n "$MAC_SIGNING_IDENTITY" > "$SCRIPT_DIR/$SIGNING_IDENTITY_FILENAME" +} + +# capture all output from a subshell to log output additionally to a file (as well as the terminal) +( ( + set +u + if [ -n "$SKIP_SIGNING" ]; then + commentary "skipping signing setup..." + else + set -u + main + fi +) 2>&1) | tee "$SCRIPT_DIR/log/setup.txt" \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/sign.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/sign.sh new file mode 100755 index 0000000000000000000000000000000000000000..3838394b975a9b458a75768942f757c4f1a8627f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/sign.sh @@ -0,0 +1,98 @@ +#!/usr/bin/env bash +set -eu -o pipefail + +BINARY_PATH="$1" +IS_SNAPSHOT="$2" +TARGET_NAME="$3" + +## grab utilities +SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd ) +. "$SCRIPT_DIR"/utils.sh +mkdir -p "$SCRIPT_DIR/log" + + +# sign_binary [binary-path] [signing-identity] +# +# signs a single binary with cosign +# +sign_binary() { + exe_path=$1 + identity=$2 + + if [ -x "$exe_path" ] && file -b "$exe_path" | grep -q "Mach-O" + then + echo "signing $exe_path ..." + else + echo "skip signing $exe_path ..." + return 0 + fi + + set -x + + codesign \ + -s "$identity" \ + -f \ + --verbose=4 \ + --timestamp \ + --options runtime \ + "$exe_path" + + if [ $? -ne 0 ]; then + exit_with_error "signing failed" + fi + + codesign --verify "$exe_path" --verbose=4 + + set +x +} + + +main() { + binary_abs_path=$(realpath "$BINARY_PATH") + + if [ ! -f "$binary_abs_path" ]; then + echo "archive does not exist: $binary_abs_path" + fi + + case "$IS_SNAPSHOT" in + + "1" | "true" | "yes") + commentary "disabling notarization..." + perform_notarization=false + ;; + + "0" | "false" | "no") + commentary "enabling notarization..." + . "$SCRIPT_DIR"/notarize.sh + perform_notarization=true + ;; + + *) + exit_with_error "could not determine if this was a production build (isSnapshot='$IS_SNAPSHOT')" + ;; + esac + + # grab the signing identity from the local temp file (setup by setup.sh) + MAC_SIGNING_IDENTITY=$(cat "$SCRIPT_DIR/$SIGNING_IDENTITY_FILENAME") + + # sign all of the binaries in the archive and recreate the input archive with the signed binaries + sign_binary "$binary_abs_path" "$MAC_SIGNING_IDENTITY" + + # send all of the binaries off to apple to bless + if $perform_notarization ; then + notarize "$binary_abs_path" + else + commentary "skipping notarization..." + fi +} + +# capture all output from a subshell to log output additionally to a file (as well as the terminal) +( ( + set +u + if [ -n "$SKIP_SIGNING" ]; then + commentary "skipping signing..." + else + set -u + main + fi +) 2>&1) | tee "$SCRIPT_DIR/log/signing-$(basename $BINARY_PATH)-$TARGET_NAME.txt" \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/utils.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/utils.sh new file mode 100644 index 0000000000000000000000000000000000000000..8e798df0d01086515ed7d2a9b0655ce84d9e9886 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/apple-signing/utils.sh @@ -0,0 +1,78 @@ +SIGNING_IDENTITY_FILENAME=signing-identity.txt + +## terminal goodies +PURPLE='\033[0;35m' +GREEN='\033[0;32m' +RED='\033[0;31m' +BOLD=$(tput -T linux bold) +RESET='\033[0m' + +function success() { + echo -e "\n${GREEN}${BOLD}$@${RESET}" +} + +function title() { + success "Task: $@" +} + +function commentary() { + echo -e "\n${PURPLE}# $@${RESET}" +} + +function error() { + echo -e "${RED}${BOLD}error: $@${RESET}" +} + +function exit_with_error() { + error $@ + exit 1 +} + +function exit_with_message() { + success $@ + exit 0 +} + +function realpath { + echo "$(cd $(dirname $1); pwd)/$(basename $1)"; +} + + +# this function adds all of the existing keychains plus the new one which is the same as going to Keychain Access +# and selecting "Add Keychain" to make the keychain visible under "Custom Keychains". This is done with +# "security list-keychains -s" for some reason. The downside is that this sets the search path, not appends +# to it, so you will loose existing keychains in the search path... which is truly terrible. +function add_keychain() { + keychains=$(security list-keychains -d user) + keychainNames=(); + for keychain in $keychains + do + basename=$(basename "$keychain") + keychainName=${basename::${#basename}-4} + keychainNames+=("$keychainName") + done + + echo "existing user keychains: ${keychainNames[@]}" + + security -v list-keychains -s "${keychainNames[@]}" "$1" +} + +function exit_not_ci() { + printf "WARNING! It looks like this isn't the CI environment. This script modifies the macOS Keychain setup in ways you probably wouldn't want for your own machine. It also requires an Apple Developer ID Certificate that you shouldn't have outside of the CI environment.\n\nExiting early to make sure nothing bad happens.\n" + exit 1 +} + +CI_HOME="/Users/runner" + +function assert_in_ci() { + + if [[ "${HOME}" != "${CI_HOME}" ]]; then + exit_not_ci + fi + + set +u + if [ -z "${GITHUB_ACTIONS}" ]; then + exit_not_ci + fi + set -u +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/go-mod-tidy-check.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/go-mod-tidy-check.sh new file mode 100755 index 0000000000000000000000000000000000000000..41bc63910bb429733d0f1854eb574106cbe56e5a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/go-mod-tidy-check.sh @@ -0,0 +1,31 @@ +#!/usr/bin/env bash +set -eu + +ORIGINAL_STATE_DIR=$(mktemp -d "TEMP-original-state-XXXXXXXXX") +TIDY_STATE_DIR=$(mktemp -d "TEMP-tidy-state-XXXXXXXXX") + +trap "cp -v ${ORIGINAL_STATE_DIR}/* ./ && rm -fR ${ORIGINAL_STATE_DIR} ${TIDY_STATE_DIR}" EXIT + +echo "Capturing original state of files..." +cp -v go.mod go.sum "${ORIGINAL_STATE_DIR}" + +echo "Capturing state of go.mod and go.sum after running go mod tidy..." +go mod tidy +cp -v go.mod go.sum "${TIDY_STATE_DIR}" +echo "" + +set +e + +# Detect difference between the git HEAD state and the go mod tidy state +DIFF_MOD=$(diff -u "${ORIGINAL_STATE_DIR}/go.mod" "${TIDY_STATE_DIR}/go.mod") +DIFF_SUM=$(diff -u "${ORIGINAL_STATE_DIR}/go.sum" "${TIDY_STATE_DIR}/go.sum") + +if [[ -n "${DIFF_MOD}" || -n "${DIFF_SUM}" ]]; then + echo "go.mod diff:" + echo "${DIFF_MOD}" + echo "go.sum diff:" + echo "${DIFF_SUM}" + echo "" + printf "FAILED! go.mod and/or go.sum are NOT tidy; please run 'go mod tidy'.\n\n" + exit 1 +fi diff --git a/ci/tools/openeuler-purl/syft-dev/.github/scripts/goreleaser-install.sh b/ci/tools/openeuler-purl/syft-dev/.github/scripts/goreleaser-install.sh new file mode 100755 index 0000000000000000000000000000000000000000..ac990bf8200892524d8117ec3383c647c910c319 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/scripts/goreleaser-install.sh @@ -0,0 +1,398 @@ +#!/bin/sh +set -e +# Code generated by godownloader on 2019-12-25T12:47:14Z. DO NOT EDIT. +# + +usage() { + this=$1 + cat </dev/null +} +echoerr() { + echo "$@" 1>&2 +} +log_prefix() { + echo "$0" +} +_logp=6 +log_set_priority() { + _logp="$1" +} +log_priority() { + if test -z "$1"; then + echo "$_logp" + return + fi + [ "$1" -le "$_logp" ] +} +log_tag() { + case $1 in + 0) echo "emerg" ;; + 1) echo "alert" ;; + 2) echo "crit" ;; + 3) echo "err" ;; + 4) echo "warning" ;; + 5) echo "notice" ;; + 6) echo "info" ;; + 7) echo "debug" ;; + *) echo "$1" ;; + esac +} +log_debug() { + log_priority 7 || return 0 + echoerr "$(log_prefix)" "$(log_tag 7)" "$@" +} +log_info() { + log_priority 6 || return 0 + echoerr "$(log_prefix)" "$(log_tag 6)" "$@" +} +log_err() { + log_priority 3 || return 0 + echoerr "$(log_prefix)" "$(log_tag 3)" "$@" +} +log_crit() { + log_priority 2 || return 0 + echoerr "$(log_prefix)" "$(log_tag 2)" "$@" +} +uname_os() { + os=$(uname -s | tr '[:upper:]' '[:lower:]') + case "$os" in + cygwin_nt*) os="windows" ;; + mingw*) os="windows" ;; + msys_nt*) os="windows" ;; + esac + echo "$os" +} +uname_arch() { + arch=$(uname -m) + case $arch in + x86_64) arch="amd64" ;; + x86) arch="386" ;; + i686) arch="386" ;; + i386) arch="386" ;; + aarch64) arch="arm64" ;; + armv5*) arch="armv5" ;; + armv6*) arch="armv6" ;; + armv7*) arch="armv7" ;; + esac + echo ${arch} +} +uname_os_check() { + os=$(uname_os) + case "$os" in + darwin) return 0 ;; + dragonfly) return 0 ;; + freebsd) return 0 ;; + linux) return 0 ;; + android) return 0 ;; + nacl) return 0 ;; + netbsd) return 0 ;; + openbsd) return 0 ;; + plan9) return 0 ;; + solaris) return 0 ;; + windows) return 0 ;; + esac + log_crit "uname_os_check '$(uname -s)' got converted to '$os' which is not a GOOS value. Please file bug at https://github.com/client9/shlib" + return 1 +} +uname_arch_check() { + arch=$(uname_arch) + case "$arch" in + 386) return 0 ;; + amd64) return 0 ;; + arm64) return 0 ;; + armv5) return 0 ;; + armv6) return 0 ;; + armv7) return 0 ;; + ppc64) return 0 ;; + ppc64le) return 0 ;; + mips) return 0 ;; + mipsle) return 0 ;; + mips64) return 0 ;; + mips64le) return 0 ;; + s390x) return 0 ;; + amd64p32) return 0 ;; + esac + log_crit "uname_arch_check '$(uname -m)' got converted to '$arch' which is not a GOARCH value. Please file bug report at https://github.com/client9/shlib" + return 1 +} +untar() { + tarball=$1 + case "${tarball}" in + *.tar.gz | *.tgz) tar --no-same-owner -xzf "${tarball}" ;; + *.tar) tar --no-same-owner -xf "${tarball}" ;; + *.zip) unzip "${tarball}" ;; + *) + log_err "untar unknown archive format for ${tarball}" + return 1 + ;; + esac +} +http_download_curl() { + local_file=$1 + source_url=$2 + header=$3 + if [ -z "$header" ]; then + code=$(curl -w '%{http_code}' -sL -o "$local_file" "$source_url") + else + code=$(curl -w '%{http_code}' -sL -H "$header" -o "$local_file" "$source_url") + fi + if [ "$code" != "200" ]; then + log_debug "http_download_curl received HTTP status $code" + return 1 + fi + return 0 +} +http_download_wget() { + local_file=$1 + source_url=$2 + header=$3 + if [ -z "$header" ]; then + wget -q -O "$local_file" "$source_url" + else + wget -q --header "$header" -O "$local_file" "$source_url" + fi +} +http_download() { + log_debug "http_download $2" + if is_command curl; then + http_download_curl "$@" + return + elif is_command wget; then + http_download_wget "$@" + return + fi + log_crit "http_download unable to find wget or curl" + return 1 +} +http_copy() { + tmp=$(mktemp) + http_download "${tmp}" "$1" "$2" || return 1 + body=$(cat "$tmp") + rm -f "${tmp}" + echo "$body" +} +github_release() { + owner_repo=$1 + version=$2 + test -z "$version" && version="latest" + giturl="https://github.com/${owner_repo}/releases/${version}" + json=$(http_copy "$giturl" "Accept:application/json") + test -z "$json" && return 1 + version=$(echo "$json" | tr -s '\n' ' ' | sed 's/.*"tag_name":"//' | sed 's/".*//') + test -z "$version" && return 1 + echo "$version" +} +hash_sha256() { + TARGET=${1:-/dev/stdin} + if is_command gsha256sum; then + hash=$(gsha256sum "$TARGET") || return 1 + echo "$hash" | cut -d ' ' -f 1 + elif is_command sha256sum; then + hash=$(sha256sum "$TARGET") || return 1 + echo "$hash" | cut -d ' ' -f 1 + elif is_command shasum; then + hash=$(shasum -a 256 "$TARGET" 2>/dev/null) || return 1 + echo "$hash" | cut -d ' ' -f 1 + elif is_command openssl; then + hash=$(openssl -dst openssl dgst -sha256 "$TARGET") || return 1 + echo "$hash" | cut -d ' ' -f a + else + log_crit "hash_sha256 unable to find command to compute sha-256 hash" + return 1 + fi +} +hash_sha256_verify() { + TARGET=$1 + checksums=$2 + if [ -z "$checksums" ]; then + log_err "hash_sha256_verify checksum file not specified in arg2" + return 1 + fi + BASENAME=${TARGET##*/} + want=$(grep "${BASENAME}$" "${checksums}" 2>/dev/null | tr '\t' ' ' | cut -d ' ' -f 1) + if [ -z "$want" ]; then + log_err "hash_sha256_verify unable to find checksum for '${TARGET}' in '${checksums}'" + return 1 + fi + got=$(hash_sha256 "$TARGET") + if [ "$want" != "$got" ]; then + log_err "hash_sha256_verify checksum for '$TARGET' did not verify ${want} vs $got" + return 1 + fi +} +cat /dev/null </dev/null | jq -r '.Version') + BOUNCER_LATEST_VERSION=$(go list -m -json github.com/wagoodman/go-bouncer@latest 2>/dev/null | jq -r '.Version') + CHRONICLE_LATEST_VERSION=$(go list -m -json github.com/anchore/chronicle@latest 2>/dev/null | jq -r '.Version') + GORELEASER_LATEST_VERSION=$(go list -m -json github.com/goreleaser/goreleaser@latest 2>/dev/null | jq -r '.Version') + YAJSV_LATEST_VERSION=$(go list -m -json github.com/neilpa/yajsv@latest 2>/dev/null | jq -r '.Version') + COSIGN_LATEST_VERSION=$(go list -m -json github.com/sigstore/cosign@latest 2>/dev/null | jq -r '.Version') + + # update version variables in the Makefile + sed -r -i -e 's/^(GOLANGCILINT_VERSION = ).*/\1'${GOLANGCILINT_LATEST_VERSION}'/' Makefile + sed -r -i -e 's/^(BOUNCER_VERSION = ).*/\1'${BOUNCER_LATEST_VERSION}'/' Makefile + sed -r -i -e 's/^(CHRONICLE_VERSION = ).*/\1'${CHRONICLE_LATEST_VERSION}'/' Makefile + sed -r -i -e 's/^(GORELEASER_VERSION = ).*/\1'${GORELEASER_LATEST_VERSION}'/' Makefile + sed -r -i -e 's/^(YAJSV_VERSION = ).*/\1'${YAJSV_LATEST_VERSION}'/' Makefile + sed -r -i -e 's/^(COSIGN_VERSION = ).*/\1'${COSIGN_LATEST_VERSION}'/' Makefile + + # update cosign in go.mod as well + go get github.com/sigstore/cosign@$COSIGN_LATEST_VERSION + go mod tidy + + # export the versions for use with create-pull-request + echo "::set-output name=GOLANGCILINT::$GOLANGCILINT_LATEST_VERSION" + echo "::set-output name=BOUNCER::$BOUNCER_LATEST_VERSION" + echo "::set-output name=CHRONICLE::$CHRONICLE_LATEST_VERSION" + echo "::set-output name=GORELEASER::$GORELEASER_LATEST_VERSION" + echo "::set-output name=YAJSV::$YAJSV_LATEST_VERSION" + echo "::set-output name=COSIGN::$COSIGN_LATEST_VERSION" + id: latest-versions + + - uses: tibdex/github-app-token@v1 + id: generate-token + with: + app_id: ${{ secrets.TOKEN_APP_ID }} + private_key: ${{ secrets.TOKEN_APP_PRIVATE_KEY }} + + - uses: peter-evans/create-pull-request@v4 + with: + signoff: true + delete-branch: true + branch: auto/latest-bootstrap-tools + labels: dependencies + commit-message: 'Update syft bootstrap tools to latest versions.' + title: 'Update syft bootstrap tools to latest versions.' + body: | + - [golangci-lint ${{ steps.latest-versions.outputs.GOLANGCILINT }}](https://github.com/golangci/golangci-lint/releases/tag/${{ steps.latest-versions.outputs.GOLANGCILINT }}) + - [bouncer ${{ steps.latest-versions.outputs.BOUNCER }}](https://github.com/wagoodman/go-bouncer/releases/tag/${{ steps.latest-versions.outputs.BOUNCER }}) + - [chronicle ${{ steps.latest-versions.outputs.CHRONICLE }}](https://github.com/anchore/chronicle/releases/tag/${{ steps.latest-versions.outputs.CHRONICLE }}) + - [goreleaser ${{ steps.latest-versions.outputs.GORELEASER }}](https://github.com/goreleaser/goreleaser/releases/tag/${{ steps.latest-versions.outputs.GORELEASER }}) + - [yajsv ${{ steps.latest-versions.outputs.YAJSV }}](https://github.com/neilpa/yajsv/releases/tag/${{ steps.latest-versions.outputs.YAJSV }}) + - [cosign ${{ steps.latest-versions.outputs.COSIGN }}](https://github.com/sigstore/cosign/releases/tag/${{ steps.latest-versions.outputs.COSIGN }}) + This is an auto-generated pull request to update all of the bootstrap tools to the latest versions. + token: ${{ steps.generate-token.outputs.token }} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/.github/workflows/update-stereoscope-release.yml b/ci/tools/openeuler-purl/syft-dev/.github/workflows/update-stereoscope-release.yml new file mode 100644 index 0000000000000000000000000000000000000000..ab50c64cd254d69309b104263e22f838ca26372a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/workflows/update-stereoscope-release.yml @@ -0,0 +1,51 @@ +name: PR for latest Stereoscope release +on: + schedule: + - cron: "0 8 * * *" # 3 AM EST + + workflow_dispatch: + +env: + GO_VERSION: "1.18.x" + GO_STABLE_VERSION: true + +jobs: + upgrade-stereoscope: + runs-on: ubuntu-latest + if: github.repository == 'anchore/syft' # only run for main repo + steps: + - uses: actions/checkout@v3 + + - uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + stable: ${{ env.GO_STABLE_VERSION }} + + - run: | + LATEST_VERSION=$(git ls-remote https://github.com/anchore/stereoscope main | head -n1 | awk '{print $1;}') + + # update go.mod + go get github.com/anchore/stereoscope@$LATEST_VERSION + go mod tidy + + # export the version for use with create-pull-request + echo "::set-output name=LATEST_VERSION::$LATEST_VERSION" + id: latest-version + + - uses: tibdex/github-app-token@v1 + id: generate-token + with: + app_id: ${{ secrets.TOKEN_APP_ID }} + private_key: ${{ secrets.TOKEN_APP_PRIVATE_KEY }} + + - uses: peter-evans/create-pull-request@v4 + with: + signoff: true + delete-branch: true + branch: auto/latest + labels: dependencies + commit-message: "Update Stereoscope to ${{ steps.latest-version.outputs.LATEST_VERSION }}" + title: "Update Stereoscope to ${{ steps.latest-version.outputs.LATEST_VERSION }}" + body: | + Update Stereoscope to ${{ steps.latest-version.outputs.LATEST_VERSION }} + token: ${{ steps.generate-token.outputs.token }} diff --git a/ci/tools/openeuler-purl/syft-dev/.github/workflows/validations.yaml b/ci/tools/openeuler-purl/syft-dev/.github/workflows/validations.yaml new file mode 100644 index 0000000000000000000000000000000000000000..b01a2d8299cfb1dd02da8ada90746dcb21e27a80 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.github/workflows/validations.yaml @@ -0,0 +1,406 @@ +name: "Validations" +on: + workflow_dispatch: + push: + branches: + - main + pull_request: + +env: + GO_VERSION: "1.18.x" + GO_STABLE_VERSION: true + +jobs: + + Static-Analysis: + # Note: changing this job name requires making the same update in the .github/workflows/release.yaml pipeline + name: "Static analysis" + runs-on: ubuntu-20.04 + steps: + - uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + stable: ${{ env.GO_STABLE_VERSION }} + + - uses: actions/checkout@v2 + + - name: Restore tool cache + id: tool-cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/.tmp + key: ${{ runner.os }}-tool-${{ hashFiles('Makefile') }} + + - name: Restore go cache + id: go-cache + uses: actions/cache@v2.1.3 + with: + path: ~/go/pkg/mod + key: ${{ runner.os }}-go-${{ env.GO_VERSION }}-${{ hashFiles('**/go.sum') }} + restore-keys: | + ${{ runner.os }}-go-${{ env.GO_VERSION }}- + + - name: (cache-miss) Bootstrap all project dependencies + if: steps.tool-cache.outputs.cache-hit != 'true' || steps.go-cache.outputs.cache-hit != 'true' + run: make bootstrap + + - name: Bootstrap CI environment dependencies + run: make ci-bootstrap + + - name: Run static analysis + run: make static-analysis + + Unit-Test: + # Note: changing this job name requires making the same update in the .github/workflows/release.yaml pipeline + name: "Unit tests" + runs-on: ubuntu-20.04 + steps: + - uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + stable: ${{ env.GO_STABLE_VERSION }} + + - uses: actions/checkout@v2 + + - name: Restore tool cache + id: tool-cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/.tmp + key: ${{ runner.os }}-tool-${{ hashFiles('Makefile') }} + + - name: Restore go cache + id: go-cache + uses: actions/cache@v2.1.3 + with: + path: ~/go/pkg/mod + key: ${{ runner.os }}-go-${{ env.GO_VERSION }}-${{ hashFiles('**/go.sum') }} + restore-keys: | + ${{ runner.os }}-go-${{ env.GO_VERSION }}- + + - name: (cache-miss) Bootstrap all project dependencies + if: steps.tool-cache.outputs.cache-hit != 'true' || steps.go-cache.outputs.cache-hit != 'true' + run: make bootstrap + + - name: Bootstrap CI environment dependencies + run: make ci-bootstrap + + - name: Build cache key for java test-fixture blobs (for unit tests) + run: make java-packages-fingerprint + + - name: Restore Java test-fixture cache + id: unit-java-cache + uses: actions/cache@v2.1.3 + with: + path: syft/pkg/cataloger/java/test-fixtures/java-builds/packages + key: ${{ runner.os }}-unit-java-cache-${{ hashFiles( 'syft/pkg/cataloger/java/test-fixtures/java-builds/packages.fingerprint' ) }} + + - name: Build cache key for rpm test-fixture blobs (for unit tests) + run: make rpm-binaries-fingerprint + + - name: Restore RPM test-fixture cache + id: unit-rpm-cache + uses: actions/cache@v2.1.3 + with: + path: syft/pkg/cataloger/rpm/test-fixtures/rpms + key: ${{ runner.os }}-unit-rpm-cache-${{ hashFiles( 'syft/pkg/cataloger/rpm/test-fixtures/rpms.fingerprint' ) }} + + - name: Build cache key for go binary test-fixture blobs (for unit tests) + run: make go-binaries-fingerprint + + - name: Restore Go binary test-fixture cache + id: unit-go-binary-cache + uses: actions/cache@v2.1.3 + with: + path: syft/pkg/cataloger/golang/test-fixtures/archs/binaries + key: ${{ runner.os }}-unit-go-binaries-cache-${{ hashFiles( 'syft/pkg/cataloger/golang/test-fixtures/archs/binaries.fingerprint' ) }} + + - name: Run unit tests + run: make unit + + - uses: actions/upload-artifact@v2 + with: + name: unit-test-results + path: test/results/**/* + + Integration-Test: + # Note: changing this job name requires making the same update in the .github/workflows/release.yaml pipeline + name: "Integration tests" + runs-on: ubuntu-20.04 + steps: + - uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + stable: ${{ env.GO_STABLE_VERSION }} + + - uses: actions/checkout@v2 + + - name: Restore tool cache + id: tool-cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/.tmp + key: ${{ runner.os }}-tool-${{ hashFiles('Makefile') }} + + - name: Restore go cache + id: go-cache + uses: actions/cache@v2.1.3 + with: + path: ~/go/pkg/mod + key: ${{ runner.os }}-go-${{ env.GO_VERSION }}-${{ hashFiles('**/go.sum') }} + restore-keys: | + ${{ runner.os }}-go-${{ env.GO_VERSION }}- + + - name: (cache-miss) Bootstrap all project dependencies + if: steps.tool-cache.outputs.cache-hit != 'true' || steps.go-cache.outputs.cache-hit != 'true' + run: make bootstrap + + - name: Bootstrap CI environment dependencies + run: make ci-bootstrap + + - name: Validate syft output against the CycloneDX schema + run: make validate-cyclonedx-schema + + - name: Build key for tar cache + run: make integration-fingerprint + + - name: Restore integration test cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/test/integration/test-fixtures/cache + key: ${{ runner.os }}-integration-test-cache-${{ hashFiles('test/integration/test-fixtures/cache.fingerprint') }} + + - name: Run integration tests + run: make integration + + Benchmark-Test: + name: "Benchmark tests" + runs-on: ubuntu-20.04 + # note: we want benchmarks to run on pull_request events in order to publish results to a sticky comment, and + # we also want to run on push such that merges to main are recorded to the cache. For this reason we don't filter + # the job by event. + steps: + - uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + stable: ${{ env.GO_STABLE_VERSION }} + + - uses: actions/checkout@v2 + + - name: Restore tool cache + id: tool-cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/.tmp + key: ${{ runner.os }}-tool-${{ hashFiles('Makefile') }} + + - name: Restore go cache + id: go-cache + uses: actions/cache@v2.1.3 + with: + path: ~/go/pkg/mod + key: ${{ runner.os }}-go-${{ env.GO_VERSION }}-${{ hashFiles('**/go.sum') }} + restore-keys: | + ${{ runner.os }}-go-${{ env.GO_VERSION }}- + + - name: (cache-miss) Bootstrap all project dependencies + if: steps.tool-cache.outputs.cache-hit != 'true' || steps.go-cache.outputs.cache-hit != 'true' + run: make bootstrap + + - name: Bootstrap CI environment dependencies + run: make ci-bootstrap + + - name: Restore base benchmark result + uses: actions/cache@v2 + with: + path: test/results/benchmark-main.txt + # use base sha for PR or new commit hash for main push in benchmark result key + key: ${{ runner.os }}-bench-${{ (github.event.pull_request.base.sha != github.event.after) && github.event.pull_request.base.sha || github.event.after }} + + - name: Run benchmark tests + id: benchmark + run: | + REF_NAME=${GITHUB_REF##*/} make benchmark + OUTPUT=$(make show-benchstat) + OUTPUT="${OUTPUT//'%'/'%25'}" # URL encode all '%' characters + OUTPUT="${OUTPUT//$'\n'/'%0A'}" # URL encode all '\n' characters + OUTPUT="${OUTPUT//$'\r'/'%0D'}" # URL encode all '\r' characters + echo "::set-output name=result::$OUTPUT" + + - uses: actions/upload-artifact@v2 + with: + name: benchmark-test-results + path: test/results/**/* + + - name: Update PR benchmark results comment + uses: marocchino/sticky-pull-request-comment@v2 + continue-on-error: true + with: + header: benchmark + message: | + ### Benchmark Test Results + +
+ Benchmark results from the latest changes vs base branch + + ``` + ${{ steps.benchmark.outputs.result }} + ``` + +
+ + Build-Snapshot-Artifacts: + name: "Build snapshot artifacts" + runs-on: ubuntu-20.04 + steps: + - uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + stable: ${{ env.GO_STABLE_VERSION }} + + - uses: actions/checkout@v2 + + - name: Set up QEMU + uses: docker/setup-qemu-action@v1 + + - name: Restore tool cache + id: tool-cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/.tmp + key: ${{ runner.os }}-tool-${{ hashFiles('Makefile') }} + + - name: Restore go cache + id: go-cache + uses: actions/cache@v2.1.3 + with: + path: ~/go/pkg/mod + key: ${{ runner.os }}-go-${{ env.GO_VERSION }}-${{ hashFiles('**/go.sum') }} + restore-keys: | + ${{ runner.os }}-go-${{ env.GO_VERSION }}- + + - name: (cache-miss) Bootstrap all project dependencies + if: steps.tool-cache.outputs.cache-hit != 'true' || steps.go-cache.outputs.cache-hit != 'true' + run: make bootstrap + + - name: Build snapshot artifacts + run: make snapshot + + - uses: actions/upload-artifact@v2 + with: + name: artifacts + path: snapshot/**/* + + Acceptance-Linux: + # Note: changing this job name requires making the same update in the .github/workflows/release.yaml pipeline + name: "Acceptance tests (Linux)" + needs: [Build-Snapshot-Artifacts] + runs-on: ubuntu-20.04 + steps: + - uses: actions/checkout@v2 + + - uses: actions/download-artifact@v2 + with: + name: artifacts + path: snapshot + + - name: Run comparison tests (Linux) + run: make compare-linux + + - name: Build key for image cache + run: make install-fingerprint + + - name: Restore install.sh test image cache + id: install-test-image-cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/test/install/cache + key: ${{ runner.os }}-install-test-image-cache-${{ hashFiles('test/install/cache.fingerprint') }} + + - name: Load test image cache + if: steps.install-test-image-cache.outputs.cache-hit == 'true' + run: make install-test-cache-load + + - name: Run install.sh tests (Linux) + run: make install-test + + - name: (cache-miss) Create test image cache + if: steps.install-test-image-cache.outputs.cache-hit != 'true' + run: make install-test-cache-save + + + Acceptance-Mac: + # Note: changing this job name requires making the same update in the .github/workflows/release.yaml pipeline + name: "Acceptance tests (Mac)" + needs: [Build-Snapshot-Artifacts] + runs-on: macos-latest + steps: + - uses: actions/checkout@v2 + + - uses: actions/download-artifact@v2 + with: + name: artifacts + path: snapshot + + - name: Restore docker image cache for compare testing + id: mac-compare-testing-cache + uses: actions/cache@v2.1.3 + with: + path: image.tar + key: ${{ runner.os }}-${{ hashFiles('test/compare/mac.sh') }} + + - name: Run comparison tests (Mac) + run: make compare-mac + + - name: Run install.sh tests (Mac) + run: make install-test-ci-mac + + Cli-Linux: + # Note: changing this job name requires making the same update in the .github/workflows/release.yaml pipeline + name: "CLI tests (Linux)" + needs: [Build-Snapshot-Artifacts] + runs-on: ubuntu-20.04 + steps: + - uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + stable: ${{ env.GO_STABLE_VERSION }} + + - uses: actions/checkout@v2 + + - name: Restore go cache + id: go-cache + uses: actions/cache@v2.1.3 + with: + path: ~/go/pkg/mod + key: ${{ runner.os }}-go-${{ env.GO_VERSION }}-${{ hashFiles('**/go.sum') }} + restore-keys: | + ${{ runner.os }}-go-${{ env.GO_VERSION }}- + + - name: Restore tool cache + id: tool-cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/.tmp + key: ${{ runner.os }}-tool-${{ hashFiles('Makefile') }} + + - name: (cache-miss) Bootstrap all project dependencies + if: steps.tool-cache.outputs.cache-hit != 'true' || steps.go-cache.outputs.cache-hit != 'true' + run: make bootstrap + + - name: Build key for tar cache + run: make cli-fingerprint + + - name: Restore CLI test cache + uses: actions/cache@v2.1.3 + with: + path: ${{ github.workspace }}/test/cli/test-fixtures/cache + key: ${{ runner.os }}-cli-test-cache-${{ hashFiles('test/cli/test-fixtures/cache.fingerprint') }} + + - uses: actions/download-artifact@v2 + with: + name: artifacts + path: snapshot + + - name: Run CLI Tests (Linux) + run: make cli diff --git a/ci/tools/openeuler-purl/syft-dev/.gitignore b/ci/tools/openeuler-purl/syft-dev/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..891ae1507fa983c8743e599dac4f926ec883b1b9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.gitignore @@ -0,0 +1,43 @@ +CHANGELOG.md +/test/results +/dist +/snapshot +.server/ +.vscode/ +.history/ +*.fingerprint +*.tar +*.jar +*.war +*.ear +*.jpi +*.hpi +*.zip +.idea/ +*.log +.images +.tmp/ +coverage.txt +bin/ + +# Binaries for programs and plugins +*.exe +*.exe~ +*.dll +*.so +*.dylib + +# Test binary, build with `go test -c` +*.test + +# Output of the go coverage tool, specifically when used with LiteIDE +*.out + +# macOS Finder metadata +.DS_STORE + +*.profile + +# attestation +cosign.key +cosign.pub diff --git a/ci/tools/openeuler-purl/syft-dev/.golangci.yaml b/ci/tools/openeuler-purl/syft-dev/.golangci.yaml new file mode 100644 index 0000000000000000000000000000000000000000..536445ff8b49b17b4c80b64b42af3d3f7890286e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.golangci.yaml @@ -0,0 +1,61 @@ +# TODO: enable this when we have coverage on docstring comments +#issues: +# # The list of ids of default excludes to include or disable. +# include: +# - EXC0002 # disable excluding of issues about comments from golint + +linters: + # inverted configuration with `enable-all` and `disable` is not scalable during updates of golangci-lint + disable-all: true + enable: + - asciicheck + - bodyclose + - deadcode + - depguard + - dogsled + - dupl + - errcheck + - exportloopref + - funlen + - gocognit + - goconst + - gocritic + - gocyclo + - gofmt + - goimports + - goprintffuncname + - gosec + - gosimple + - govet + - ineffassign + - misspell + - nakedret + - nolintlint + - revive + - rowserrcheck + - staticcheck + - structcheck + - stylecheck + - typecheck + - unconvert + - unparam + - unused + - varcheck + - whitespace + +# do not enable... +# - gochecknoglobals +# - gochecknoinits # this is too aggressive +# - godot +# - godox +# - goerr113 +# - golint # deprecated +# - gomnd # this is too aggressive +# - interfacer # this is a good idea, but is no longer supported and is prone to false positives +# - lll # without a way to specify per-line exception cases, this is not usable +# - maligned # this is an excellent linter, but tricky to optimize and we are not sensitive to memory layout optimizations +# - nestif +# - prealloc # following this rule isn't consistently a good idea, as it sometimes forces unnecessary allocations that result in less idiomatic code +# - scopelint # deprecated +# - testpackage +# - wsl # this doens't have an auto-fixer yet and is pretty noisy (https://github.com/bombsimon/wsl/issues/90) diff --git a/ci/tools/openeuler-purl/syft-dev/.goreleaser.yaml b/ci/tools/openeuler-purl/syft-dev/.goreleaser.yaml new file mode 100644 index 0000000000000000000000000000000000000000..9361429c9dbb525d420a863baad9a612e2bcdda7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.goreleaser.yaml @@ -0,0 +1,95 @@ +release: + prerelease: auto + draft: false + +before: + hooks: + - ./.github/scripts/apple-signing/setup.sh {{ .IsSnapshot }} + +builds: + - id: linux-build + dir: ./cmd/syft + binary: syft + goos: + - linux + goarch: + - amd64 + - arm64 + - ppc64le + - s390x + # set the modified timestamp on the output binary to the git timestamp to ensure a reproducible build + mod_timestamp: &build-timestamp '{{ .CommitTimestamp }}' + env: &build-env + - CGO_ENABLED=0 + ldflags: &build-ldflags | + -w + -s + -extldflags '-static' + -X github.com/anchore/syft/internal/version.version={{.Version}} + -X github.com/anchore/syft/internal/version.gitCommit={{.Commit}} + -X github.com/anchore/syft/internal/version.buildDate={{.Date}} + -X github.com/anchore/syft/internal/version.gitDescription={{.Summary}} + + - id: darwin-build + dir: ./cmd/syft + binary: syft + goos: + - darwin + goarch: + - amd64 + - arm64 + mod_timestamp: *build-timestamp + env: *build-env + ldflags: *build-ldflags + hooks: + post: + # we must have signing as a build hook instead of the signs section. The signs section must register a new + # asset, where we want to replace an existing asset. A post-build hook has the advantage of not needing to + # unpackage and repackage a tar.gz with a signed binary + - ./.github/scripts/apple-signing/sign.sh "{{ .Path }}" "{{ .IsSnapshot }}" "{{ .Target }}" + + - id: windows-build + dir: ./cmd/syft + binary: syft + goos: + - windows + goarch: + - amd64 + mod_timestamp: *build-timestamp + env: *build-env + ldflags: *build-ldflags + +archives: + - id: linux-archives + builds: + - linux-build + + # note: the signing process is depending on tar.gz archives. If this format changes then .github/scripts/apple-signing/*.sh will need to be adjusted + - id: darwin-archives + builds: + - darwin-build + + - id: windows-archives + format: zip + builds: + - windows-build + +nfpms: + - license: "Apache 2.0" + maintainer: "Anchore, Inc" + homepage: &website "https://github.com/anchore/syft" + description: &description "A tool that generates a Software Bill Of Materials (SBOM) from container images and filesystems" + formats: + - rpm + - deb + +brews: + - tap: + owner: anchore + name: homebrew-syft + ids: + - darwin-archives + - linux-archives + homepage: *website + description: *description + license: "Apache License 2.0" diff --git a/ci/tools/openeuler-purl/syft-dev/.goreleaser_docker.yaml b/ci/tools/openeuler-purl/syft-dev/.goreleaser_docker.yaml new file mode 100644 index 0000000000000000000000000000000000000000..70d49a2d1e13966f1bcde0f1a7c712bbf0f9b0f2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/.goreleaser_docker.yaml @@ -0,0 +1,193 @@ +# Separate docker configuration to isolate docker dependency away from +# mac-os runner on github actions. +# See: +# https://github.com/anchore/syft/issues/577 +# https://github.com/anchore/syft/issues/519 +# https://github.com/anchore/syft/issues/576 +release: + disable: true + +env: + # required to support multi architecture docker builds + - DOCKER_CLI_EXPERIMENTAL=enabled + +builds: + - id: linux-build + dir: ./cmd/syft + binary: syft + goos: + - linux + goarch: + - amd64 + - arm64 + - ppc64le + - s390x + # set the modified timestamp on the output binary to the git timestamp to ensure a reproducible build + mod_timestamp: &build-timestamp '{{ .CommitTimestamp }}' + env: &build-env + - CGO_ENABLED=0 + ldflags: &build-ldflags | + -w + -s + -extldflags '-static' + -X github.com/anchore/syft/internal/version.version={{.Version}} + -X github.com/anchore/syft/internal/version.gitCommit={{.Commit}} + -X github.com/anchore/syft/internal/version.buildDate={{.Date}} + -X github.com/anchore/syft/internal/version.gitDescription={{.Summary}} + +dockers: + - image_templates: + - anchore/syft:debug + - anchore/syft:{{.Tag}}-debug + - ghcr.io/anchore/syft:debug + - ghcr.io/anchore/syft:{{.Tag}}-debug + goarch: amd64 + dockerfile: Dockerfile.debug + use: buildx + build_flag_templates: + - "--platform=linux/amd64" + - "--build-arg=BUILD_DATE={{.Date}}" + - "--build-arg=BUILD_VERSION={{.Version}}" + - "--build-arg=VCS_REF={{.FullCommit}}" + - "--build-arg=VCS_URL={{.GitURL}}" + + - image_templates: + - anchore/syft:debug-arm64v8 + - anchore/syft:{{.Tag}}-debug-arm64v8 + - ghcr.io/anchore/syft:debug-arm64v8 + - ghcr.io/anchore/syft:{{.Tag}}-debug-arm64v8 + goarch: arm64 + dockerfile: Dockerfile.debug + use: buildx + build_flag_templates: + - "--platform=linux/arm64/v8" + - "--build-arg=BUILD_DATE={{.Date}}" + - "--build-arg=BUILD_VERSION={{.Version}}" + - "--build-arg=VCS_REF={{.FullCommit}}" + - "--build-arg=VCS_URL={{.GitURL}}" + + - image_templates: + - anchore/syft:debug-ppc64le + - anchore/syft:{{.Tag}}-debug-ppc64le + - ghcr.io/anchore/syft:debug-ppc64le + - ghcr.io/anchore/syft:{{.Tag}}-debug-ppc64le + goarch: ppc64le + dockerfile: Dockerfile.debug + use: buildx + build_flag_templates: + - "--platform=linux/ppc64le" + - "--build-arg=BUILD_DATE={{.Date}}" + - "--build-arg=BUILD_VERSION={{.Version}}" + - "--build-arg=VCS_REF={{.FullCommit}}" + - "--build-arg=VCS_URL={{.GitURL}}" + + - image_templates: + - anchore/syft:debug-s390x + - anchore/syft:{{.Tag}}-debug-s390x + - ghcr.io/anchore/syft:debug-s390x + - ghcr.io/anchore/syft:{{.Tag}}-debug-s390x + goarch: s390x + dockerfile: Dockerfile.debug + use: buildx + build_flag_templates: + - "--platform=linux/s390x" + - "--build-arg=BUILD_DATE={{.Date}}" + - "--build-arg=BUILD_VERSION={{.Version}}" + - "--build-arg=VCS_REF={{.FullCommit}}" + - "--build-arg=VCS_URL={{.GitURL}}" + + - image_templates: + - anchore/syft:latest + - anchore/syft:{{.Tag}} + - ghcr.io/anchore/syft:latest + - ghcr.io/anchore/syft:{{.Tag}} + goarch: amd64 + dockerfile: Dockerfile + use: buildx + build_flag_templates: + - "--platform=linux/amd64" + - "--build-arg=BUILD_DATE={{.Date}}" + - "--build-arg=BUILD_VERSION={{.Version}}" + - "--build-arg=VCS_REF={{.FullCommit}}" + - "--build-arg=VCS_URL={{.GitURL}}" + + - image_templates: + - anchore/syft:{{.Tag}}-arm64v8 + - ghcr.io/anchore/syft:{{.Tag}}-arm64v8 + goarch: arm64 + dockerfile: Dockerfile + use: buildx + build_flag_templates: + - "--platform=linux/arm64/v8" + - "--build-arg=BUILD_DATE={{.Date}}" + - "--build-arg=BUILD_VERSION={{.Version}}" + - "--build-arg=VCS_REF={{.FullCommit}}" + - "--build-arg=VCS_URL={{.GitURL}}" + + - image_templates: + - anchore/syft:{{.Tag}}-ppc64le + - ghcr.io/anchore/syft:{{.Tag}}-ppc64le + goarch: ppc64le + dockerfile: Dockerfile + use: buildx + build_flag_templates: + - "--platform=linux/ppc64le" + - "--build-arg=BUILD_DATE={{.Date}}" + - "--build-arg=BUILD_VERSION={{.Version}}" + - "--build-arg=VCS_REF={{.FullCommit}}" + - "--build-arg=VCS_URL={{.GitURL}}" + + - image_templates: + - anchore/syft:{{.Tag}}-s390x + - ghcr.io/anchore/syft:{{.Tag}}-s390x + goarch: s390x + dockerfile: Dockerfile + use: buildx + build_flag_templates: + - "--platform=linux/s390x" + - "--build-arg=BUILD_DATE={{.Date}}" + - "--build-arg=BUILD_VERSION={{.Version}}" + - "--build-arg=VCS_REF={{.FullCommit}}" + - "--build-arg=VCS_URL={{.GitURL}}" + +docker_manifests: + - name_template: anchore/syft:latest + image_templates: + - anchore/syft:{{.Tag}} + - anchore/syft:{{.Tag}}-arm64v8 + - anchore/syft:{{.Tag}}-ppc64le + - anchore/syft:{{.Tag}}-s390x + + - name_template: anchore/syft:debug + - anchore/syft:{{.Tag}}-debug + - anchore/syft:{{.Tag}}-debug-arm64v8 + - anchore/syft:{{.Tag}}-debug-ppc64le + - anchore/syft:{{.Tag}}-debug-s390x + + - name_template: anchore/syft:{{.Tag}} + image_templates: + - anchore/syft:{{.Tag}} + - anchore/syft:{{.Tag}}-arm64v8 + - anchore/syft:{{.Tag}}-ppc64le + - anchore/syft:{{.Tag}}-s390x + + - name_template: ghcr.io/anchore/syft:latest + image_templates: + - ghcr.io/anchore/syft:{{.Tag}} + - ghcr.io/anchore/syft:{{.Tag}}-arm64v8 + - ghcr.io/anchore/syft:{{.Tag}}-ppc64le + - ghcr.io/anchore/syft:{{.Tag}}-s390x + + - name_template: ghcr.io/anchore/syft:debug + image_templates: + - ghcr.io/anchore/syft:{{.Tag}}-debug + - ghcr.io/anchore/syft:{{.Tag}}-debug-arm64v8 + - ghcr.io/anchore/syft:{{.Tag}}-debug-ppc64le + - ghcr.io/anchore/syft:{{.Tag}}-debug-s390x + + - name_template: ghcr.io/anchore/syft:{{.Tag}} + image_templates: + - ghcr.io/anchore/syft:{{.Tag}} + - ghcr.io/anchore/syft:{{.Tag}}-arm64v8 + - ghcr.io/anchore/syft:{{.Tag}}-ppc64le + - ghcr.io/anchore/syft:{{.Tag}}-s390x diff --git a/ci/tools/openeuler-purl/syft-dev/CONTRIBUTING.md b/ci/tools/openeuler-purl/syft-dev/CONTRIBUTING.md new file mode 100644 index 0000000000000000000000000000000000000000..dc02ce2ab19cf94217b0cc308dc2bf4e43b5331b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/CONTRIBUTING.md @@ -0,0 +1,154 @@ +# Contributing to Syft + +If you are looking to contribute to this project and want to open a GitHub pull request ("PR"), there are a few guidelines of what we are looking for in patches. Make sure you go through this document and ensure that your code proposal is aligned. + +## Setting up your environment + +Before you can contribute to Syft, you need to configure your development environment. + +### Debian setup + +You will need to install Go. The version on https://go.dev works best, using the system golang doesn't always work the way you might expect. + +At the time of writing, Go 1.19 does not work correctly with Syft. Please use Go 1.18 for now. + +You will also need Docker. There's no reason the system packages shouldn't work, but we used the official Docker package. You can find instructions for installing Docker in Debian [here](https://docs.docker.com/engine/install/debian/). + +You also need to install some Debian packages + +```sh +sudo apt-get install build-essential zip bc libxml2-utils git +``` + +## Configuring Git + +You will need to configure your git client with your name and email address. This is easily done from the command line. + +```text +$ git config --global user.name "John Doe" +$ git config --global user.email "john.doe@example.com" +``` + +This username and email address will matter later in this guide. + +## Fork the repo + +You should fork the Syft repo using the "Fork" button at the top right of the Syft GitHub [site](https://github.com/anchore/syft/). You will be doing your development in your fork, then submit a pull request to Syft. There are many resources how to use GitHub effectively, we will not cover those here. + +## Adding a feature or fix + +If you look at the Syft [Issue](https://github.com/anchore/syft/issues) there are plenty of bugs and feature requests. Maybe look at the [good first issue](https://github.com/anchore/syft/issues?q=is%3Aopen+is%3Aissue+label%3A%22good+first+issue%22) list if you're not sure where to start. + +## Commit guidelines + +In the Syft project we like commits and pull requests (PR) to be easy to understand and review. Open source thrives best when everything happening is over documented and small enough to be understood. + +### Granular commits + +Please try to make every commit as simple as possible, but no simpler. The idea is that each commit should be a logical unit of code. Try not to commit too many tiny changes, for example every line changed in a file as a separate commit. And also try not to make a commit enormous, for example committing all your work at the end of the day. + +Rather than try to follow a strict guide on what is or is not best, we try to be flexible and simple in this space. Do what makes the most sense for the changes you are trying to include. + +### Commit title and description + +Remember that the message you leave for a commit is for the reviewer in the present, and for someone (maybe you) changing something in the future. Please make sure the title and description used is easy to understand and explains what was done. Jokes and clever comments generally don't age well in commit messages. Just the facts please. + +## Sign off your work + +The `sign-off` is an added line at the end of the explanation for the commit, certifying that you wrote it or otherwise have the right to submit it as an open-source patch. By submitting a contribution, you agree to be bound by the terms of the DCO Version 1.1 and Apache License Version 2.0. + +Signing off a commit certifies the below Developer's Certificate of Origin (DCO): + +```text +Developer's Certificate of Origin 1.1 + +By making a contribution to this project, I certify that: + + (a) The contribution was created in whole or in part by me and I + have the right to submit it under the open source license + indicated in the file; or + + (b) The contribution is based upon previous work that, to the best + of my knowledge, is covered under an appropriate open source + license and I have the right under that license to submit that + work with modifications, whether created in whole or in part + by me, under the same open source license (unless I am + permitted to submit under a different license), as indicated + in the file; or + + (c) The contribution was provided directly to me by some other + person who certified (a), (b) or (c) and I have not modified + it. + + (d) I understand and agree that this project and the contribution + are public and that a record of the contribution (including all + personal information I submit with it, including my sign-off) is + maintained indefinitely and may be redistributed consistent with + this project or the open source license(s) involved. +``` + +All contributions to this project are licensed under the [Apache License Version 2.0, January 2004](http://www.apache.org/licenses/). + +When committing your change, you can add the required line manually so that it looks like this: + +```text +Signed-off-by: John Doe +``` + +Creating a signed-off commit is then possible with `-s` or `--signoff`: + +```text +$ git commit -s -m "this is a commit message" +``` + +To double-check that the commit was signed-off, look at the log output: + +```text +$ git log -1 +commit 37ceh170e4hb283bb73d958f2036ee5k07e7fde7 (HEAD -> issue-35, origin/main, main) +Author: John Doe +Date: Mon Aug 1 11:27:13 2020 -0400 + + this is a commit message + + Signed-off-by: John Doe +``` + +## Test your changes + +This project has a `Makefile` which includes many helpers running both unit and integration tests. You can run `make help` to see all the options. Although PRs will have automatic checks for these, it is useful to run them locally, ensuring they pass before submitting changes. Ensure you've bootstrapped once before running tests: + +```text +$ make bootstrap +``` + +You only need to bootstrap once. After the bootstrap process, you can run the tests as many times as needed: + +```text +$ make unit +$ make integration +``` + +You can also run `make all` to run a more extensive test suite, but there is additional configuration that will be needed for those tests to run correctly. We will not cover the extra steps here. + +## Pull Request + +If you made it this far and all the tests are passing, it's time to submit a Pull Request (PR) for Syft. Submitting a PR is always a scary moment as what happens next can be an unknown. The Syft project strives to be easy to work with, we appreciate all contributions. Nobody is going to yell at you or try to make you feel bad. We love contributions and know how scary that first PR can be. + +### PR Title and Description + +Just like the commit title and description mentioned above, the PR title and description is very important for letting others know what's happening. Please include any details you think a reviewer will need to more properly review your PR. + +A PR that is very large or poorly described has a higher likelihood of being pushed to the end of the list. Reviewers like PRs they can understand and quickly review. + +### What to expect next + +Please be patient with the project. We try to review PRs in a timely manner, but this is highly dependent on all the other tasks we have going on. It's OK to ask for a status update every week or two, it's not OK to ask for a status update every day. + +It's very likely the reviewer will have questions and suggestions for changes to your PR. If your changes don't match the current style and flow of the other code, expect a request to change what you've done. + +## Document your changes + +And lastly, when proposed changes are modifying user-facing functionality or output, it is expected the PR will include updates to the documentation as well. Syft is not a project that is heavy on documentation. This will mostly be updating the README and help for the tool. + +If nobody knows new features exist, they can't use them! diff --git a/ci/tools/openeuler-purl/syft-dev/DEVELOPING.md b/ci/tools/openeuler-purl/syft-dev/DEVELOPING.md new file mode 100644 index 0000000000000000000000000000000000000000..f12462ab4ef690c32ce8390ea933c3b6389d09f1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/DEVELOPING.md @@ -0,0 +1,179 @@ +# Developing + +## Getting started + +In order to test and develop in this repo you will need the following dependencies installed: +- docker +- make + +After cloning do the following: +1. run `make bootstrap` to download go mod dependencies, create the `/.tmp` dir, and download helper utilities. +2. run `make` to run linting, tests, and other verifications to make certain everything is working alright. + +Checkout `make help` to see what other actions you can take. + +The main make tasks for common static analysis and testing are `lint`, `lint-fix`, `unit`, `integration`, and `cli`. + +## Levels of testing + +- `unit`: The default level of test which is distributed throughout the repo are unit tests. Any `_test.go` file that + does not reside somewhere within the `/test` directory is a unit test. Other forms of testing should be organized in + the `/test` directory. These tests should focus on correctness of functionality in depth. % Test coverage metrics + only considers unit tests and no other forms of testing. + +- `integration`: located within `test/integration`, these tests focus on the behavior surfaced by the common library + entrypoints from the `syft` package and make light assertions about the results surfaced. Additionally, these tests + tend to make diversity assertions for enum-like objects, ensuring that as enum values are added to a definition + that integration tests will automatically fail if no test attempts to use that enum value. For more details see + the "Data diversity and freshness assertions" section below. + +- `cli`: located with in `test/cli`, these are tests that test the correctness of application behavior from a + snapshot build. This should be used in cases where a unit or integration test will not do or if you are looking + for in-depth testing of code in the `cmd/` package (such as testing the proper behavior of application configuration, + CLI switches, and glue code before syft library calls). + +- `acceptance`: located within `test/compare` and `test/install`, these are smoke-like tests that ensure that application + packaging and installation works as expected. For example, during release we provide RPM packages as a download + artifact. We also have an accompanying RPM acceptance test that installs the RPM from a snapshot build and ensures the + output of a syft invocation matches canned expected output. New acceptance tests should be added for each release artifact + and architecture supported (when possible). + +### Data diversity and freshness assertions + +It is important that tests against the codebase are flexible enough to begin failing when they do not cover "enough" +of the objects under test. "Cover" in this case does not mean that some percentage of the code has been executed +during testing, but instead that there is enough diversity of data input reflected in testing relative to the +definitions available. + +For instance, consider an enum-like value like so: +```go +type Language string + +const ( + Java Language = "java" + JavaScript Language = "javascript" + Python Language = "python" + Ruby Language = "ruby" + Go Language = "go" +) +``` + +Say we have a test that exercises all the languages defined today: + +```go +func TestCatalogPackages(t *testing.T) { + testTable := []struct { + // ... the set of test cases that test all languages + } + for _, test := range cases { + t.Run(test.name, func (t *testing.T) { + // use inputFixturePath and assert that syft.CatalogPackages() returns the set of expected Package objects + // ... + }) + } +} +``` + +Where each test case has a `inputFixturePath` that would result with packages from each language. This test is +brittle since it does not assert that all languages were exercised directly and future modifications (such as +adding a new language) won't be covered by any test cases. + +To address this the enum-like object should have a definition of all objects that can be used in testing: + +```go +type Language string + +// const( Java Language = ..., ... ) + +var AllLanguages = []Language{ + Java, + JavaScript, + Python, + Ruby, + Go, + Rust, +} +``` + +Allowing testing to automatically fail when adding a new language: + +```go +func TestCatalogPackages(t *testing.T) { + testTable := []struct { + // ... the set of test cases that (hopefully) covers all languages + } + + // new stuff... + observedLanguages := strset.New() + + for _, test := range cases { + t.Run(test.name, func (t *testing.T) { + // use inputFixturePath and assert that syft.CatalogPackages() returns the set of expected Package objects + // ... + + // new stuff... + for _, actualPkg := range actual { + observedLanguages.Add(string(actualPkg.Language)) + } + + }) + } + + // new stuff... + for _, expectedLanguage := range pkg.AllLanguages { + if !observedLanguages.Contains(expectedLanguage) { + t.Errorf("failed to test language=%q", expectedLanguage) + } + } +} +``` + +This is a better test since it will fail when someone adds a new language but fails to write a test case that should +exercise that new language. This method is ideal for integration-level testing, where testing correctness in depth +is not needed (that is what unit tests are for) but instead testing in breadth to ensure that units are well integrated. + +A similar case can be made for data freshness; if the quality of the results will be diminished if the input data +is not kept up to date then a test should be written (when possible) to assert any input data is not stale. + +An example of this is the static list of licenses that is stored in `internal/spdxlicense` for use by the SPDX +presenters. This list is updated and published periodically by an external group and syft can grab and update this +list by running `go generate ./...` from the root of the repo. + +An integration test has been written to grabs the latest license list version externally and compares that version +with the version generated in the codebase. If they differ, the test fails, indicating to someone that there is an +action needed to update it. + +**_The key takeaway is to try and write tests that fail when data assumptions change and not just when code changes.**_ + +### Snapshot tests + +The format objects make a lot of use of "snapshot" testing, where you save the expected output bytes from a call into the +git repository and during testing make a comparison of the actual bytes from the subject under test with the golden +copy saved in the repo. The "golden" files are stored in the `test-fixtures/snapshot` directory relative to the go +package under test and should always be updated by invoking `go test` on the specific test file with a specific CLI +update flag provided. + +Many of the `Format` tests make use of this approach, where the raw SBOM report is saved in the repo and the test +compares that SBOM with what is generated from the latest presenter code. For instance, at the time of this writing +the CycloneDX presenter snapshots can be updated by running: + +```bash +go test ./internal/formats -update-cyclonedx +``` + +These flags are defined at the top of the test files that have tests that use the snapshot files. + +Snapshot testing is only as good as the manual verification of the golden snapshot file saved to the repo! Be careful +and diligent when updating these files. + +## Architecture + +TODO: outline: +- analysis creates a static SBOM which can be encoded and decoded. +- format objects, should strive to not add or enrich data in encoding that could otherwise be done during analysis +- pkg.Catalogers +- file catalogers +- source.Source +- file.Resolvers +- logger abstraction +- events / bus abstraction \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/Dockerfile b/ci/tools/openeuler-purl/syft-dev/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..c93c21fabf3b15333433d51dc2c20421271ef57d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/Dockerfile @@ -0,0 +1,29 @@ +FROM gcr.io/distroless/static-debian11:debug AS build + +FROM scratch +# needed for version check HTTPS request +COPY --from=build /etc/ssl/certs/ca-certificates.crt /etc/ssl/certs/ca-certificates.crt + +# create the /tmp dir, which is needed for image content cache +WORKDIR /tmp + +COPY syft / + +ARG BUILD_DATE +ARG BUILD_VERSION +ARG VCS_REF +ARG VCS_URL + +LABEL org.opencontainers.image.created=$BUILD_DATE +LABEL org.opencontainers.image.title="syft" +LABEL org.opencontainers.image.description="CLI tool and library for generating a Software Bill of Materials from container images and filesystems" +LABEL org.opencontainers.image.source=$VCS_URL +LABEL org.opencontainers.image.revision=$VCS_REF +LABEL org.opencontainers.image.vendor="Anchore, Inc." +LABEL org.opencontainers.image.version=$BUILD_VERSION +LABEL org.opencontainers.image.licenses="Apache-2.0" +LABEL io.artifacthub.package.readme-url="https://raw.githubusercontent.com/anchore/syft/main/README.md" +LABEL io.artifacthub.package.logo-url="https://user-images.githubusercontent.com/5199289/136844524-1527b09f-c5cb-4aa9-be54-5aa92a6086c1.png" +LABEL io.artifacthub.package.license="Apache-2.0" + +ENTRYPOINT ["/syft"] diff --git a/ci/tools/openeuler-purl/syft-dev/Dockerfile.debug b/ci/tools/openeuler-purl/syft-dev/Dockerfile.debug new file mode 100644 index 0000000000000000000000000000000000000000..3c1761cf41d0443caa9b75fe0dfb7b6b653d8d71 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/Dockerfile.debug @@ -0,0 +1,25 @@ +FROM gcr.io/distroless/static-debian11:debug + +# create the /tmp dir, which is needed for image content cache +WORKDIR /tmp + +COPY syft / + +ARG BUILD_DATE +ARG BUILD_VERSION +ARG VCS_REF +ARG VCS_URL + +LABEL org.opencontainers.image.created=$BUILD_DATE +LABEL org.opencontainers.image.title="syft" +LABEL org.opencontainers.image.description="CLI tool and library for generating a Software Bill of Materials from container images and filesystems" +LABEL org.opencontainers.image.source=$VCS_URL +LABEL org.opencontainers.image.revision=$VCS_REF +LABEL org.opencontainers.image.vendor="Anchore, Inc." +LABEL org.opencontainers.image.version=$BUILD_VERSION +LABEL org.opencontainers.image.licenses="Apache-2.0" +LABEL io.artifacthub.package.readme-url="https://raw.githubusercontent.com/anchore/syft/main/README.md" +LABEL io.artifacthub.package.logo-url="https://user-images.githubusercontent.com/5199289/136844524-1527b09f-c5cb-4aa9-be54-5aa92a6086c1.png" +LABEL io.artifacthub.package.license="Apache-2.0" + +ENTRYPOINT ["/syft"] diff --git a/ci/tools/openeuler-purl/syft-dev/LICENSE b/ci/tools/openeuler-purl/syft-dev/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..261eeb9e9f8b2b4b0d119366dda99c6fd7d35c64 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/LICENSE @@ -0,0 +1,201 @@ + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + + Copyright [yyyy] [name of copyright owner] + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/ci/tools/openeuler-purl/syft-dev/Makefile b/ci/tools/openeuler-purl/syft-dev/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..f7091a6483138f9276e0c96b4271af885b48da60 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/Makefile @@ -0,0 +1,422 @@ +BIN = syft +TEMPDIR = ./.tmp +RESULTSDIR = test/results +COVER_REPORT = $(RESULTSDIR)/unit-coverage-details.txt +COVER_TOTAL = $(RESULTSDIR)/unit-coverage-summary.txt +LINTCMD = $(TEMPDIR)/golangci-lint run --tests=false --timeout=4m --config .golangci.yaml +RELEASE_CMD=$(TEMPDIR)/goreleaser release --rm-dist +SNAPSHOT_CMD=$(RELEASE_CMD) --skip-publish --snapshot +VERSION=$(shell git describe --dirty --always --tags) +COMPARE_TEST_IMAGE = centos:8.2.2004 +COMPARE_DIR = ./test/compare +GOLANGCILINT_VERSION = v1.49.0 +BOUNCER_VERSION = v0.4.0 +CHRONICLE_VERSION = v0.4.1 +GORELEASER_VERSION = v1.11.2 +YAJSV_VERSION = v1.4.0 +COSIGN_VERSION = v1.11.1 + +# formatting variables +BOLD := $(shell tput -T linux bold) +PURPLE := $(shell tput -T linux setaf 5) +GREEN := $(shell tput -T linux setaf 2) +CYAN := $(shell tput -T linux setaf 6) +RED := $(shell tput -T linux setaf 1) +RESET := $(shell tput -T linux sgr0) +TITLE := $(BOLD)$(PURPLE) +SUCCESS := $(BOLD)$(GREEN) + +# the quality gate lower threshold for unit test total % coverage (by function statements) +COVERAGE_THRESHOLD := 62 + +# CI cache busting values; change these if you want CI to not use previous stored cache +INTEGRATION_CACHE_BUSTER="894d8ca" +CLI_CACHE_BUSTER="e5cdfd8" +BOOTSTRAP_CACHE="c7afb99ad" + +## Build variables +DISTDIR=./dist +SNAPSHOTDIR=./snapshot +OS=$(shell uname | tr '[:upper:]' '[:lower:]') +SNAPSHOT_BIN=$(realpath $(shell pwd)/$(SNAPSHOTDIR)/$(OS)-build_$(OS)_amd64_v1/$(BIN)) + +## Variable assertions + +ifndef TEMPDIR + $(error TEMPDIR is not set) +endif + +ifndef RESULTSDIR + $(error RESULTSDIR is not set) +endif + +ifndef COMPARE_DIR + $(error COMPARE_DIR is not set) +endif + +ifndef DISTDIR + $(error DISTDIR is not set) +endif + +ifndef SNAPSHOTDIR + $(error SNAPSHOTDIR is not set) +endif + +ifndef VERSION + $(error VERSION is not set) +endif + +ifndef REF_NAME + REF_NAME = $(VERSION) +endif + +define title + @printf '$(TITLE)$(1)$(RESET)\n' +endef + +define safe_rm_rf + bash -c 'test -z "$(1)" && false || rm -rf $(1)' +endef + +define safe_rm_rf_children + bash -c 'test -z "$(1)" && false || rm -rf $(1)/*' +endef + +## Tasks + +.PHONY: all +all: clean static-analysis test ## Run all linux-based checks (linting, license check, unit, integration, and linux compare tests) + @printf '$(SUCCESS)All checks pass!$(RESET)\n' + +.PHONY: test +test: unit validate-cyclonedx-schema integration benchmark compare-linux cli ## Run all tests (currently unit, integration, linux compare, and cli tests) + +.PHONY: help +help: + @grep -E '^[a-zA-Z_-]+:.*?## .*$$' $(MAKEFILE_LIST) | sort | awk 'BEGIN {FS = ":.*?## "}; {printf "$(BOLD)$(CYAN)%-25s$(RESET)%s\n", $$1, $$2}' + +.PHONY: ci-bootstrap +ci-bootstrap: + DEBIAN_FRONTEND=noninteractive sudo apt update && sudo -E apt install -y bc jq libxml2-utils + +.PHONY: +ci-bootstrap-mac: + github_changelog_generator --version || sudo gem install github_changelog_generator + +$(RESULTSDIR): + mkdir -p $(RESULTSDIR) + +$(TEMPDIR): + mkdir -p $(TEMPDIR) + +.PHONY: bootstrap-tools +bootstrap-tools: $(TEMPDIR) + GO111MODULE=off GOBIN=$(realpath $(TEMPDIR)) go get -u golang.org/x/perf/cmd/benchstat + curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(TEMPDIR)/ $(GOLANGCILINT_VERSION) + curl -sSfL https://raw.githubusercontent.com/wagoodman/go-bouncer/master/bouncer.sh | sh -s -- -b $(TEMPDIR)/ $(BOUNCER_VERSION) + curl -sSfL https://raw.githubusercontent.com/anchore/chronicle/main/install.sh | sh -s -- -b $(TEMPDIR)/ $(CHRONICLE_VERSION) + .github/scripts/goreleaser-install.sh -d -b $(TEMPDIR)/ $(GORELEASER_VERSION) + GOBIN="$(realpath $(TEMPDIR))" go install github.com/neilpa/yajsv@$(YAJSV_VERSION) + GOBIN="$(realpath $(TEMPDIR))" go install github.com/sigstore/cosign/cmd/cosign@$(COSIGN_VERSION) + +.PHONY: bootstrap-go +bootstrap-go: + go mod download + +.PHONY: bootstrap +bootstrap: $(RESULTSDIR) bootstrap-go bootstrap-tools ## Download and install all go dependencies (+ prep tooling in the ./tmp dir) + $(call title,Bootstrapping dependencies) + +.PHONY: static-analysis +static-analysis: check-go-mod-tidy check-licenses lint + +.PHONY: lint +lint: ## Run gofmt + golangci lint checks + $(call title,Running linters) + # ensure there are no go fmt differences + @printf "files with gofmt issues: [$(shell gofmt -l -s .)]\n" + @test -z "$(shell gofmt -l -s .)" + + # run all golangci-lint rules + $(LINTCMD) + + # go tooling does not play well with certain filename characters, ensure the common cases don't result in future "go get" failures + $(eval MALFORMED_FILENAMES := $(shell find . | grep -e ':')) + @bash -c "[[ '$(MALFORMED_FILENAMES)' == '' ]] || (printf '\nfound unsupported filename characters:\n$(MALFORMED_FILENAMES)\n\n' && false)" + +.PHONY: lint-fix +lint-fix: ## Auto-format all source code + run golangci lint fixers + $(call title,Running lint fixers) + gofmt -w -s . + $(LINTCMD) --fix + go mod tidy + +.PHONY: check-licenses +check-licenses: ## Ensure transitive dependencies are compliant with the current license policy + $(TEMPDIR)/bouncer check ./... + +check-go-mod-tidy: + @ .github/scripts/go-mod-tidy-check.sh && echo "go.mod and go.sum are tidy!" + +.PHONY: validate-cyclonedx-schema +validate-cyclonedx-schema: + cd schema/cyclonedx && make + +.PHONY: unit +unit: $(RESULTSDIR) fixtures ## Run unit tests (with coverage) + $(call title,Running unit tests) + go test -coverprofile $(COVER_REPORT) $(shell go list ./... | grep -v anchore/syft/test) + @go tool cover -func $(COVER_REPORT) | grep total | awk '{print substr($$3, 1, length($$3)-1)}' > $(COVER_TOTAL) + @echo "Coverage: $$(cat $(COVER_TOTAL))" + @if [ $$(echo "$$(cat $(COVER_TOTAL)) >= $(COVERAGE_THRESHOLD)" | bc -l) -ne 1 ]; then echo "$(RED)$(BOLD)Failed coverage quality gate (> $(COVERAGE_THRESHOLD)%)$(RESET)" && false; fi + +.PHONY: benchmark +benchmark: $(RESULTSDIR) ## Run benchmark tests and compare against the baseline (if available) + $(call title,Running benchmark tests) + go test -p 1 -run=^Benchmark -bench=. -count=5 -benchmem ./... | tee $(RESULTSDIR)/benchmark-$(REF_NAME).txt + (test -s $(RESULTSDIR)/benchmark-main.txt && \ + $(TEMPDIR)/benchstat $(RESULTSDIR)/benchmark-main.txt $(RESULTSDIR)/benchmark-$(REF_NAME).txt || \ + $(TEMPDIR)/benchstat $(RESULTSDIR)/benchmark-$(REF_NAME).txt) \ + | tee $(RESULTSDIR)/benchstat.txt + +.PHONY: show-benchstat +show-benchstat: + @cat $(RESULTSDIR)/benchstat.txt + +# note: this is used by CI to determine if the install test fixture cache (docker image tars) should be busted +install-fingerprint: + cd test/install && \ + make cache.fingerprint + +install-test: $(SNAPSHOTDIR) + cd test/install && \ + make + +install-test-cache-save: $(SNAPSHOTDIR) + cd test/install && \ + make save + +install-test-cache-load: $(SNAPSHOTDIR) + cd test/install && \ + make load + +install-test-ci-mac: $(SNAPSHOTDIR) + cd test/install && \ + make ci-test-mac + +.PHONY: integration +integration: ## Run integration tests + $(call title,Running integration tests) + go test -v ./test/integration + +# note: this is used by CI to determine if the integration test fixture cache (docker image tars) should be busted +integration-fingerprint: + $(call title,Integration test fixture fingerprint) + find test/integration/test-fixtures/image-* -type f -exec md5sum {} + | awk '{print $1}' | sort | tee /dev/stderr | md5sum | tee test/integration/test-fixtures/cache.fingerprint && echo "$(INTEGRATION_CACHE_BUSTER)" >> test/integration/test-fixtures/cache.fingerprint + +.PHONY: java-packages-fingerprint +java-packages-fingerprint: + $(call title,Java test fixture fingerprint) + cd syft/pkg/cataloger/java/test-fixtures/java-builds && \ + make packages.fingerprint + +.PHONY: go-binaries-fingerprint +go-binaries-fingerprint: + $(call title,Go binaries test fixture fingerprint) + cd syft/pkg/cataloger/golang/test-fixtures/archs && \ + make binaries.fingerprint + +.PHONY: rpm-binaries-fingerprint +rpm-binaries-fingerprint: + $(call title,RPM binary test fixture fingerprint) + cd syft/pkg/cataloger/rpm/test-fixtures && \ + make rpms.fingerprint + +.PHONY: fixtures +fixtures: + $(call title,Generating test fixtures) + cd syft/pkg/cataloger/java/test-fixtures/java-builds && make + cd syft/pkg/cataloger/rpm/test-fixtures && make + +.PHONY: generate-json-schema +generate-json-schema: ## Generate a new json schema + cd schema/json && go run generate.go + +.PHONY: generate-license-list +generate-license-list: ## Generate an updated spdx license list + go generate ./internal/spdxlicense/... + gofmt -s -w ./internal/spdxlicense + +.PHONY: build +build: $(SNAPSHOTDIR) ## Build release snapshot binaries and packages + +$(SNAPSHOTDIR): ## Build snapshot release binaries and packages + $(call title,Building snapshot artifacts) + + # create a config with the dist dir overridden + echo "dist: $(SNAPSHOTDIR)" > $(TEMPDIR)/goreleaser.yaml + cat .goreleaser.yaml >> $(TEMPDIR)/goreleaser.yaml + + # build release snapshots + bash -c "SKIP_SIGNING=true $(SNAPSHOT_CMD) --skip-sign --config $(TEMPDIR)/goreleaser.yaml" + +.PHONY: snapshot-with-signing +snapshot-with-signing: ## Build snapshot release binaries and packages (with dummy signing) + $(call title,Building snapshot artifacts (+ signing)) + + # create a config with the dist dir overridden + echo "dist: $(SNAPSHOTDIR)" > $(TEMPDIR)/goreleaser.yaml + cat .goreleaser.yaml >> $(TEMPDIR)/goreleaser.yaml + + rm -f .github/scripts/apple-signing/log/*.txt + + # build release snapshots + bash -c "$(SNAPSHOT_CMD) --config $(TEMPDIR)/goreleaser.yaml || (cat .github/scripts/apple-signing/log/*.txt && false)" + + # remove the keychain with the trusted self-signed cert automatically + .github/scripts/apple-signing/cleanup.sh + +snapshot-docker-assets: # Build snapshot images of docker images that will be published on release + $(call title,Building snapshot docker release assets) + + # create a config with the dist dir overridden + echo "dist: $(DISTDIR)" > $(TEMPDIR)/goreleaser.yaml + cat .goreleaser_docker.yaml >> $(TEMPDIR)/goreleaser.yaml + + bash -c "\ + $(SNAPSHOT_CMD) \ + --config $(TEMPDIR)/goreleaser.yaml \ + --parallelism 1" + +# note: we cannot clean the snapshot directory since the pipeline builds the snapshot separately +.PHONY: compare-mac +compare-mac: $(RESULTSDIR) $(SNAPSHOTDIR) ## Run compare tests on build snapshot binaries and packages (Mac) + $(call title,Running compare test: Run on Mac) + $(COMPARE_DIR)/mac.sh \ + $(SNAPSHOTDIR) \ + $(COMPARE_DIR) \ + $(COMPARE_TEST_IMAGE) \ + $(RESULTSDIR) + +# note: we cannot clean the snapshot directory since the pipeline builds the snapshot separately +.PHONY: compare-linux +compare-linux: compare-test-deb-package-install compare-test-rpm-package-install ## Run compare tests on build snapshot binaries and packages (Linux) + +.PHONY: compare-test-deb-package-install +compare-test-deb-package-install: $(RESULTSDIR) $(SNAPSHOTDIR) + $(call title,Running compare test: DEB install) + $(COMPARE_DIR)/deb.sh \ + $(SNAPSHOTDIR) \ + $(COMPARE_DIR) \ + $(COMPARE_TEST_IMAGE) \ + $(RESULTSDIR) + +.PHONY: compare-test-rpm-package-install +compare-test-rpm-package-install: $(RESULTSDIR) $(SNAPSHOTDIR) + $(call title,Running compare test: RPM install) + $(COMPARE_DIR)/rpm.sh \ + $(SNAPSHOTDIR) \ + $(COMPARE_DIR) \ + $(COMPARE_TEST_IMAGE) \ + $(RESULTSDIR) + +# note: this is used by CI to determine if the integration test fixture cache (docker image tars) should be busted +cli-fingerprint: + $(call title,CLI test fixture fingerprint) + find test/cli/test-fixtures/image-* -type f -exec md5sum {} + | awk '{print $1}' | sort | md5sum | tee test/cli/test-fixtures/cache.fingerprint && echo "$(CLI_CACHE_BUSTER)" >> test/cli/test-fixtures/cache.fingerprint + +.PHONY: cli +cli: $(SNAPSHOTDIR) ## Run CLI tests + chmod 755 "$(SNAPSHOT_BIN)" + $(SNAPSHOT_BIN) version + SYFT_BINARY_LOCATION='$(SNAPSHOT_BIN)' \ + go test -count=1 -timeout=15m -v ./test/cli + +.PHONY: changelog +changelog: clean-changelog CHANGELOG.md + @docker run -it --rm \ + -v $(shell pwd)/CHANGELOG.md:/CHANGELOG.md \ + rawkode/mdv \ + -t 748.5989 \ + /CHANGELOG.md + +CHANGELOG.md: + $(TEMPDIR)/chronicle -vv > CHANGELOG.md + +.PHONY: release +release: clean-dist CHANGELOG.md ## Build and publish final binaries and packages. Intended to be run only on macOS. + $(call title,Publishing release artifacts) + + # create a config with the dist dir overridden + echo "dist: $(DISTDIR)" > $(TEMPDIR)/goreleaser.yaml + cat .goreleaser.yaml >> $(TEMPDIR)/goreleaser.yaml + + rm -f .github/scripts/apple-signing/log/*.txt + + # note: notarization cannot be done in parallel, thus --parallelism 1 + bash -c "\ + $(RELEASE_CMD) \ + --config $(TEMPDIR)/goreleaser.yaml \ + --parallelism 1 \ + --release-notes <(cat CHANGELOG.md)\ + || (cat .github/scripts/apple-signing/log/*.txt && false)" + + cat .github/scripts/apple-signing/log/*.txt + + # TODO: turn this into a post-release hook + # upload the version file that supports the application version update check (excluding pre-releases) + .github/scripts/update-version-file.sh "$(DISTDIR)" "$(VERSION)" + +.PHONY: release-docker-assets +release-docker-assets: + $(call title,Publishing docker release assets) + + # create a config with the dist dir overridden + echo "dist: $(DISTDIR)" > $(TEMPDIR)/goreleaser.yaml + cat .goreleaser_docker.yaml >> $(TEMPDIR)/goreleaser.yaml + + bash -c "\ + $(RELEASE_CMD) \ + --config $(TEMPDIR)/goreleaser.yaml \ + --parallelism 1" + +.PHONY: clean +clean: clean-dist clean-snapshot clean-test-image-cache ## Remove previous builds, result reports, and test cache + $(call safe_rm_rf_children,$(RESULTSDIR)) + +.PHONY: clean-snapshot +clean-snapshot: + $(call safe_rm_rf,$(SNAPSHOTDIR)) + rm -f $(TEMPDIR)/goreleaser.yaml + +.PHONY: clean-dist +clean-dist: clean-changelog + $(call safe_rm_rf,$(DISTDIR)) + rm -f $(TEMPDIR)/goreleaser.yaml + +.PHONY: clean-changelog +clean-changelog: + rm -f CHANGELOG.md + +clean-test-image-cache: clean-test-image-tar-cache clean-test-image-docker-cache + +.PHONY: clear-test-image-tar-cache +clean-test-image-tar-cache: ## Delete all test cache (built docker image tars) + find . -type f -wholename "**/test-fixtures/cache/stereoscope-fixture-*.tar" -delete + +.PHONY: clear-test-image-docker-cache +clean-test-image-docker-cache: ## Purge all test docker images + docker images --format '{{.ID}} {{.Repository}}' | grep stereoscope-fixture- | awk '{print $$1}' | uniq | xargs -r docker rmi --force + +.PHONY: show-test-image-cache +show-test-image-cache: ## Show all docker and image tar cache + $(call title,Docker daemon cache) + @docker images --format '{{.ID}} {{.Repository}}:{{.Tag}}' | grep stereoscope-fixture- | sort + + $(call title,Tar cache) + @find . -type f -wholename "**/test-fixtures/cache/stereoscope-fixture-*.tar" | sort + +.PHONY: show-test-snapshots +show-test-snapshots: ## Show all test snapshots + $(call title,Test snapshots) + @find . -type f -wholename "**/test-fixtures/snapshot/*" | sort diff --git a/ci/tools/openeuler-purl/syft-dev/README.md b/ci/tools/openeuler-purl/syft-dev/README.md new file mode 100644 index 0000000000000000000000000000000000000000..235285ef8a472ef014ef0cb2d9ece62851de3f42 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/README.md @@ -0,0 +1,668 @@ +

+ Cute pink owl syft logo +

+ +[![Validations](https://github.com/anchore/syft/actions/workflows/validations.yaml/badge.svg)](https://github.com/anchore/syft/actions/workflows/validations.yaml) +[![Go Report Card](https://goreportcard.com/badge/github.com/anchore/syft)](https://goreportcard.com/report/github.com/anchore/syft) +[![GitHub release](https://img.shields.io/github/release/anchore/syft.svg)](https://github.com/anchore/syft/releases/latest) +[![GitHub go.mod Go version](https://img.shields.io/github/go-mod/go-version/anchore/syft.svg)](https://github.com/anchore/syft) +[![License: Apache-2.0](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://github.com/anchore/syft/blob/main/LICENSE) +[![Slack Invite](https://img.shields.io/badge/Slack-Join-blue?logo=slack)](https://anchore.com/slack) + +A CLI tool and Go library for generating a Software Bill of Materials (SBOM) from container images and filesystems. Exceptional for vulnerability detection when used with a scanner like [Grype](https://github.com/anchore/grype). + +### Join our community meetings! + +- Calendar: https://calendar.google.com/calendar/u/0/r?cid=Y182OTM4dGt0MjRtajI0NnNzOThiaGtnM29qNEBncm91cC5jYWxlbmRhci5nb29nbGUuY29t +- Agenda: https://docs.google.com/document/d/1ZtSAa6fj2a6KRWviTn3WoJm09edvrNUp4Iz_dOjjyY8/edit?usp=sharing (join [this group](https://groups.google.com/g/anchore-oss-community) for write access) +- All are welcome! + +For commercial support options with Syft or Grype, please [contact Anchore](https://get.anchore.com/contact/) + +![syft-demo](https://user-images.githubusercontent.com/590471/90277200-2a253000-de33-11ea-893f-32c219eea11a.gif) + +## Features +- Generates SBOMs for container images, filesystems, archives, and more to discover packages and libraries +- Supports OCI, Docker and [Singularity](https://github.com/sylabs/singularity) image formats +- Linux distribution identification +- Works seamlessly with [Grype](https://github.com/anchore/grype) (a fast, modern vulnerability scanner) +- Able to create signed SBOM attestations using the [in-toto specification](https://github.com/in-toto/attestation/blob/main/spec/README.md) +- Convert between SBOM formats, such as CycloneDX, SPDX, and Syft's own format. + +### Supported Ecosystems + +- Alpine (apk) +- C (conan) +- C++ (conan) +- Dart (pubs) +- Debian (dpkg) +- Dotnet (deps.json) +- Objective-C (cocoapods) +- Go (go.mod, Go binaries) +- Haskell (cabal, stack) +- Java (jar, ear, war, par, sar) +- JavaScript (npm, yarn) +- Jenkins Plugins (jpi, hpi) +- PHP (composer) +- Python (wheel, egg, poetry, requirements.txt) +- Red Hat (rpm) +- Ruby (gem) +- Rust (cargo.lock) +- Swift (cocoapods) + +## Installation + +**Note**: Currently, Syft is built only for Linux, macOS and Windows. + +### Recommended +```bash +curl -sSfL https://raw.githubusercontent.com/anchore/syft/main/install.sh | sh -s -- -b /usr/local/bin +``` + +... or, you can specify a release version and destination directory for the installation: + +``` +curl -sSfL https://raw.githubusercontent.com/anchore/syft/main/install.sh | sh -s -- -b +``` + +### Chocolatey + +The chocolatey distribution of syft is community maintained and not distributed by the anchore team + +```powershell +choco install syft -y +``` + +### Homebrew +```bash +brew tap anchore/syft +brew install syft +``` + +### Nix + +**Note**: Nix packaging of Syft is [community maintained](https://github.com/NixOS/nixpkgs/blob/master/pkgs/tools/admin/syft/default.nix). Syft is currently only in the [unstable channel](https://nixos.wiki/wiki/Nix_channels#The_official_channels) awaiting the `22.05` release + +```bash +nix-env -i syft +``` + +... or, just try it out in an ephemeral nix shell: + +```bash +nix-shell -p syft +``` + +## Getting started + +### SBOM + +To generate an SBOM for a container image: + +``` +syft +``` + +The above output includes only software that is visible in the container (i.e., the squashed representation of the image). To include software from all image layers in the SBOM, regardless of its presence in the final image, provide `--scope all-layers`: + +``` +syft --scope all-layers +``` + + + +## Supported sources + +Syft can generate a SBOM from a variety of sources: + +``` +# catalog a container image archive (from the result of `docker image save ...`, `podman save ...`, or `skopeo copy` commands) +syft path/to/image.tar + +# catalog a Singularity Image Format (SIF) container +syft path/to/image.sif + +# catalog a directory +syft path/to/dir +``` + +Sources can be explicitly provided with a scheme: + +``` +docker:yourrepo/yourimage:tag use images from the Docker daemon +podman:yourrepo/yourimage:tag use images from the Podman daemon +docker-archive:path/to/yourimage.tar use a tarball from disk for archives created from "docker save" +oci-archive:path/to/yourimage.tar use a tarball from disk for OCI archives (from Skopeo or otherwise) +oci-dir:path/to/yourimage read directly from a path on disk for OCI layout directories (from Skopeo or otherwise) +singularity:path/to/yourimage.sif read directly from a Singularity Image Format (SIF) container on disk +dir:path/to/yourproject read directly from a path on disk (any directory) +file:path/to/yourproject/file read directly from a path on disk (any single file) +registry:yourrepo/yourimage:tag pull image directly from a registry (no container runtime required) +``` + +#### Default Cataloger Configuration by scan type + +##### Image Scanning: +- alpmdb +- rpmdb +- dpkgdb +- apkdb +- portage +- ruby-gemspec +- python-package +- php-composer-installed Cataloger +- javascript-package +- java +- go-module-binary +- dotnet-deps + +##### Directory Scanning: +- alpmdb +- apkdb +- dpkgdb +- portage +- rpmdb +- ruby-gemfile +- python-index +- python-package +- php-composer-lock +- javascript-lock +- java +- java-pom +- go-module-binary +- go-mod-file +- rust-cargo-lock +- dartlang-lock +- dotnet-deps +- cocoapods +- conan +- hackage + +#### Non Default: +- cargo-auditable-binary + +### Excluding file paths + +Syft can exclude files and paths from being scanned within a source by using glob expressions +with one or more `--exclude` parameters: +``` +syft --exclude './out/**/*.json' --exclude /etc +``` +**Note:** in the case of _image scanning_, since the entire filesystem is scanned it is +possible to use absolute paths like `/etc` or `/usr/**/*.txt` whereas _directory scans_ +exclude files _relative to the specified directory_. For example: scanning `/usr/foo` with +`--exclude ./package.json` would exclude `/usr/foo/package.json` and `--exclude '**/package.json'` +would exclude all `package.json` files under `/usr/foo`. For _directory scans_, +it is required to begin path expressions with `./`, `*/`, or `**/`, all of which +will be resolved _relative to the specified scan directory_. Keep in mind, your shell +may attempt to expand wildcards, so put those parameters in single quotes, like: +`'**/*.json'`. + +### Output formats + +The output format for Syft is configurable as well using the +`-o` (or `--output`) option: + +``` +syft -o +``` + +Where the `formats` available are: +- `json`: Use this to get as much information out of Syft as possible! +- `text`: A row-oriented, human-and-machine-friendly output. +- `cyclonedx-xml`: A XML report conforming to the [CycloneDX 1.4 specification](https://cyclonedx.org/specification/overview/). +- `cyclonedx-json`: A JSON report conforming to the [CycloneDX 1.4 specification](https://cyclonedx.org/specification/overview/). +- `spdx-tag-value`: A tag-value formatted report conforming to the [SPDX 2.2 specification](https://spdx.github.io/spdx-spec/). +- `spdx-json`: A JSON report conforming to the [SPDX 2.2 JSON Schema](https://github.com/spdx/spdx-spec/blob/v2.2/schemas/spdx-schema.json). +- `github`: A JSON report conforming to GitHub's dependency snapshot format. +- `table`: A columnar summary (default). +- `template`: Lets the user specify the output format. See ["Using templates"](#using-templates) below. + +## Using templates + +Syft lets you define custom output formats, using [Go templates](https://pkg.go.dev/text/template). Here's how it works: + +- Define your format as a Go template, and save this template as a file. + +- Set the output format to "template" (`-o template`). + +- Specify the path to the template file (`-t ./path/to/custom.template`). + +- Syft's template processing uses the same data models as the `json` output format — so if you're wondering what data is available as you author a template, you can use the output from `syft -o json` as a reference. + +**Example:** You could make Syft output data in CSV format by writing a Go template that renders CSV data and then running `syft -o template -t ~/path/to/csv.tmpl`. + +Here's what the `csv.tmpl` file might look like: +```gotemplate +"Package","Version Installed","Found by" +{{- range .Artifacts}} +"{{.Name}}","{{.Version}}","{{.FoundBy}}" +{{- end}} +``` + +Which would produce output like: +```text +"Package","Version Installed","Found by" +"alpine-baselayout","3.2.0-r20","apkdb-cataloger" +"alpine-baselayout-data","3.2.0-r20","apkdb-cataloger" +"alpine-keys","2.4-r1","apkdb-cataloger" +... +``` + +Syft also includes a vast array of utility templating functions from [sprig](http://masterminds.github.io/sprig/) apart from the default Golang [text/template](https://pkg.go.dev/text/template#hdr-Functions) to allow users to customize the output format. + +## Multiple outputs + +Syft can also output _multiple_ files in differing formats by appending +`=` to the option, for example to output Syft JSON and SPDX JSON: + +```shell +syft -o json=sbom.syft.json -o spdx-json=sbom.spdx.json +``` + +## Private Registry Authentication + +### Local Docker Credentials +When a container runtime is not present, Syft can still utilize credentials configured in common credential sources (such as `~/.docker/config.json`). It will pull images from private registries using these credentials. The config file is where your credentials are stored when authenticating with private registries via some command like `docker login`. For more information see the `go-containerregistry` [documentation](https://github.com/google/go-containerregistry/tree/main/pkg/authn). + +An example `config.json` looks something like this: +```json +{ + "auths": { + "registry.example.com": { + "username": "AzureDiamond", + "password": "hunter2" + } + } +} +``` + +You can run the following command as an example. It details the mount/environment configuration a container needs to access a private registry: + +``` +docker run -v ./config.json:/config/config.json -e "DOCKER_CONFIG=/config" anchore/syft:latest +``` + +### Docker Credentials in Kubernetes + +Here's a simple workflow to mount this config file as a secret into a container on Kubernetes. + +1. Create a secret. The value of `config.json` is important. It refers to the specification detailed [here](https://github.com/google/go-containerregistry/tree/main/pkg/authn#the-config-file). Below this section is the `secret.yaml` file that the pod configuration will consume as a volume. The key `config.json` is important. It will end up being the name of the file when mounted into the pod. + + ```yaml + # secret.yaml + + apiVersion: v1 + kind: Secret + metadata: + name: registry-config + namespace: syft + data: + config.json: + ``` + + `kubectl apply -f secret.yaml` + + +2. Create your pod running syft. The env `DOCKER_CONFIG` is important because it advertises where to look for the credential file. In the below example, setting `DOCKER_CONFIG=/config` informs syft that credentials can be found at `/config/config.json`. This is why we used `config.json` as the key for our secret. When mounted into containers the secrets' key is used as the filename. The `volumeMounts` section mounts our secret to `/config`. The `volumes` section names our volume and leverages the secret we created in step one. + + ```yaml + # pod.yaml + + apiVersion: v1 + kind: Pod + metadata: + name: syft-k8s-usage + spec: + containers: + - image: anchore/syft:latest + name: syft-private-registry-demo + env: + - name: DOCKER_CONFIG + value: /config + volumeMounts: + - mountPath: /config + name: registry-config + readOnly: true + args: + - + volumes: + - name: registry-config + secret: + secretName: registry-config + ``` + + `kubectl apply -f pod.yaml` + + +3. The user can now run `kubectl logs syft-private-registry-demo`. The logs should show the Syft analysis for the `` provided in the pod configuration. + +Using the above information, users should be able to configure private registry access without having to do so in the `grype` or `syft` configuration files. They will also not be dependent on a Docker daemon, (or some other runtime software) for registry configuration and access. + +## Format conversion (experimental) + +The ability to convert existing SBOMs means you can create SBOMs in different formats quickly, without the need to regenerate the SBOM from scratch, which may take significantly more time. + +``` +syft convert -o [=] +``` + +This feature is experimental and data might be lost when converting formats. Packages are the main SBOM component easily transferable across formats, whereas files and relationships, as well as other information Syft doesn't support, are more likely to be lost. + +We support formats with wide community usage AND good encode/decode support by Syft. The supported formats are: +- Syft JSON +- SPDX 2.2 JSON +- SPDX 2.2 tag-value +- CycloneDX 1.4 JSON +- CycloneDX 1.4 XML + +Conversion example: +```sh +syft alpine:latest -o syft-json=sbom.syft.json # generate a syft SBOM +syft convert sbom.syft.json -o cyclonedx-json=sbom.cdx.json # convert it to CycloneDX +``` + +## Attestation (experimental) +### Keyless support +Syft supports generating attestations using cosign's [keyless](https://github.com/sigstore/cosign/blob/main/KEYLESS.md) signatures. + +To use this feature with a format like CycloneDX json simply run: +``` +syft attest --output cyclonedx-json +``` +This command will open a web browser and allow the user to authenticate their OIDC identity as the root of trust for the attestation (Github, Google, Microsoft). + +After authenticating, Syft will upload the attestation to the OCI registry specified by the image that the user has write access to. + +You will need to make sure your credentials are configured for the OCI registry you are uploading to so that the attestation can write successfully. + +Users can then verify the attestation(or any image with attestations) by running: +``` +COSIGN_EXPERIMENTAL=1 cosign verify-attestation +``` + +Users should see that the uploaded attestation claims are validated, the claims exist within the transparency log, and certificates on the attestations were verified against [fulcio](https://github.com/SigStore/fulcio). +There will also be a printout of the certificates subject `` and the certificate issuer URL: ``: +``` +Certificate subject: test.email@testdomain.com +Certificate issuer URL: https://accounts.google.com +``` + +#### Local private key support + +To generate an SBOM attestation for a container image using a local private key: +``` +syft attest --output [FORMAT] --key [KEY] [SOURCE] [flags] +``` + +The above output is in the form of the [DSSE envelope](https://github.com/secure-systems-lab/dsse/blob/master/envelope.md#dsse-envelope). +The payload is a base64 encoded `in-toto` statement with the generated SBOM as the predicate. For details on workflows using this command see [here](#adding-an-sbom-to-an-image-as-an-attestation-using-syft). + + + +## Configuration + +Configuration search paths: + +- `.syft.yaml` +- `.syft/config.yaml` +- `~/.syft.yaml` +- `/syft/config.yaml` + +Configuration options (example values are the default): + +```yaml +# the output format(s) of the SBOM report (options: table, text, json, spdx, ...) +# same as -o, --output, and SYFT_OUTPUT env var +# to specify multiple output files in differing formats, use a list: +# output: +# - "json=" +# - "spdx-json=" +output: "table" + +# suppress all output (except for the SBOM report) +# same as -q ; SYFT_QUIET env var +quiet: false + +# same as --file; write output report to a file (default is to write to stdout) +file: "" + +# enable/disable checking for application updates on startup +# same as SYFT_CHECK_FOR_APP_UPDATE env var +check-for-app-update: true + +# a list of globs to exclude from scanning. same as --exclude ; for example: +# exclude: +# - "/etc/**" +# - "./out/**/*.json" +exclude: [] + +# os and/or architecture to use when referencing container images (e.g. "windows/armv6" or "arm64") +# same as --platform; SYFT_PLATFORM env var +platform: "" + +# set the list of package catalogers to use when generating the SBOM +# default = empty (cataloger set determined automatically by the source type [image or file/directory]) +# catalogers: +# - ruby-gemfile +# - ruby-gemspec +# - python-index +# - python-package +# - javascript-lock +# - javascript-package +# - php-composer-installed +# - php-composer-lock +# - alpmdb +# - dpkgdb +# - rpmdb +# - java +# - apkdb +# - go-module-binary +# - go-mod-file +# - dartlang-lock +# - rust +# - dotnet-deps +# rust-audit-binary scans Rust binaries built with https://github.com/Shnatsel/rust-audit +# - rust-audit-binary +catalogers: + +# cataloging packages is exposed through the packages and power-user subcommands +package: + + # search within archives that do contain a file index to search against (zip) + # note: for now this only applies to the java package cataloger + # SYFT_PACKAGE_SEARCH_INDEXED_ARCHIVES env var + search-indexed-archives: true + + # search within archives that do not contain a file index to search against (tar, tar.gz, tar.bz2, etc) + # note: enabling this may result in a performance impact since all discovered compressed tars will be decompressed + # note: for now this only applies to the java package cataloger + # SYFT_PACKAGE_SEARCH_UNINDEXED_ARCHIVES env var + search-unindexed-archives: false + + cataloger: + # enable/disable cataloging of packages + # SYFT_PACKAGE_CATALOGER_ENABLED env var + enabled: true + + # the search space to look for packages (options: all-layers, squashed) + # same as -s ; SYFT_PACKAGE_CATALOGER_SCOPE env var + scope: "squashed" + +# cataloging file classifications is exposed through the power-user subcommand +file-classification: + cataloger: + # enable/disable cataloging of file classifications + # SYFT_FILE_CLASSIFICATION_CATALOGER_ENABLED env var + enabled: true + + # the search space to look for file classifications (options: all-layers, squashed) + # SYFT_FILE_CLASSIFICATION_CATALOGER_SCOPE env var + scope: "squashed" + +# cataloging file contents is exposed through the power-user subcommand +file-contents: + cataloger: + # enable/disable cataloging of secrets + # SYFT_FILE_CONTENTS_CATALOGER_ENABLED env var + enabled: true + + # the search space to look for secrets (options: all-layers, squashed) + # SYFT_FILE_CONTENTS_CATALOGER_SCOPE env var + scope: "squashed" + + # skip searching a file entirely if it is above the given size (default = 1MB; unit = bytes) + # SYFT_FILE_CONTENTS_SKIP_FILES_ABOVE_SIZE env var + skip-files-above-size: 1048576 + + # file globs for the cataloger to match on + # SYFT_FILE_CONTENTS_GLOBS env var + globs: [] + +# cataloging file metadata is exposed through the power-user subcommand +file-metadata: + cataloger: + # enable/disable cataloging of file metadata + # SYFT_FILE_METADATA_CATALOGER_ENABLED env var + enabled: true + + # the search space to look for file metadata (options: all-layers, squashed) + # SYFT_FILE_METADATA_CATALOGER_SCOPE env var + scope: "squashed" + + # the file digest algorithms to use when cataloging files (options: "sha256", "md5", "sha1") + # SYFT_FILE_METADATA_DIGESTS env var + digests: ["sha256"] + +# cataloging secrets is exposed through the power-user subcommand +secrets: + cataloger: + # enable/disable cataloging of secrets + # SYFT_SECRETS_CATALOGER_ENABLED env var + enabled: true + + # the search space to look for secrets (options: all-layers, squashed) + # SYFT_SECRETS_CATALOGER_SCOPE env var + scope: "all-layers" + + # show extracted secret values in the final JSON report + # SYFT_SECRETS_REVEAL_VALUES env var + reveal-values: false + + # skip searching a file entirely if it is above the given size (default = 1MB; unit = bytes) + # SYFT_SECRETS_SKIP_FILES_ABOVE_SIZE env var + skip-files-above-size: 1048576 + + # name-regex pairs to consider when searching files for secrets. Note: the regex must match single line patterns + # but may also have OPTIONAL multiline capture groups. Regexes with a named capture group of "value" will + # use the entire regex to match, but the secret value will be assumed to be entirely contained within the + # "value" named capture group. + additional-patterns: {} + + # names to exclude from the secrets search, valid values are: "aws-access-key", "aws-secret-key", "pem-private-key", + # "docker-config-auth", and "generic-api-key". Note: this does not consider any names introduced in the + # "secrets.additional-patterns" config option. + # SYFT_SECRETS_EXCLUDE_PATTERN_NAMES env var + exclude-pattern-names: [] + +# options when pulling directly from a registry via the "registry:" scheme +registry: + # skip TLS verification when communicating with the registry + # SYFT_REGISTRY_INSECURE_SKIP_TLS_VERIFY env var + insecure-skip-tls-verify: false + # use http instead of https when connecting to the registry + # SYFT_REGISTRY_INSECURE_USE_HTTP env var + insecure-use-http: false + + # credentials for specific registries + auth: + # the URL to the registry (e.g. "docker.io", "localhost:5000", etc.) + # SYFT_REGISTRY_AUTH_AUTHORITY env var + - authority: "" + # SYFT_REGISTRY_AUTH_USERNAME env var + username: "" + # SYFT_REGISTRY_AUTH_PASSWORD env var + password: "" + # note: token and username/password are mutually exclusive + # SYFT_REGISTRY_AUTH_TOKEN env var + token: "" + # - ... # note, more credentials can be provided via config file only + +# generate an attested SBOM +attest: + # path to the private key file to use for attestation + # SYFT_ATTEST_KEY env var + key: "cosign.key" + + # password to decrypt to given private key + # SYFT_ATTEST_PASSWORD env var, additionally responds to COSIGN_PASSWORD + password: "" + +log: + # use structured logging + # same as SYFT_LOG_STRUCTURED env var + structured: false + + # the log level; note: detailed logging suppress the ETUI + # same as SYFT_LOG_LEVEL env var + level: "error" + + # location to write the log file (default is not to have a log file) + # same as SYFT_LOG_FILE env var + file: "" + +# uploading package SBOM is exposed through the packages subcommand +anchore: + # (feature-preview) the Anchore Enterprise Host or URL to upload results to (supported on Enterprise 3.0+) + # same as -H ; SYFT_ANCHORE_HOST env var + host: "" + + # (feature-preview) the path after the host to the Anchore External API (supported on Enterprise 3.0+) + # same as SYFT_ANCHORE_PATH env var + path: "" + + # (feature-preview) the username to authenticate against Anchore Enterprise (supported on Enterprise 3.0+) + # same as -u ; SYFT_ANCHORE_USERNAME env var + username: "" + + # (feature-preview) the password to authenticate against Anchore Enterprise (supported on Enterprise 3.0+) + # same as -p ; SYFT_ANCHORE_PASSWORD env var + password: "" + + # (feature-preview) path to dockerfile to be uploaded with the syft results to Anchore Enterprise (supported on Enterprise 3.0+) + # same as -d ; SYFT_ANCHORE_DOCKERFILE env var + dockerfile: "" +``` + +### Adding an SBOM to an image as an attestation using Syft + +`syft attest --output [FORMAT] --key [KEY] [SOURCE] [flags]` + +SBOMs themselves can serve as input to different analysis tools. [Grype](https://github.com/anchore/grype), a vulnerability scanner CLI tool from Anchore, is one such tool. Publishers of container images can use attestations to enable their consumers to trust Syft-generated SBOM descriptions of those container images. To create and provide these attestations, image publishers can run `syft attest` in conjunction with the [cosign](https://github.com/sigstore/cosign) tool to attach SBOM attestations to their images. + +#### Example attestation +Note for the following example replace `docker.io/image:latest` with an image you own. You should also have push access to +its remote reference. Replace `$MY_PRIVATE_KEY` with a private key you own or have generated with cosign. + +```bash +syft attest --key $MY_PRIVATE_KEY docker.io/image:latest > image_latest_sbom_attestation.json +cosign attach attestation --attestation image_latest_sbom_attestation.json docker.io/image:latest +``` + +Verify the new attestation exists on your image. + +```bash +cosign verify-attestation -key $MY_PUBLIC_KEY docker.io/image:latest | jq '.payload | @base64d | .payload | fromjson | .predicate' +``` + +You should see this output along with the attached SBOM: + +``` +Verification for docker.io/image:latest -- +The following checks were performed on each of these signatures: + - The cosign claims were validated + - The signatures were verified against the specified public key + - Any certificates were verified against the Fulcio roots. +``` + +Consumers of your image can now trust that the SBOM associated with your image is correct and from a trusted source. diff --git a/ci/tools/openeuler-purl/syft-dev/RELEASE.md b/ci/tools/openeuler-purl/syft-dev/RELEASE.md new file mode 100644 index 0000000000000000000000000000000000000000..4d8362c269f058862ef3a64ad0ac996a314bcc44 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/RELEASE.md @@ -0,0 +1,104 @@ +# Release Process + +A good release process has the following qualities: + +1. There is a way to plan what should be in a release +1. There is a way to see what is actually in a release +1. Allow for different kinds of releases (major breaking vs backwards compatible + enhancements vs patch updates) +1. Specify a repeatable way to build and publish software artifacts + +## Planning a release + +To indicate a set of features to be released together add each issue to an in-repository +Milestone named with major-minor version to be released (e.g. `v0.1`). It is OK for other +features to be in the release that were not originally planned, and these issues and PRs +do not need to be added to the Milestone in question. Only the set of features that, when +completed, would allow the release to be considered complete. A Milestone is only used to: + +- Plan what is desired to be in a release +- Track progress to indicate when we may be ready to cut a new release + +Not all releases need to be planned. For instance, patch releases for fixes should be +released when they are ready and when releasing would not interfere with another current +release (where some partial or breaking features have already been merged). Beta releases +and release candidates should not be independently planned from the non-beta release. That +is, the features for a `v0.1-beta.1` release should be planned under the `v0.1` Milestone, +not under a separate `v0.1-beta.1` Milestone. + +Unless necessary, feature releases should be small and frequent, which may obviate the +need for regular release planning under a Milestone. + +## What is in a release + +Milestones are specifically for planning a release, not necessarily tracking all changes +that a release may bring (and more importantly, not all releases are necessarily planned +either). + +This is one of the (many) reasons for a Changelog. A good Changelog lists changes grouped +by the type of change (new, enhancement, deprecation, breaking, bug fix, security fix), in +chronological order (within groups), linking the PR where the change was made in the +Changelog line. Furthermore, there should be a place to see all released versions, the +release date for each release, the semantic version of the release, and the set of changes +for each release. + +This project auto-generates the Changelog contents for each current release and posts the +generated contents to the GitHub Release page. Leveraging the GitHub Releases feature +allows GitHub to manage the Changelog on each release outside of the git repository while +still being hosted with the released assets. + +The Changelog is generated from the metadata from in-repository issues and PRs, using +labels to guide what kind of change each item is (e.g. breaking, new feature, bug fix, +etx). Only issues/PRs with select labels are included in the Changelog, and only if the +issue/PR was created after the last release. Additional labels are used to exclude items +from the Changelog. + +The above suggestions imply that we should: + +- Ensure there is a sufficient title for each PR and issue title to be included in the + Changelog +- The appropriate label is applied to PRs and/or issues to drive specific change type + sections (deprecated, breaking, security, bug, etc) + +With this approach as we cultivate good organization of PRs and issues we automatically +get an equally good Changelog. + +## Major, minor, and patch releases + +The latest version of the tool is the only supported version, which implies that multiple +parallel release branches will not be a regular process (if ever). Multiple releases can +be planned in parallel, however, only one can be actively developed at a time. That is, if +PRs attached to a release Milestone have been merged into the main branch, that release is +now the "next" release. This implies that the source of truth for release lies with the +git log and Changelog, not with the release Milestones (which are purely for planning and +tracking). + +Semantic versioning should be used to indicate breaking changes, new features, and fixes. +The exception to this is `< 1.0`, where the major version is not bumped for breaking changes, +instead the minor version indicates both new features and breaking changes. + +## Cutting a release + +Ideally releasing should be done often with small increments when possible. Unless a +breaking change is blocking the release, or no fixes/features have been merged, a good +target release cadence is between every 2 or 4 weeks. + +This release process itself should be as automated as possible, and have only a few steps: + +1. Tag the main branch with a full semantic-version, prefixed with a `v`. If there is a + milestone with a partial version, the full version should be used for the git tag (e.g. + with a Milestone of `v0.1` the tag should be `v0.1.0`). You can determine the changes going + into a release by running `make changelog-unreleased`. Use this change list to determine the + release increment. After determining the release increment (major, minor, patch), create the tag. + Given the above example the command to create the tag would be `git tag v0.1.0`. + +1. Push the tag. Given the above example the command to push the tag would be `git push origin v0.1.0`. + +1. A release admin must approve the release on the GitHub Actions release pipeline run page. + Once approved, the release pipeline will generate all assets and draft a GitHub Release. + +1. Navigate to the GitHub Release draft page to review the final changelog and publish the + release. Once published, a release-follow-up pipeline will publish derivative artifacts + (docker image to DockerHub, brew formula to the external homebrew git repo, etc). + +1. If there is a release Milestone, close it. diff --git a/ci/tools/openeuler-purl/syft-dev/artifacthub-repo.yml b/ci/tools/openeuler-purl/syft-dev/artifacthub-repo.yml new file mode 100644 index 0000000000000000000000000000000000000000..35cb6b8cbaad954ce398d3baec04b6f794965c12 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/artifacthub-repo.yml @@ -0,0 +1,5 @@ +# See documentation here: https://github.com/artifacthub/hub/blob/v1.6.0/docs/metadata/artifacthub-repo.yml + +owners: + - name: wagoodman + email: wagoodman@gmail.com diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest.go new file mode 100644 index 0000000000000000000000000000000000000000..e102144d2b622339d0beb29ea6cde1b94157c1c8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest.go @@ -0,0 +1,80 @@ +package cli + +import ( + "fmt" + "log" + + "github.com/anchore/syft/cmd/syft/cli/attest" + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/config" + "github.com/spf13/cobra" + "github.com/spf13/viper" + + sigopts "github.com/sigstore/cosign/cmd/cosign/cli/options" +) + +const ( + attestExample = ` {{.appName}} {{.command}} --output [FORMAT] --key [KEY] alpine:latest + Supports the following image sources: + {{.appName}} {{.command}} --key [KEY] yourrepo/yourimage:tag defaults to using images from a Docker daemon. If Docker is not present, the image is pulled directly from the registry. + {{.appName}} {{.command}} --key [KEY] path/to/a/file/or/dir only for OCI tar or OCI directory +` + attestSchemeHelp = "\n" + indent + schemeHelpHeader + "\n" + imageSchemeHelp + + attestHelp = attestExample + attestSchemeHelp +) + +func Attest(v *viper.Viper, app *config.Application, ro *options.RootOptions) *cobra.Command { + ao := options.AttestOptions{} + cmd := &cobra.Command{ + Use: "attest --output [FORMAT] --key [KEY] [SOURCE]", + Short: "Generate a package SBOM as an attestation for the given [SOURCE] container image", + Long: "Generate a packaged-based Software Bill Of Materials (SBOM) from a container image as the predicate of an in-toto attestation", + Example: internal.Tprintf(attestHelp, map[string]interface{}{ + "appName": internal.ApplicationName, + "command": "attest", + }), + Args: func(cmd *cobra.Command, args []string) error { + // run to unmarshal viper object onto app config + // the viper object correctly + if err := app.LoadAllValues(v, ro.Config); err != nil { + return fmt.Errorf("invalid application config: %v", err) + } + // configure logging for command + newLogWrapper(app) + logApplicationConfig(app) + return validateArgs(cmd, args) + }, + SilenceUsage: true, + SilenceErrors: true, + RunE: func(cmd *cobra.Command, args []string) error { + // this MUST be called first to make sure app config decodes + // the viper object correctly + if app.CheckForAppUpdate { + checkForApplicationUpdate() + } + + // build cosign key options for attestation + ko := sigopts.KeyOpts{ + KeyRef: app.Attest.KeyRef, + FulcioURL: app.Attest.FulcioURL, + IDToken: app.Attest.FulcioIdentityToken, + InsecureSkipFulcioVerify: app.Attest.InsecureSkipFulcioVerify, + RekorURL: app.Attest.RekorURL, + OIDCIssuer: app.Attest.OIDCIssuer, + OIDCClientID: app.Attest.OIDCClientID, + OIDCRedirectURL: app.Attest.OIDCRedirectURL, + } + + return attest.Run(cmd.Context(), app, ko, args) + }, + } + + err := ao.AddFlags(cmd, v) + if err != nil { + log.Fatal(err) + } + + return cmd +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest/attest.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest/attest.go new file mode 100644 index 0000000000000000000000000000000000000000..d0d6d0d16252dec35f26bdd77cdddaa805ffa419 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest/attest.go @@ -0,0 +1,364 @@ +package attest + +import ( + "bytes" + "context" + "encoding/json" + "fmt" + "os" + + "github.com/wagoodman/go-progress" + + "github.com/anchore/stereoscope" + "github.com/anchore/stereoscope/pkg/image" + "github.com/anchore/syft/cmd/syft/cli/eventloop" + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/cmd/syft/cli/packages" + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/internal/formats/cyclonedxjson" + "github.com/anchore/syft/internal/formats/spdx22json" + "github.com/anchore/syft/internal/formats/syftjson" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/internal/ui" + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" + "github.com/google/go-containerregistry/pkg/name" + v1 "github.com/google/go-containerregistry/pkg/v1" + "github.com/in-toto/in-toto-golang/in_toto" + "github.com/pkg/errors" + sigopts "github.com/sigstore/cosign/cmd/cosign/cli/options" + "github.com/sigstore/cosign/cmd/cosign/cli/rekor" + "github.com/sigstore/cosign/cmd/cosign/cli/sign" + "github.com/sigstore/cosign/pkg/cosign" + "github.com/sigstore/cosign/pkg/cosign/attestation" + cbundle "github.com/sigstore/cosign/pkg/cosign/bundle" + "github.com/sigstore/cosign/pkg/oci/mutate" + ociremote "github.com/sigstore/cosign/pkg/oci/remote" + "github.com/sigstore/cosign/pkg/oci/static" + sigs "github.com/sigstore/cosign/pkg/signature" + "github.com/sigstore/cosign/pkg/types" + "github.com/sigstore/rekor/pkg/generated/client" + "github.com/sigstore/rekor/pkg/generated/models" + "github.com/sigstore/sigstore/pkg/signature/dsse" + "github.com/wagoodman/go-partybus" + + signatureoptions "github.com/sigstore/sigstore/pkg/signature/options" +) + +var ( + allowedAttestFormats = []sbom.FormatID{ + syftjson.ID, + spdx22json.ID, + cyclonedxjson.ID, + } + + intotoJSONDsseType = `application/vnd.in-toto+json` +) + +func Run(ctx context.Context, app *config.Application, ko sigopts.KeyOpts, args []string) error { + // We cannot generate an attestation for more than one output + if len(app.Outputs) > 1 { + return fmt.Errorf("unable to generate attestation for more than one output") + } + + // can only be an image for attestation or OCI DIR + userInput := args[0] + si, err := parseImageSource(userInput, app) + if err != nil { + return err + } + + format := syft.FormatByName(app.Outputs[0]) + predicateType := formatPredicateType(format) + if predicateType == "" { + return fmt.Errorf( + "could not produce attestation predicate for given format: %q. Available formats: %+v", + options.FormatAliases(format.ID()), + options.FormatAliases(allowedAttestFormats...), + ) + } + + if app.Attest.KeyRef != "" { + passFunc, err := selectPassFunc(app.Attest.KeyRef, app.Attest.Password) + if err != nil { + return err + } + + ko.PassFunc = passFunc + } + + sv, err := sign.SignerFromKeyOpts(ctx, "", "", ko) + if err != nil { + return err + } + defer sv.Close() + + eventBus := partybus.NewBus() + stereoscope.SetBus(eventBus) + syft.SetBus(eventBus) + subscription := eventBus.Subscribe() + + return eventloop.EventLoop( + execWorker(app, *si, format, predicateType, sv, app.File), + eventloop.SetupSignals(), + subscription, + stereoscope.Cleanup, + ui.Select(options.IsVerbose(app), app.Quiet)..., + ) +} + +func parseImageSource(userInput string, app *config.Application) (s *source.Input, err error) { + si, err := source.ParseInput(userInput, app.Platform, false) + if err != nil { + return nil, fmt.Errorf("could not generate source input for attest command: %w", err) + } + + switch si.Scheme { + case source.ImageScheme, source.UnknownScheme: + // at this point we know that it cannot be dir: or file: schemes; + // we will assume that the unknown scheme could represent an image; + si.Scheme = source.ImageScheme + default: + return nil, fmt.Errorf("attest command can only be used with image sources but discovered %q when given %q", si.Scheme, userInput) + } + + // if the original detection was from the local daemon we want to short circuit + // that and attempt to generate the image source from its current registry source instead + switch si.ImageSource { + case image.UnknownSource, image.OciRegistrySource: + si.ImageSource = image.OciRegistrySource + default: + return nil, fmt.Errorf("attest command can only be used with image sources fetch directly from the registry, but discovered an image source of %q when given %q", si.ImageSource, userInput) + } + + return si, nil +} + +func execWorker(app *config.Application, sourceInput source.Input, format sbom.Format, predicateType string, sv *sign.SignerVerifier, file string) <-chan error { + errs := make(chan error) + go func() { + defer close(errs) + + src, cleanup, err := source.NewFromRegistry(sourceInput, app.Registry.ToOptions(), app.Exclusions) + if cleanup != nil { + defer cleanup() + } + if err != nil { + errs <- fmt.Errorf("failed to construct source from user input %q: %w", sourceInput.UserInput, err) + return + } + + s, err := packages.GenerateSBOM(src, errs, app) + if err != nil { + errs <- err + return + } + + sbomBytes, err := syft.Encode(*s, format) + if err != nil { + errs <- err + return + } + + err = generateAttestation(app, sbomBytes, src, sv, predicateType, file) + if err != nil { + errs <- err + return + } + }() + return errs +} + +func generateAttestation(app *config.Application, predicate []byte, src *source.Source, sv *sign.SignerVerifier, predicateType string, file string) error { + switch len(src.Image.Metadata.RepoDigests) { + case 0: + return fmt.Errorf("cannot generate attestation since no repo digests were found; make sure you're passing an OCI registry source for the attest command") + case 1: + default: + return fmt.Errorf("cannot generate attestation since multiple repo digests were found for the image: %+v", src.Image.Metadata.RepoDigests) + } + + wrapped := dsse.WrapSigner(sv, intotoJSONDsseType) + ref, err := name.ParseReference(src.Metadata.ImageMetadata.UserInput) + if err != nil { + return err + } + + digest, err := ociremote.ResolveDigest(ref) + if err != nil { + return err + } + + h, _ := v1.NewHash(digest.Identifier()) + + sh, err := attestation.GenerateStatement(attestation.GenerateOpts{ + Predicate: bytes.NewBuffer(predicate), + Type: predicateType, + Digest: h.Hex, + }) + if err != nil { + return err + } + + payload, err := json.Marshal(sh) + if err != nil { + return err + } + + signedPayload, err := wrapped.SignMessage(bytes.NewReader(payload), signatureoptions.WithContext(context.Background())) + if err != nil { + return errors.Wrap(err, "unable to sign SBOM") + } + + // We want to give the option to not upload the generated attestation + // if passed or if the user is using local PKI + if app.Attest.NoUpload || app.Attest.KeyRef != "" { + bus.Publish(partybus.Event{ + Type: event.Exit, + Value: func() error { + var err error + if file != "" { + err = os.WriteFile(file, signedPayload, 0600) + } else { + _, err = os.Stdout.Write(signedPayload) + } + return err + }, + }) + return nil + } + + return uploadAttestation(app, signedPayload, digest, sv) +} + +func trackUploadAttestation() (*progress.Stage, *progress.Manual) { + stage := &progress.Stage{} + prog := &progress.Manual{} + + bus.Publish(partybus.Event{ + Type: event.UploadAttestation, + Value: progress.StagedProgressable(&struct { + progress.Stager + progress.Progressable + }{ + Stager: stage, + Progressable: prog, + }), + }) + + return stage, prog +} + +// uploads signed SBOM payload to Rekor transparency log along with key information; +// returns a bundle for attestation annotations +// rekor bundle includes a signed payload and rekor timestamp; +// the bundle is then wrapped onto an OCI signed entity and uploaded to +// the user's image's OCI registry repository as *.att +func uploadAttestation(app *config.Application, signedPayload []byte, digest name.Digest, sv *sign.SignerVerifier) error { + // add application/vnd.dsse.envelope.v1+json as media type for other applications to decode attestation + opts := []static.Option{static.WithLayerMediaType(types.DssePayloadType)} + if sv.Cert != nil { + opts = append(opts, static.WithCertChain(sv.Cert, sv.Chain)) + } + + stage, prog := trackUploadAttestation() + defer prog.SetCompleted() // just in case we return early + + prog.Total = 2 + stage.Current = "uploading signing information to transparency log" + + // uploads payload to Rekor transparency log along with key information; + // returns bundle for attesation annotations + // rekor bundle includes a signed payload and rekor timestamp; + // the bundle is then wrapped onto an OCI signed entity and uploaded to + // the user's image's OCI registry repository as *.att + bundle, err := uploadToTlog(context.TODO(), sv, app.Attest.RekorURL, func(r *client.Rekor, b []byte) (*models.LogEntryAnon, error) { + return cosign.TLogUploadInTotoAttestation(context.TODO(), r, signedPayload, b) + }) + if err != nil { + return err + } + + prog.N = 1 + stage.Current = "uploading attestation to OCI registry" + + // add bundle OCI attestation that is uploaded to + opts = append(opts, static.WithBundle(bundle)) + sig, err := static.NewAttestation(signedPayload, opts...) + if err != nil { + return err + } + + se, err := ociremote.SignedEntity(digest) + if err != nil { + return err + } + + newSE, err := mutate.AttachAttestationToEntity(se, sig) + if err != nil { + return err + } + + // Publish the attestations associated with this entity + err = ociremote.WriteAttestations(digest.Repository, newSE) + if err != nil { + return err + } + + prog.SetCompleted() + + bus.Publish(partybus.Event{ + Type: event.Exit, + Value: func() error { + return nil + }, + }) + return nil +} + +func formatPredicateType(format sbom.Format) string { + switch format.ID() { + case spdx22json.ID: + return in_toto.PredicateSPDX + case cyclonedxjson.ID: + // Tentative see https://github.com/in-toto/attestation/issues/82 + return "https://cyclonedx.org/bom" + case syftjson.ID: + return "https://syft.dev/bom" + default: + return "" + } +} + +type tlogUploadFn func(*client.Rekor, []byte) (*models.LogEntryAnon, error) + +func uploadToTlog(ctx context.Context, sv *sign.SignerVerifier, rekorURL string, upload tlogUploadFn) (*cbundle.RekorBundle, error) { + var rekorBytes []byte + // Upload the cert or the public key, depending on what we have + if sv.Cert != nil { + rekorBytes = sv.Cert + } else { + pemBytes, err := sigs.PublicKeyPem(sv, signatureoptions.WithContext(ctx)) + if err != nil { + return nil, err + } + rekorBytes = pemBytes + } + + rekorClient, err := rekor.NewClient(rekorURL) + if err != nil { + return nil, err + } + entry, err := upload(rekorClient, rekorBytes) + if err != nil { + return nil, err + } + + if entry.LogIndex != nil { + log.Debugf("transparency log entry created with index: %v", *entry.LogIndex) + } + return cbundle.EntryToBundle(entry), nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest/password.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest/password.go new file mode 100644 index 0000000000000000000000000000000000000000..89520a0e90bb593793958f4c6639c7571c54d2de --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/attest/password.go @@ -0,0 +1,56 @@ +package attest + +import ( + "errors" + "fmt" + "io" + "os" + "strings" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/sigstore/cosign/pkg/cosign" +) + +func selectPassFunc(keypath, password string) (cosign.PassFunc, error) { + keyContents, err := os.ReadFile(keypath) + if err != nil { + return nil, err + } + + var fn cosign.PassFunc = func(bool) (b []byte, err error) { return nil, nil } + + _, err = cosign.LoadPrivateKey(keyContents, nil) + if err != nil { + fn = func(bool) (b []byte, err error) { + return fetchPassword(password) + } + } + + return fn, nil +} + +func fetchPassword(password string) (b []byte, err error) { + potentiallyPipedInput, err := internal.IsPipedInput() + if err != nil { + log.Warnf("unable to determine if there is piped input: %+v", err) + } + + switch { + case password != "": + return []byte(password), nil + case potentiallyPipedInput: + // handle piped in passwords + pwBytes, err := io.ReadAll(os.Stdin) + if err != nil { + return nil, fmt.Errorf("unable to get password from stdin: %w", err) + } + // be resilient to input that may have newline characters (in case someone is using echo without -n) + cleanPw := strings.TrimRight(string(pwBytes), "\n") + return []byte(cleanPw), nil + case internal.IsTerminal(): + return cosign.GetPassFromTerm(false) + } + + return nil, errors.New("no method available to fetch password") +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/commands.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/commands.go new file mode 100644 index 0000000000000000000000000000000000000000..d1adaff78feac3017d69cf40e3527ba4ab752bce --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/commands.go @@ -0,0 +1,159 @@ +package cli + +import ( + "fmt" + "strings" + + "github.com/anchore/stereoscope" + "github.com/anchore/syft/internal/logger" + "github.com/anchore/syft/syft" + + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/internal/version" + "github.com/anchore/syft/syft/event" + cranecmd "github.com/google/go-containerregistry/cmd/crane/cmd" + "github.com/gookit/color" + "github.com/spf13/cobra" + "github.com/spf13/viper" + "github.com/wagoodman/go-partybus" +) + +const indent = " " + +// New constructs the `syft packages` command, aliases the root command to `syft packages`, +// and constructs the `syft power-user` and `syft attest` commands. It is also responsible for +// organizing flag usage and injecting the application config for each command. +// Because of how the `cobra` library behaves, the application's configuration is initialized +// at this level. Values from the config should only be used after `app.LoadAllValues` has been called. +// Cobra does not have knowledge of the user provided flags until the `RunE` block of each command. +// `RunE` is the earliest that the complete application configuration can be loaded. +// +//nolint:funlen +func New() (*cobra.Command, error) { + app := &config.Application{} + + // allow for nested options to be specified via environment variables + // e.g. pod.context = APPNAME_POD_CONTEXT + v := viper.NewWithOptions(viper.EnvKeyReplacer(strings.NewReplacer(".", "_", "-", "_"))) + + // since root is aliased as the packages cmd we need to construct this command first + // we also need the command to have information about the `root` options because of this alias + ro := &options.RootOptions{} + po := &options.PackagesOptions{} + packagesCmd := Packages(v, app, ro, po) + + // root options are also passed to the attestCmd so that a user provided config location can be discovered + attestCmd := Attest(v, app, ro) + poweruserCmd := PowerUser(v, app, ro) + convertCmd := Convert(v, app, ro, po) + + // rootCmd is currently an alias for the packages command + rootCmd := &cobra.Command{ + Short: packagesCmd.Short, + Long: packagesCmd.Long, + Args: packagesCmd.Args, + Example: packagesCmd.Example, + SilenceUsage: true, + SilenceErrors: true, + RunE: packagesCmd.RunE, + Version: version.FromBuild().Version, + } + rootCmd.SetVersionTemplate(fmt.Sprintf("%s {{.Version}}\n", internal.ApplicationName)) + + // start adding flags to all the commands + err := ro.AddFlags(rootCmd, v) + if err != nil { + return nil, err + } + // package flags need to be decorated onto the rootCmd so that rootCmd can function as a packages alias + err = po.AddFlags(rootCmd, v) + if err != nil { + return nil, err + } + // attest also uses flags from the packagesCmd since it generates an sbom + err = po.AddFlags(attestCmd, v) + if err != nil { + return nil, err + } + // poweruser also uses the packagesCmd flags since it is a specialized version of the command + err = po.AddFlags(poweruserCmd, v) + if err != nil { + return nil, err + } + + // commands to add to root + cmds := []*cobra.Command{ + packagesCmd, + attestCmd, + convertCmd, + poweruserCmd, + poweruserCmd, + Completion(), + Version(v, app), + cranecmd.NewCmdAuthLogin("syft"), + } + + // Add sub-commands. + for _, cmd := range cmds { + rootCmd.AddCommand(cmd) + } + + return rootCmd, err +} + +func validateArgs(cmd *cobra.Command, args []string) error { + if len(args) == 0 { + // in the case that no arguments are given we want to show the help text and return with a non-0 return code. + if err := cmd.Help(); err != nil { + return fmt.Errorf("unable to display help: %w", err) + } + return fmt.Errorf("an image/directory argument is required") + } + + return cobra.MaximumNArgs(1)(cmd, args) +} + +func checkForApplicationUpdate() { + log.Debugf("checking if new vesion of %s is available", internal.ApplicationName) + isAvailable, newVersion, err := version.IsUpdateAvailable() + if err != nil { + // this should never stop the application + log.Errorf(err.Error()) + } + if isAvailable { + log.Infof("new version of %s is available: %s (current version is %s)", internal.ApplicationName, newVersion, version.FromBuild().Version) + + bus.Publish(partybus.Event{ + Type: event.AppUpdateAvailable, + Value: newVersion, + }) + } else { + log.Debugf("no new %s update available", internal.ApplicationName) + } +} + +func logApplicationConfig(app *config.Application) { + versionInfo := version.FromBuild() + log.Infof("syft version: %+v", versionInfo.Version) + log.Debugf("application config:\n%+v", color.Magenta.Sprint(app.String())) +} + +func newLogWrapper(app *config.Application) { + cfg := logger.LogrusConfig{ + EnableConsole: (app.Log.FileLocation == "" || app.Verbosity > 0) && !app.Quiet, + EnableFile: app.Log.FileLocation != "", + Level: app.Log.LevelOpt, + Structured: app.Log.Structured, + FileLocation: app.Log.FileLocation, + } + + logWrapper := logger.NewLogrusLogger(cfg) + syft.SetLogger(logWrapper) + stereoscope.SetLogger(&logger.LogrusNestedLogger{ + Logger: logWrapper.Logger.WithField("from-lib", "stereoscope"), + }) +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/completion.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/completion.go new file mode 100644 index 0000000000000000000000000000000000000000..9896f8d732f2f95ba7962dce699fcd0c18df7ce6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/completion.go @@ -0,0 +1,54 @@ +package cli + +import ( + "os" + + "github.com/spf13/cobra" +) + +func Completion() *cobra.Command { + cmd := &cobra.Command{ + Use: "completion [bash|zsh|fish]", + Short: "Generate a shell completion for Syft (listing local docker images)", + Long: `To load completions (docker image list): + Bash: + $ source <(syft completion bash) +# To load completions for each session, execute once: + Linux: + $ syft completion bash > /etc/bash_completion.d/syft + MacOS: + $ syft completion bash > /usr/local/etc/bash_completion.d/syft + Zsh: +# If shell completion is not already enabled in your environment you will need +# to enable it. You can execute the following once: + $ echo "autoload -U compinit; compinit" >> ~/.zshrc +# To load completions for each session, execute once: + $ syft completion zsh > "${fpath[1]}/_syft" +# You will need to start a new shell for this setup to take effect. + Fish: + $ syft completion fish | source +# To load completions for each session, execute once: + $ syft completion fish > ~/.config/fish/completions/syft.fish + `, + DisableFlagsInUseLine: true, + ValidArgs: []string{"bash", "zsh", "fish"}, + Args: cobra.ExactValidArgs(1), + RunE: func(cmd *cobra.Command, args []string) error { + var err error + switch args[0] { + case "bash": + err = cmd.Root().GenBashCompletion(os.Stdout) + case "zsh": + err = cmd.Root().GenZshCompletion(os.Stdout) + case "fish": + err = cmd.Root().GenFishCompletion(os.Stdout, true) + } + if err != nil { + return err + } + return nil + }, + } + + return cmd +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/convert.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/convert.go new file mode 100644 index 0000000000000000000000000000000000000000..51e46e75df44e87ece6f49f6a799ee7d43f45839 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/convert.go @@ -0,0 +1,55 @@ +package cli + +import ( + "fmt" + "log" + + "github.com/anchore/syft/cmd/syft/cli/convert" + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/config" + "github.com/spf13/cobra" + "github.com/spf13/viper" +) + +const ( + convertExample = ` {{.appName}} {{.command}} img.syft.json -o spdx-json convert a syft SBOM to spdx-json, output goes to stdout in table format, by default + {{.appName}} {{.command}} img.syft.json -o cyclonedx-json=img.cdx.json convert a syft SBOM to CycloneDX, output goes to a file named img.cdx.json +` +) + +//nolint:dupl +func Convert(v *viper.Viper, app *config.Application, ro *options.RootOptions, po *options.PackagesOptions) *cobra.Command { + cmd := &cobra.Command{ + Use: "convert [SOURCE-SBOM] -o [FORMAT]", + Short: "Convert between SBOM formats", + Long: "[Experimental] Convert SBOM files to, and from, SPDX, CycloneDX and Syft's format. For more info about data loss between formats see https://github.com/anchore/syft#format-conversion-experimental", + Example: internal.Tprintf(convertExample, map[string]interface{}{ + "appName": internal.ApplicationName, + "command": "convert", + }), + Args: func(cmd *cobra.Command, args []string) error { + if err := app.LoadAllValues(v, ro.Config); err != nil { + return fmt.Errorf("invalid application config: %w", err) + } + newLogWrapper(app) + logApplicationConfig(app) + return validateArgs(cmd, args) + }, + SilenceUsage: true, + SilenceErrors: true, + RunE: func(cmd *cobra.Command, args []string) error { + if app.CheckForAppUpdate { + checkForApplicationUpdate() + } + return convert.Run(cmd.Context(), app, args) + }, + } + + err := po.AddFlags(cmd, v) + if err != nil { + log.Fatal(err) + } + + return cmd +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/convert/convert.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/convert/convert.go new file mode 100644 index 0000000000000000000000000000000000000000..d94fc38edbba44c2077049945fb7600efbf5f86d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/convert/convert.go @@ -0,0 +1,41 @@ +package convert + +import ( + "context" + "fmt" + "os" + + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft" +) + +func Run(ctx context.Context, app *config.Application, args []string) error { + log.Warn("convert is an experimental feature, run `syft convert -h` for help") + writer, err := options.MakeWriter(app.Outputs, app.File, "") + if err != nil { + return err + } + + defer func() { + if err := writer.Close(); err != nil { + log.Warnf("unable to write to report destination: %w", err) + } + }() + + // this can only be a SBOM file + userInput := args[0] + f, err := os.Open(userInput) + if err != nil { + return fmt.Errorf("failed to open SBOM file: %w", err) + } + defer f.Close() + + sbom, _, err := syft.Decode(f) + if err != nil { + return fmt.Errorf("failed to decode SBOM: %w", err) + } + + return writer.Write(*sbom) +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/event_loop.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/event_loop.go new file mode 100644 index 0000000000000000000000000000000000000000..396dd74919f9d306d83a8e576b32ff4821eeff81 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/event_loop.go @@ -0,0 +1,99 @@ +package eventloop + +import ( + "errors" + "fmt" + "os" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/internal/ui" + "github.com/hashicorp/go-multierror" + "github.com/wagoodman/go-partybus" +) + +// eventLoop listens to worker errors (from execution path), worker events (from a partybus subscription), and +// signal interrupts. Is responsible for handling each event relative to a given UI an to coordinate eventing until +// an eventual graceful exit. +// +//nolint:funlen +func EventLoop(workerErrs <-chan error, signals <-chan os.Signal, subscription *partybus.Subscription, cleanupFn func(), uxs ...ui.UI) error { + defer cleanupFn() + events := subscription.Events() + var err error + var ux ui.UI + + if ux, err = setupUI(subscription.Unsubscribe, uxs...); err != nil { + return err + } + + var retErr error + var forceTeardown bool + + for { + if workerErrs == nil && events == nil { + break + } + select { + case err, isOpen := <-workerErrs: + if !isOpen { + workerErrs = nil + continue + } + if err != nil { + // capture the error from the worker and unsubscribe to complete a graceful shutdown + retErr = multierror.Append(retErr, err) + _ = subscription.Unsubscribe() + // the worker has exited, we may have been mid-handling events for the UI which should now be + // ignored, in which case forcing a teardown of the UI irregardless of the state is required. + forceTeardown = true + } + case e, isOpen := <-events: + if !isOpen { + events = nil + continue + } + + if err := ux.Handle(e); err != nil { + if errors.Is(err, partybus.ErrUnsubscribe) { + events = nil + } else { + retErr = multierror.Append(retErr, err) + // TODO: should we unsubscribe? should we try to halt execution? or continue? + } + } + case <-signals: + // ignore further results from any event source and exit ASAP, but ensure that all cache is cleaned up. + // we ignore further errors since cleaning up the tmp directories will affect running catalogers that are + // reading/writing from/to their nested temp dirs. This is acceptable since we are bailing without result. + + // TODO: potential future improvement would be to pass context into workers with a cancel function that is + // to the event loop. In this way we can have a more controlled shutdown even at the most nested levels + // of processing. + events = nil + workerErrs = nil + forceTeardown = true + } + } + + if err := ux.Teardown(forceTeardown); err != nil { + retErr = multierror.Append(retErr, err) + } + + return retErr +} + +// setupUI takes one or more UIs that responds to events and takes a event bus unsubscribe function for use +// during teardown. With the given UIs, the first UI which the ui.Setup() function does not return an error +// will be utilized in execution. Providing a set of UIs allows for the caller to provide graceful fallbacks +// when there are environmental problem (e.g. unable to setup a TUI with the current TTY). +func setupUI(unsubscribe func() error, uis ...ui.UI) (ui.UI, error) { + for _, ux := range uis { + if err := ux.Setup(unsubscribe); err != nil { + log.Warnf("unable to setup given UI, falling back to alternative UI: %+v", err) + continue + } + + return ux, nil + } + return nil, fmt.Errorf("unable to setup any UI") +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/event_loop_test.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/event_loop_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d2a12fd52af1763b565736486fd06b115864cec9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/event_loop_test.go @@ -0,0 +1,455 @@ +package eventloop + +import ( + "fmt" + "os" + "syscall" + "testing" + "time" + + "github.com/anchore/syft/internal/ui" + "github.com/anchore/syft/syft/event" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/mock" + "github.com/wagoodman/go-partybus" +) + +var _ ui.UI = (*uiMock)(nil) + +type uiMock struct { + t *testing.T + finalEvent partybus.Event + unsubscribe func() error + mock.Mock +} + +func (u *uiMock) Setup(unsubscribe func() error) error { + u.t.Logf("UI Setup called") + u.unsubscribe = unsubscribe + return u.Called(unsubscribe).Error(0) +} + +func (u *uiMock) Handle(event partybus.Event) error { + u.t.Logf("UI Handle called: %+v", event.Type) + if event == u.finalEvent { + assert.NoError(u.t, u.unsubscribe()) + } + return u.Called(event).Error(0) +} + +func (u *uiMock) Teardown(_ bool) error { + u.t.Logf("UI Teardown called") + return u.Called().Error(0) +} + +func Test_EventLoop_gracefulExit(t *testing.T) { + test := func(t *testing.T) { + + testBus := partybus.NewBus() + subscription := testBus.Subscribe() + t.Cleanup(testBus.Close) + + finalEvent := partybus.Event{ + Type: event.Exit, + } + + worker := func() <-chan error { + ret := make(chan error) + go func() { + t.Log("worker running") + // send an empty item (which is ignored) ensuring we've entered the select statement, + // then close (a partial shutdown). + ret <- nil + t.Log("worker sent nothing") + close(ret) + t.Log("worker closed") + // do the other half of the shutdown + testBus.Publish(finalEvent) + t.Log("worker published final event") + }() + return ret + } + + signaler := func() <-chan os.Signal { + return nil + } + + ux := &uiMock{ + t: t, + finalEvent: finalEvent, + } + + // ensure the mock sees at least the final event + ux.On("Handle", finalEvent).Return(nil) + // ensure the mock sees basic setup/teardown events + ux.On("Setup", mock.AnythingOfType("func() error")).Return(nil) + ux.On("Teardown").Return(nil) + + var cleanupCalled bool + cleanupFn := func() { + t.Log("cleanup called") + cleanupCalled = true + } + + assert.NoError(t, + EventLoop( + worker(), + signaler(), + subscription, + cleanupFn, + ux, + ), + ) + + assert.True(t, cleanupCalled, "cleanup function not called") + ux.AssertExpectations(t) + } + + // if there is a bug, then there is a risk of the event loop never returning + testWithTimeout(t, 5*time.Second, test) +} + +func Test_EventLoop_workerError(t *testing.T) { + test := func(t *testing.T) { + + testBus := partybus.NewBus() + subscription := testBus.Subscribe() + t.Cleanup(testBus.Close) + + workerErr := fmt.Errorf("worker error") + + worker := func() <-chan error { + ret := make(chan error) + go func() { + t.Log("worker running") + // send an empty item (which is ignored) ensuring we've entered the select statement, + // then close (a partial shutdown). + ret <- nil + t.Log("worker sent nothing") + ret <- workerErr + t.Log("worker sent error") + close(ret) + t.Log("worker closed") + // note: NO final event is fired + }() + return ret + } + + signaler := func() <-chan os.Signal { + return nil + } + + ux := &uiMock{ + t: t, + } + + // ensure the mock sees basic setup/teardown events + ux.On("Setup", mock.AnythingOfType("func() error")).Return(nil) + ux.On("Teardown").Return(nil) + + var cleanupCalled bool + cleanupFn := func() { + t.Log("cleanup called") + cleanupCalled = true + } + + // ensure we see an error returned + assert.ErrorIs(t, + EventLoop( + worker(), + signaler(), + subscription, + cleanupFn, + ux, + ), + workerErr, + "should have seen a worker error, but did not", + ) + + assert.True(t, cleanupCalled, "cleanup function not called") + ux.AssertExpectations(t) + } + + // if there is a bug, then there is a risk of the event loop never returning + testWithTimeout(t, 5*time.Second, test) +} + +func Test_EventLoop_unsubscribeError(t *testing.T) { + test := func(t *testing.T) { + + testBus := partybus.NewBus() + subscription := testBus.Subscribe() + t.Cleanup(testBus.Close) + + finalEvent := partybus.Event{ + Type: event.Exit, + } + + worker := func() <-chan error { + ret := make(chan error) + go func() { + t.Log("worker running") + // send an empty item (which is ignored) ensuring we've entered the select statement, + // then close (a partial shutdown). + ret <- nil + t.Log("worker sent nothing") + close(ret) + t.Log("worker closed") + // do the other half of the shutdown + testBus.Publish(finalEvent) + t.Log("worker published final event") + }() + return ret + } + + signaler := func() <-chan os.Signal { + return nil + } + + ux := &uiMock{ + t: t, + finalEvent: finalEvent, + } + + // ensure the mock sees at least the final event... note the unsubscribe error here + ux.On("Handle", finalEvent).Return(partybus.ErrUnsubscribe) + // ensure the mock sees basic setup/teardown events + ux.On("Setup", mock.AnythingOfType("func() error")).Return(nil) + ux.On("Teardown").Return(nil) + + var cleanupCalled bool + cleanupFn := func() { + t.Log("cleanup called") + cleanupCalled = true + } + + // unsubscribe errors should be handled and ignored, not propagated. We are additionally asserting that + // this case is handled as a controlled shutdown (this test should not timeout) + assert.NoError(t, + EventLoop( + worker(), + signaler(), + subscription, + cleanupFn, + ux, + ), + ) + + assert.True(t, cleanupCalled, "cleanup function not called") + ux.AssertExpectations(t) + } + + // if there is a bug, then there is a risk of the event loop never returning + testWithTimeout(t, 5*time.Second, test) +} + +func Test_EventLoop_handlerError(t *testing.T) { + test := func(t *testing.T) { + + testBus := partybus.NewBus() + subscription := testBus.Subscribe() + t.Cleanup(testBus.Close) + + finalEvent := partybus.Event{ + Type: event.Exit, + Error: fmt.Errorf("an exit error occured"), + } + + worker := func() <-chan error { + ret := make(chan error) + go func() { + t.Log("worker running") + // send an empty item (which is ignored) ensuring we've entered the select statement, + // then close (a partial shutdown). + ret <- nil + t.Log("worker sent nothing") + close(ret) + t.Log("worker closed") + // do the other half of the shutdown + testBus.Publish(finalEvent) + t.Log("worker published final event") + }() + return ret + } + + signaler := func() <-chan os.Signal { + return nil + } + + ux := &uiMock{ + t: t, + finalEvent: finalEvent, + } + + // ensure the mock sees at least the final event... note the event error is propagated + ux.On("Handle", finalEvent).Return(finalEvent.Error) + // ensure the mock sees basic setup/teardown events + ux.On("Setup", mock.AnythingOfType("func() error")).Return(nil) + ux.On("Teardown").Return(nil) + + var cleanupCalled bool + cleanupFn := func() { + t.Log("cleanup called") + cleanupCalled = true + } + + // handle errors SHOULD propagate the event loop. We are additionally asserting that this case is + // handled as a controlled shutdown (this test should not timeout) + assert.ErrorIs(t, + EventLoop( + worker(), + signaler(), + subscription, + cleanupFn, + ux, + ), + finalEvent.Error, + "should have seen a event error, but did not", + ) + + assert.True(t, cleanupCalled, "cleanup function not called") + ux.AssertExpectations(t) + } + + // if there is a bug, then there is a risk of the event loop never returning + testWithTimeout(t, 5*time.Second, test) +} + +func Test_EventLoop_signalsStopExecution(t *testing.T) { + test := func(t *testing.T) { + + testBus := partybus.NewBus() + subscription := testBus.Subscribe() + t.Cleanup(testBus.Close) + + worker := func() <-chan error { + // the worker will never return work and the event loop will always be waiting... + return make(chan error) + } + + signaler := func() <-chan os.Signal { + ret := make(chan os.Signal) + go func() { + ret <- syscall.SIGINT + // note: we do NOT close the channel to ensure the event loop does not depend on that behavior to exit + }() + return ret + } + + ux := &uiMock{ + t: t, + } + + // ensure the mock sees basic setup/teardown events + ux.On("Setup", mock.AnythingOfType("func() error")).Return(nil) + ux.On("Teardown").Return(nil) + + var cleanupCalled bool + cleanupFn := func() { + t.Log("cleanup called") + cleanupCalled = true + } + + assert.NoError(t, + EventLoop( + worker(), + signaler(), + subscription, + cleanupFn, + ux, + ), + ) + + assert.True(t, cleanupCalled, "cleanup function not called") + ux.AssertExpectations(t) + } + + // if there is a bug, then there is a risk of the event loop never returning + testWithTimeout(t, 5*time.Second, test) +} + +func Test_EventLoop_uiTeardownError(t *testing.T) { + test := func(t *testing.T) { + + testBus := partybus.NewBus() + subscription := testBus.Subscribe() + t.Cleanup(testBus.Close) + + finalEvent := partybus.Event{ + Type: event.Exit, + } + + worker := func() <-chan error { + ret := make(chan error) + go func() { + t.Log("worker running") + // send an empty item (which is ignored) ensuring we've entered the select statement, + // then close (a partial shutdown). + ret <- nil + t.Log("worker sent nothing") + close(ret) + t.Log("worker closed") + // do the other half of the shutdown + testBus.Publish(finalEvent) + t.Log("worker published final event") + }() + return ret + } + + signaler := func() <-chan os.Signal { + return nil + } + + ux := &uiMock{ + t: t, + finalEvent: finalEvent, + } + + teardownError := fmt.Errorf("sorry, dave, the UI doesn't want to be torn down") + + // ensure the mock sees at least the final event... note the event error is propagated + ux.On("Handle", finalEvent).Return(nil) + // ensure the mock sees basic setup/teardown events + ux.On("Setup", mock.AnythingOfType("func() error")).Return(nil) + ux.On("Teardown").Return(teardownError) + + var cleanupCalled bool + cleanupFn := func() { + t.Log("cleanup called") + cleanupCalled = true + } + + // ensure we see an error returned + assert.ErrorIs(t, + EventLoop( + worker(), + signaler(), + subscription, + cleanupFn, + ux, + ), + teardownError, + "should have seen a UI teardown error, but did not", + ) + + assert.True(t, cleanupCalled, "cleanup function not called") + ux.AssertExpectations(t) + } + + // if there is a bug, then there is a risk of the event loop never returning + testWithTimeout(t, 5*time.Second, test) +} + +func testWithTimeout(t *testing.T, timeout time.Duration, test func(*testing.T)) { + done := make(chan bool) + go func() { + test(t) + done <- true + }() + + select { + case <-time.After(timeout): + t.Fatal("test timed out") + case <-done: + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/signals.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/signals.go new file mode 100644 index 0000000000000000000000000000000000000000..72a97711e8d44041978d851fa140227ddfcafcae --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/signals.go @@ -0,0 +1,20 @@ +package eventloop + +import ( + "os" + "os/signal" + "syscall" +) + +func SetupSignals() <-chan os.Signal { + c := make(chan os.Signal, 1) // Note: A buffered channel is recommended for this; see https://golang.org/pkg/os/signal/#Notify + + interruptions := []os.Signal{ + syscall.SIGINT, + syscall.SIGTERM, + } + + signal.Notify(c, interruptions...) + + return c +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/tasks.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/tasks.go new file mode 100644 index 0000000000000000000000000000000000000000..4d16f64f610a87ce5dda558880da93441bb5867d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/eventloop/tasks.go @@ -0,0 +1,232 @@ +package eventloop + +import ( + "crypto" + "fmt" + + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" +) + +type Task func(*sbom.Artifacts, *source.Source) ([]artifact.Relationship, error) + +func Tasks(app *config.Application) ([]Task, error) { + var tasks []Task + + generators := []func(app *config.Application) (Task, error){ + generateCatalogPackagesTask, + generateCatalogFileMetadataTask, + generateCatalogFileDigestsTask, + generateCatalogSecretsTask, + generateCatalogFileClassificationsTask, + generateCatalogContentsTask, + } + + for _, generator := range generators { + task, err := generator(app) + if err != nil { + return nil, err + } + + if task != nil { + tasks = append(tasks, task) + } + } + + return tasks, nil +} + +func generateCatalogPackagesTask(app *config.Application) (Task, error) { + if !app.Package.Cataloger.Enabled { + return nil, nil + } + + task := func(results *sbom.Artifacts, src *source.Source) ([]artifact.Relationship, error) { + packageCatalog, relationships, theDistro, err := syft.CatalogPackages(src, app.ToCatalogerConfig()) + if err != nil { + return nil, err + } + + results.PackageCatalog = packageCatalog + results.LinuxDistribution = theDistro + + return relationships, nil + } + + return task, nil +} + +func generateCatalogFileMetadataTask(app *config.Application) (Task, error) { + if !app.FileMetadata.Cataloger.Enabled { + return nil, nil + } + + metadataCataloger := file.NewMetadataCataloger() + + task := func(results *sbom.Artifacts, src *source.Source) ([]artifact.Relationship, error) { + resolver, err := src.FileResolver(app.FileMetadata.Cataloger.ScopeOpt) + if err != nil { + return nil, err + } + + result, err := metadataCataloger.Catalog(resolver) + if err != nil { + return nil, err + } + results.FileMetadata = result + return nil, nil + } + + return task, nil +} + +func generateCatalogFileDigestsTask(app *config.Application) (Task, error) { + if !app.FileMetadata.Cataloger.Enabled { + return nil, nil + } + + supportedHashAlgorithms := make(map[string]crypto.Hash) + for _, h := range []crypto.Hash{ + crypto.MD5, + crypto.SHA1, + crypto.SHA256, + } { + supportedHashAlgorithms[file.DigestAlgorithmName(h)] = h + } + + var hashes []crypto.Hash + for _, hashStr := range app.FileMetadata.Digests { + name := file.CleanDigestAlgorithmName(hashStr) + hashObj, ok := supportedHashAlgorithms[name] + if !ok { + return nil, fmt.Errorf("unsupported hash algorithm: %s", hashStr) + } + hashes = append(hashes, hashObj) + } + + digestsCataloger, err := file.NewDigestsCataloger(hashes) + if err != nil { + return nil, err + } + + task := func(results *sbom.Artifacts, src *source.Source) ([]artifact.Relationship, error) { + resolver, err := src.FileResolver(app.FileMetadata.Cataloger.ScopeOpt) + if err != nil { + return nil, err + } + + result, err := digestsCataloger.Catalog(resolver) + if err != nil { + return nil, err + } + results.FileDigests = result + return nil, nil + } + + return task, nil +} + +func generateCatalogSecretsTask(app *config.Application) (Task, error) { + if !app.Secrets.Cataloger.Enabled { + return nil, nil + } + + patterns, err := file.GenerateSearchPatterns(file.DefaultSecretsPatterns, app.Secrets.AdditionalPatterns, app.Secrets.ExcludePatternNames) + if err != nil { + return nil, err + } + + secretsCataloger, err := file.NewSecretsCataloger(patterns, app.Secrets.RevealValues, app.Secrets.SkipFilesAboveSize) + if err != nil { + return nil, err + } + + task := func(results *sbom.Artifacts, src *source.Source) ([]artifact.Relationship, error) { + resolver, err := src.FileResolver(app.Secrets.Cataloger.ScopeOpt) + if err != nil { + return nil, err + } + + result, err := secretsCataloger.Catalog(resolver) + if err != nil { + return nil, err + } + results.Secrets = result + return nil, nil + } + + return task, nil +} + +func generateCatalogFileClassificationsTask(app *config.Application) (Task, error) { + if !app.FileClassification.Cataloger.Enabled { + return nil, nil + } + + // TODO: in the future we could expose out the classifiers via configuration + classifierCataloger, err := file.NewClassificationCataloger(file.DefaultClassifiers) + if err != nil { + return nil, err + } + + task := func(results *sbom.Artifacts, src *source.Source) ([]artifact.Relationship, error) { + resolver, err := src.FileResolver(app.FileClassification.Cataloger.ScopeOpt) + if err != nil { + return nil, err + } + + result, err := classifierCataloger.Catalog(resolver) + if err != nil { + return nil, err + } + results.FileClassifications = result + return nil, nil + } + + return task, nil +} + +func generateCatalogContentsTask(app *config.Application) (Task, error) { + if !app.FileContents.Cataloger.Enabled { + return nil, nil + } + + contentsCataloger, err := file.NewContentsCataloger(app.FileContents.Globs, app.FileContents.SkipFilesAboveSize) + if err != nil { + return nil, err + } + + task := func(results *sbom.Artifacts, src *source.Source) ([]artifact.Relationship, error) { + resolver, err := src.FileResolver(app.FileContents.Cataloger.ScopeOpt) + if err != nil { + return nil, err + } + + result, err := contentsCataloger.Catalog(resolver) + if err != nil { + return nil, err + } + results.FileContents = result + return nil, nil + } + + return task, nil +} + +func RunTask(t Task, a *sbom.Artifacts, src *source.Source, c chan<- artifact.Relationship, errs chan<- error) { + defer close(c) + + relationships, err := t(a, src) + if err != nil { + errs <- err + return + } + + for _, relationship := range relationships { + c <- relationship + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/attest.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/attest.go new file mode 100644 index 0000000000000000000000000000000000000000..17f86526413a6d0bdf1563436ac86f4d660fb331 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/attest.go @@ -0,0 +1,77 @@ +package options + +import ( + "github.com/spf13/cobra" + "github.com/spf13/pflag" + "github.com/spf13/viper" +) + +const defaultKeyFileName = "cosign.key" + +type AttestOptions struct { + Key string + Cert string + CertChain string + NoUpload bool + Force bool + Recursive bool + + Rekor RekorOptions + Fulcio FulcioOptions + OIDC OIDCOptions +} + +var _ Interface = (*AttestOptions)(nil) + +func (o *AttestOptions) AddFlags(cmd *cobra.Command, v *viper.Viper) error { + if err := o.Rekor.AddFlags(cmd, v); err != nil { + return err + } + if err := o.Fulcio.AddFlags(cmd, v); err != nil { + return err + } + if err := o.OIDC.AddFlags(cmd, v); err != nil { + return err + } + + cmd.Flags().StringVarP(&o.Key, "key", "", defaultKeyFileName, + "path to the private key file to use for attestation") + + cmd.Flags().StringVarP(&o.Cert, "cert", "", "", + "path to the x.509 certificate in PEM format to include in the OCI Signature") + + cmd.Flags().BoolVarP(&o.NoUpload, "no-upload", "", false, + "do not upload the generated attestation") + + cmd.Flags().BoolVarP(&o.Force, "force", "", false, + "skip warnings and confirmations") + + cmd.Flags().BoolVarP(&o.Recursive, "recursive", "", false, + "if a multi-arch image is specified, additionally sign each discrete image") + + return bindAttestationConfigOptions(cmd.Flags(), v) +} + +func bindAttestationConfigOptions(flags *pflag.FlagSet, v *viper.Viper) error { + if err := v.BindPFlag("attest.key", flags.Lookup("key")); err != nil { + return err + } + + if err := v.BindPFlag("attest.cert", flags.Lookup("cert")); err != nil { + return err + } + + if err := v.BindPFlag("attest.no-upload", flags.Lookup("no-upload")); err != nil { + return err + } + + if err := v.BindPFlag("attest.force", flags.Lookup("force")); err != nil { + return err + } + + if err := v.BindPFlag("attest.recursive", flags.Lookup("recursive")); err != nil { + return err + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/format.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/format.go new file mode 100644 index 0000000000000000000000000000000000000000..8ccdf44c65ad641d977b480e9be270126349bd7a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/format.go @@ -0,0 +1,32 @@ +package options + +import ( + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/sbom" +) + +func FormatAliases(ids ...sbom.FormatID) (aliases []string) { + for _, id := range ids { + switch id { + case syft.JSONFormatID: + aliases = append(aliases, "syft-json") + case syft.TextFormatID: + aliases = append(aliases, "text") + case syft.TableFormatID: + aliases = append(aliases, "table") + case syft.SPDXJSONFormatID: + aliases = append(aliases, "spdx-json") + case syft.SPDXTagValueFormatID: + aliases = append(aliases, "spdx-tag-value") + case syft.CycloneDxXMLFormatID: + aliases = append(aliases, "cyclonedx-xml") + case syft.CycloneDxJSONFormatID: + aliases = append(aliases, "cyclonedx-json") + case syft.GitHubID: + aliases = append(aliases, "github", "github-json") + default: + aliases = append(aliases, string(id)) + } + } + return aliases +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/fulcio.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/fulcio.go new file mode 100644 index 0000000000000000000000000000000000000000..28a918910454d4545358ea031b67a4b7d4fa0eb6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/fulcio.go @@ -0,0 +1,48 @@ +package options + +import ( + "github.com/spf13/cobra" + "github.com/spf13/pflag" + "github.com/spf13/viper" +) + +const defaultFulcioURL = "https://fulcio.sigstore.dev" + +// FulcioOptions is the wrapper for Fulcio related options. +type FulcioOptions struct { + URL string + IdentityToken string + InsecureSkipFulcioVerify bool +} + +var _ Interface = (*FulcioOptions)(nil) + +// AddFlags implements Interface +func (o *FulcioOptions) AddFlags(cmd *cobra.Command, v *viper.Viper) error { + // TODO: change this back to api.SigstorePublicServerURL after the v1 migration is complete. + cmd.Flags().StringVar(&o.URL, "fulcio-url", defaultFulcioURL, + "address of sigstore PKI server") + + cmd.Flags().StringVar(&o.IdentityToken, "identity-token", "", + "identity token to use for certificate from fulcio") + + cmd.Flags().BoolVar(&o.InsecureSkipFulcioVerify, "insecure-skip-verify", false, + "skip verifying fulcio certificat and the SCT (Signed Certificate Timestamp) (this should only be used for testing).") + return bindFulcioConfigOptions(cmd.Flags(), v) +} + +func bindFulcioConfigOptions(flags *pflag.FlagSet, v *viper.Viper) error { + if err := v.BindPFlag("attest.fulcio-url", flags.Lookup("fulcio-url")); err != nil { + return err + } + + if err := v.BindPFlag("attest.fulcio-identity-token", flags.Lookup("identity-token")); err != nil { + return err + } + + if err := v.BindPFlag("attest.insecure-skip-verify", flags.Lookup("insecure-skip-verify")); err != nil { + return err + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/oidc.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/oidc.go new file mode 100644 index 0000000000000000000000000000000000000000..ce1ea4817d97c71f278fdc956cebaaf99be4cf71 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/oidc.go @@ -0,0 +1,48 @@ +package options + +import ( + "github.com/spf13/cobra" + "github.com/spf13/pflag" + "github.com/spf13/viper" +) + +const DefaultOIDCIssuerURL = "https://oauth2.sigstore.dev/auth" + +// OIDCOptions is the wrapper for OIDC related options. +type OIDCOptions struct { + Issuer string + ClientID string + RedirectURL string +} + +var _ Interface = (*OIDCOptions)(nil) + +// AddFlags implements Interface +func (o *OIDCOptions) AddFlags(cmd *cobra.Command, v *viper.Viper) error { + cmd.Flags().StringVar(&o.Issuer, "oidc-issuer", DefaultOIDCIssuerURL, + "OIDC provider to be used to issue ID token") + + cmd.Flags().StringVar(&o.ClientID, "oidc-client-id", "sigstore", + "OIDC client ID for application") + + cmd.Flags().StringVar(&o.RedirectURL, "oidc-redirect-url", "", + "OIDC redirect URL (Optional)") + + return bindOIDCConfigOptions(cmd.Flags(), v) +} + +func bindOIDCConfigOptions(flags *pflag.FlagSet, v *viper.Viper) error { + if err := v.BindPFlag("attest.oidc-issuer", flags.Lookup("oidc-issuer")); err != nil { + return err + } + + if err := v.BindPFlag("attest.oidc-client-id", flags.Lookup("oidc-client-id")); err != nil { + return err + } + + if err := v.BindPFlag("attest.oidc-redirect-url", flags.Lookup("oidc-redirect-url")); err != nil { + return err + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/options.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/options.go new file mode 100644 index 0000000000000000000000000000000000000000..f8646bbb9c8e5d412af83eae71ea76c1d4508a3a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/options.go @@ -0,0 +1,11 @@ +package options + +import ( + "github.com/spf13/cobra" + "github.com/spf13/viper" +) + +type Interface interface { + // AddFlags adds this options' flags to the cobra command. + AddFlags(cmd *cobra.Command, v *viper.Viper) error +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/packages.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/packages.go new file mode 100644 index 0000000000000000000000000000000000000000..8891f814e91843d6a470fad945832b161263a375 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/packages.go @@ -0,0 +1,134 @@ +package options + +import ( + "fmt" + + "github.com/anchore/syft/internal/formats/table" + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/pkg/cataloger" + "github.com/anchore/syft/syft/source" + "github.com/spf13/cobra" + "github.com/spf13/pflag" + "github.com/spf13/viper" +) + +type PackagesOptions struct { + Scope string + Output []string + OutputTemplatePath string + File string + Platform string + Host string + Username string + Password string + Dockerfile string + Exclude []string + OverwriteExistingImage bool + ImportTimeout uint + Catalogers []string +} + +var _ Interface = (*PackagesOptions)(nil) + +func (o *PackagesOptions) AddFlags(cmd *cobra.Command, v *viper.Viper) error { + cmd.Flags().StringVarP(&o.Scope, "scope", "s", cataloger.DefaultSearchConfig().Scope.String(), + fmt.Sprintf("selection of layers to catalog, options=%v", source.AllScopes)) + + cmd.Flags().StringArrayVarP(&o.Output, "output", "o", FormatAliases(table.ID), + fmt.Sprintf("report output format, options=%v", FormatAliases(syft.FormatIDs()...))) + + cmd.Flags().StringVarP(&o.File, "file", "", "", + "file to write the default report output to (default is STDOUT)") + + cmd.Flags().StringVarP(&o.OutputTemplatePath, "template", "t", "", + "specify the path to a Go template file") + + cmd.Flags().StringVarP(&o.Platform, "platform", "", "", + "an optional platform specifier for container image sources (e.g. 'linux/arm64', 'linux/arm64/v8', 'arm64', 'linux')") + + cmd.Flags().StringVarP(&o.Host, "host", "H", "", + "the hostname or URL of the Anchore Enterprise instance to upload to") + + cmd.Flags().StringVarP(&o.Username, "username", "u", "", + "the username to authenticate against Anchore Enterprise") + + cmd.Flags().StringVarP(&o.Password, "password", "p", "", + "the password to authenticate against Anchore Enterprise") + + cmd.Flags().StringVarP(&o.Dockerfile, "dockerfile", "d", "", + "include dockerfile for upload to Anchore Enterprise") + + cmd.Flags().StringArrayVarP(&o.Exclude, "exclude", "", nil, + "exclude paths from being scanned using a glob expression") + + cmd.Flags().StringArrayVarP(&o.Catalogers, "catalogers", "", nil, + "enable one or more package catalogers") + + cmd.Flags().BoolVarP(&o.OverwriteExistingImage, "overwrite-existing-image", "", false, + "overwrite an existing image during the upload to Anchore Enterprise") + + cmd.Flags().UintVarP(&o.ImportTimeout, "import-timeout", "", 30, + "set a timeout duration (in seconds) for the upload to Anchore Enterprise") + + return bindPackageConfigOptions(cmd.Flags(), v) +} + +func bindPackageConfigOptions(flags *pflag.FlagSet, v *viper.Viper) error { + // Formatting & Input options ////////////////////////////////////////////// + + if err := v.BindPFlag("package.cataloger.scope", flags.Lookup("scope")); err != nil { + return err + } + + if err := v.BindPFlag("file", flags.Lookup("file")); err != nil { + return err + } + + if err := v.BindPFlag("exclude", flags.Lookup("exclude")); err != nil { + return err + } + + if err := v.BindPFlag("catalogers", flags.Lookup("catalogers")); err != nil { + return err + } + + if err := v.BindPFlag("output", flags.Lookup("output")); err != nil { + return err + } + + if err := v.BindPFlag("output-template-path", flags.Lookup("template")); err != nil { + return err + } + + if err := v.BindPFlag("platform", flags.Lookup("platform")); err != nil { + return err + } + + // Upload options ////////////////////////////////////////////////////////// + + if err := v.BindPFlag("anchore.host", flags.Lookup("host")); err != nil { + return err + } + + if err := v.BindPFlag("anchore.username", flags.Lookup("username")); err != nil { + return err + } + + if err := v.BindPFlag("anchore.password", flags.Lookup("password")); err != nil { + return err + } + + if err := v.BindPFlag("anchore.dockerfile", flags.Lookup("dockerfile")); err != nil { + return err + } + + if err := v.BindPFlag("anchore.overwrite-existing-image", flags.Lookup("overwrite-existing-image")); err != nil { + return err + } + + if err := v.BindPFlag("anchore.import-timeout", flags.Lookup("import-timeout")); err != nil { + return err + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/rekor.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/rekor.go new file mode 100644 index 0000000000000000000000000000000000000000..668c06e4b18678c6c089b2395afca2fbbfc238ae --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/rekor.go @@ -0,0 +1,32 @@ +package options + +import ( + "github.com/spf13/cobra" + "github.com/spf13/pflag" + "github.com/spf13/viper" +) + +const DefaultRekorURL = "https://rekor.sigstore.dev" + +// RekorOptions is the wrapper for Rekor related options. +type RekorOptions struct { + URL string +} + +var _ Interface = (*RekorOptions)(nil) + +// AddFlags implements Interface +func (o *RekorOptions) AddFlags(cmd *cobra.Command, v *viper.Viper) error { + cmd.Flags().StringVar(&o.URL, "rekor-url", DefaultRekorURL, + "address of rekor STL server") + return bindRekorConfigOptions(cmd.Flags(), v) +} + +func bindRekorConfigOptions(flags *pflag.FlagSet, v *viper.Viper) error { + // TODO: config re-design + if err := v.BindPFlag("attest.rekor-url", flags.Lookup("rekor-url")); err != nil { + return err + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/root.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/root.go new file mode 100644 index 0000000000000000000000000000000000000000..176ec2aece6d8d78f6e4619b1b57f22d2d2f7734 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/root.go @@ -0,0 +1,36 @@ +package options + +import ( + "github.com/spf13/cobra" + "github.com/spf13/pflag" + "github.com/spf13/viper" +) + +type RootOptions struct { + Config string + Quiet bool + Verbose int +} + +var _ Interface = (*RootOptions)(nil) + +func (o *RootOptions) AddFlags(cmd *cobra.Command, v *viper.Viper) error { + cmd.PersistentFlags().StringVarP(&o.Config, "config", "c", "", "application config file") + cmd.PersistentFlags().CountVarP(&o.Verbose, "verbose", "v", "increase verbosity (-v = info, -vv = debug)") + cmd.PersistentFlags().BoolVarP(&o.Quiet, "quiet", "q", false, "suppress all logging output") + + return bindRootConfigOptions(cmd.PersistentFlags(), v) +} + +func bindRootConfigOptions(flags *pflag.FlagSet, v *viper.Viper) error { + if err := v.BindPFlag("config", flags.Lookup("config")); err != nil { + return err + } + if err := v.BindPFlag("verbosity", flags.Lookup("verbose")); err != nil { + return err + } + if err := v.BindPFlag("quiet", flags.Lookup("quiet")); err != nil { + return err + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/verbose.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/verbose.go new file mode 100644 index 0000000000000000000000000000000000000000..aa53bb40ebe64a74e1d0fb54dec9a013d9643652 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/verbose.go @@ -0,0 +1,18 @@ +package options + +import ( + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/internal/log" +) + +func IsVerbose(app *config.Application) (result bool) { + isPipedInput, err := internal.IsPipedInput() + if err != nil { + // since we can't tell if there was piped input we assume that there could be to disable the ETUI + log.Warnf("unable to determine if there is piped input: %+v", err) + return true + } + // verbosity should consider if there is piped input (in which case we should not show the ETUI) + return app.Verbosity > 0 || isPipedInput +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/version.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/version.go new file mode 100644 index 0000000000000000000000000000000000000000..ea03c7c48e678b23c4d09bc9dccbf4962a115540 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/version.go @@ -0,0 +1,17 @@ +package options + +import ( + "github.com/spf13/cobra" + "github.com/spf13/viper" +) + +type VersionOptions struct { + Output string +} + +var _ Interface = (*PackagesOptions)(nil) + +func (o *VersionOptions) AddFlags(cmd *cobra.Command, v *viper.Viper) error { + cmd.Flags().StringVarP(&o.Output, "output", "o", "text", "format to show version information (available=[text, json])") + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/writer.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/writer.go new file mode 100644 index 0000000000000000000000000000000000000000..2b28dd97a690b03604737b5faef4fdd222d60699 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/writer.go @@ -0,0 +1,68 @@ +package options + +import ( + "fmt" + "strings" + + "github.com/anchore/syft/internal/formats/table" + "github.com/anchore/syft/internal/formats/template" + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/sbom" + "github.com/hashicorp/go-multierror" +) + +// makeWriter creates a sbom.Writer for output or returns an error. this will either return a valid writer +// or an error but neither both and if there is no error, sbom.Writer.Close() should be called +func MakeWriter(outputs []string, defaultFile, templateFilePath string) (sbom.Writer, error) { + outputOptions, err := parseOutputs(outputs, defaultFile, templateFilePath) + if err != nil { + return nil, err + } + + writer, err := sbom.NewWriter(outputOptions...) + if err != nil { + return nil, err + } + + return writer, nil +} + +// parseOptions utility to parse command-line option strings and retain the existing behavior of default format and file +func parseOutputs(outputs []string, defaultFile, templateFilePath string) (out []sbom.WriterOption, errs error) { + // always should have one option -- we generally get the default of "table", but just make sure + if len(outputs) == 0 { + outputs = append(outputs, string(table.ID)) + } + + for _, name := range outputs { + name = strings.TrimSpace(name) + + // split to at most two parts for = + parts := strings.SplitN(name, "=", 2) + + // the format name is the first part + name = parts[0] + + // default to the --file or empty string if not specified + file := defaultFile + + // If a file is specified as part of the output formatName, use that + if len(parts) > 1 { + file = parts[1] + } + + format := syft.FormatByName(name) + if format == nil { + errs = multierror.Append(errs, fmt.Errorf(`unsupported output format "%s", supported formats are: %+v`, name, FormatAliases(syft.FormatIDs()...))) + continue + } + + if tmpl, ok := format.(template.OutputFormat); ok { + tmpl.SetTemplatePath(templateFilePath) + format = tmpl + } + + out = append(out, sbom.NewWriterOption(format, file)) + } + return out, errs +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/writer_test.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/writer_test.go new file mode 100644 index 0000000000000000000000000000000000000000..25a01fde95237030377706c92ebc5eb44d679b8c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/options/writer_test.go @@ -0,0 +1,34 @@ +package options + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestIsSupportedFormat(t *testing.T) { + tests := []struct { + outputs []string + wantErr assert.ErrorAssertionFunc + }{ + { + outputs: []string{"json"}, + wantErr: assert.NoError, + }, + { + outputs: []string{"table", "json"}, + wantErr: assert.NoError, + }, + { + outputs: []string{"unknown"}, + wantErr: func(t assert.TestingT, err error, bla ...interface{}) bool { + return assert.ErrorContains(t, err, `unsupported output format "unknown", supported formats are: [`) + }, + }, + } + + for _, tt := range tests { + _, err := MakeWriter(tt.outputs, "", "") + tt.wantErr(t, err) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/packages.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/packages.go new file mode 100644 index 0000000000000000000000000000000000000000..f08c995723760b0f602af7c0fba2f834eeb424f6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/packages.go @@ -0,0 +1,83 @@ +package cli + +import ( + "fmt" + "log" + + "github.com/anchore/syft/cmd/syft/cli/options" + + "github.com/anchore/syft/cmd/syft/cli/packages" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/config" + "github.com/spf13/cobra" + "github.com/spf13/viper" +) + +const ( + packagesExample = ` {{.appName}} {{.command}} alpine:latest a summary of discovered packages + {{.appName}} {{.command}} alpine:latest -o json show all possible cataloging details + {{.appName}} {{.command}} alpine:latest -o cyclonedx show a CycloneDX formatted SBOM + {{.appName}} {{.command}} alpine:latest -o cyclonedx-json show a CycloneDX JSON formatted SBOM + {{.appName}} {{.command}} alpine:latest -o spdx show a SPDX 2.2 Tag-Value formatted SBOM + {{.appName}} {{.command}} alpine:latest -o spdx-json show a SPDX 2.2 JSON formatted SBOM + {{.appName}} {{.command}} alpine:latest -vv show verbose debug information + {{.appName}} {{.command}} alpine:latest -o template -t my_format.tmpl show a SBOM formatted according to given template file + + Supports the following image sources: + {{.appName}} {{.command}} yourrepo/yourimage:tag defaults to using images from a Docker daemon. If Docker is not present, the image is pulled directly from the registry. + {{.appName}} {{.command}} path/to/a/file/or/dir a Docker tar, OCI tar, OCI directory, SIF container, or generic filesystem directory +` + + schemeHelpHeader = "You can also explicitly specify the scheme to use:" + imageSchemeHelp = ` {{.appName}} {{.command}} docker:yourrepo/yourimage:tag explicitly use the Docker daemon + {{.appName}} {{.command}} podman:yourrepo/yourimage:tag explicitly use the Podman daemon + {{.appName}} {{.command}} registry:yourrepo/yourimage:tag pull image directly from a registry (no container runtime required) + {{.appName}} {{.command}} docker-archive:path/to/yourimage.tar use a tarball from disk for archives created from "docker save" + {{.appName}} {{.command}} oci-archive:path/to/yourimage.tar use a tarball from disk for OCI archives (from Skopeo or otherwise) + {{.appName}} {{.command}} oci-dir:path/to/yourimage read directly from a path on disk for OCI layout directories (from Skopeo or otherwise) + {{.appName}} {{.command}} singularity:path/to/yourimage.sif read directly from a Singularity Image Format (SIF) container on disk +` + nonImageSchemeHelp = ` {{.appName}} {{.command}} dir:path/to/yourproject read directly from a path on disk (any directory) + {{.appName}} {{.command}} file:path/to/yourproject/file read directly from a path on disk (any single file) +` + packagesSchemeHelp = "\n" + indent + schemeHelpHeader + "\n" + imageSchemeHelp + nonImageSchemeHelp + + packagesHelp = packagesExample + packagesSchemeHelp +) + +//nolint:dupl +func Packages(v *viper.Viper, app *config.Application, ro *options.RootOptions, po *options.PackagesOptions) *cobra.Command { + cmd := &cobra.Command{ + Use: "packages [SOURCE]", + Short: "Generate a package SBOM", + Long: "Generate a packaged-based Software Bill Of Materials (SBOM) from container images and filesystems", + Example: internal.Tprintf(packagesHelp, map[string]interface{}{ + "appName": internal.ApplicationName, + "command": "packages", + }), + Args: func(cmd *cobra.Command, args []string) error { + if err := app.LoadAllValues(v, ro.Config); err != nil { + return fmt.Errorf("invalid application config: %v", err) + } + // configure logging for command + newLogWrapper(app) + logApplicationConfig(app) + return validateArgs(cmd, args) + }, + SilenceUsage: true, + SilenceErrors: true, + RunE: func(cmd *cobra.Command, args []string) error { + if app.CheckForAppUpdate { + checkForApplicationUpdate() + } + return packages.Run(cmd.Context(), app, args) + }, + } + + err := po.AddFlags(cmd, v) + if err != nil { + log.Fatal(err) + } + + return cmd +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/packages/packages.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/packages/packages.go new file mode 100644 index 0000000000000000000000000000000000000000..0914b186c685cc678cc86bd85482beb35998601e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/packages/packages.go @@ -0,0 +1,209 @@ +package packages + +import ( + "context" + "fmt" + "io/ioutil" + "os" + + "github.com/anchore/stereoscope" + "github.com/anchore/syft/cmd/syft/cli/eventloop" + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/anchore" + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/internal/formats/template" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/internal/ui" + "github.com/anchore/syft/internal/version" + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" + "github.com/wagoodman/go-partybus" +) + +func Run(ctx context.Context, app *config.Application, args []string) error { + err := validateOutputOptions(app) + if err != nil { + return err + } + + writer, err := options.MakeWriter(app.Outputs, app.File, app.OutputTemplatePath) + if err != nil { + return err + } + + defer func() { + if err := writer.Close(); err != nil { + log.Warnf("unable to write to report destination: %w", err) + } + }() + + // could be an image or a directory, with or without a scheme + userInput := args[0] + si, err := source.ParseInput(userInput, app.Platform, true) + if err != nil { + return fmt.Errorf("could not generate source input for packages command: %w", err) + } + + eventBus := partybus.NewBus() + stereoscope.SetBus(eventBus) + syft.SetBus(eventBus) + subscription := eventBus.Subscribe() + + return eventloop.EventLoop( + execWorker(app, *si, writer), + eventloop.SetupSignals(), + subscription, + stereoscope.Cleanup, + ui.Select(options.IsVerbose(app), app.Quiet)..., + ) +} + +func execWorker(app *config.Application, si source.Input, writer sbom.Writer) <-chan error { + errs := make(chan error) + go func() { + defer close(errs) + + src, cleanup, err := source.New(si, app.Registry.ToOptions(), app.Exclusions) + if cleanup != nil { + defer cleanup() + } + if err != nil { + errs <- fmt.Errorf("failed to construct source from user input %q: %w", si.UserInput, err) + return + } + + s, err := GenerateSBOM(src, errs, app) + if err != nil { + errs <- err + return + } + + if s == nil { + errs <- fmt.Errorf("no SBOM produced for %q", si.UserInput) + } + + if app.Anchore.Host != "" { + if err := runPackageSbomUpload(src, *s, app); err != nil { + errs <- err + return + } + } + + bus.Publish(partybus.Event{ + Type: event.Exit, + Value: func() error { return writer.Write(*s) }, + }) + }() + return errs +} + +func GenerateSBOM(src *source.Source, errs chan error, app *config.Application) (*sbom.SBOM, error) { + tasks, err := eventloop.Tasks(app) + if err != nil { + return nil, err + } + + s := sbom.SBOM{ + Source: src.Metadata, + Descriptor: sbom.Descriptor{ + Name: internal.ApplicationName, + Version: version.FromBuild().Version, + Configuration: app, + }, + } + + buildRelationships(&s, src, tasks, errs) + + return &s, nil +} + +func buildRelationships(s *sbom.SBOM, src *source.Source, tasks []eventloop.Task, errs chan error) { + var relationships []<-chan artifact.Relationship + for _, task := range tasks { + c := make(chan artifact.Relationship) + relationships = append(relationships, c) + go eventloop.RunTask(task, &s.Artifacts, src, c, errs) + } + + s.Relationships = append(s.Relationships, MergeRelationships(relationships...)...) +} + +func MergeRelationships(cs ...<-chan artifact.Relationship) (relationships []artifact.Relationship) { + for _, c := range cs { + for n := range c { + relationships = append(relationships, n) + } + } + + return relationships +} + +func runPackageSbomUpload(src *source.Source, s sbom.SBOM, app *config.Application) error { + log.Infof("uploading results to %s", app.Anchore.Host) + + if src.Metadata.Scheme != source.ImageScheme { + return fmt.Errorf("unable to upload results: only images are supported") + } + + var dockerfileContents []byte + if app.Anchore.Dockerfile != "" { + if _, err := os.Stat(app.Anchore.Dockerfile); os.IsNotExist(err) { + return fmt.Errorf("unable dockerfile=%q does not exist: %w", app.Anchore.Dockerfile, err) + } + + fh, err := os.Open(app.Anchore.Dockerfile) + if err != nil { + return fmt.Errorf("unable to open dockerfile=%q: %w", app.Anchore.Dockerfile, err) + } + + dockerfileContents, err = ioutil.ReadAll(fh) + if err != nil { + return fmt.Errorf("unable to read dockerfile=%q: %w", app.Anchore.Dockerfile, err) + } + } + + c, err := anchore.NewClient(anchore.Configuration{ + BaseURL: app.Anchore.Host, + Username: app.Anchore.Username, + Password: app.Anchore.Password, + }) + + if err != nil { + return fmt.Errorf("failed to create anchore client: %w", err) + } + + importCfg := anchore.ImportConfig{ + ImageMetadata: src.Image.Metadata, + SBOM: s, + Dockerfile: dockerfileContents, + OverwriteExistingUpload: app.Anchore.OverwriteExistingImage, + Timeout: app.Anchore.ImportTimeout, + } + + if err := c.Import(context.Background(), importCfg); err != nil { + return fmt.Errorf("failed to upload results to host=%s: %+v", app.Anchore.Host, err) + } + + return nil +} + +func validateOutputOptions(app *config.Application) error { + var usesTemplateOutput bool + for _, o := range app.Outputs { + if o == template.ID.String() { + usesTemplateOutput = true + break + } + } + + if usesTemplateOutput && app.OutputTemplatePath == "" { + return fmt.Errorf(`must specify path to template file when using "template" output format`) + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/poweruser.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/poweruser.go new file mode 100644 index 0000000000000000000000000000000000000000..65d4cc6bffc2f08a31ca5828d2805431a88fe1f4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/poweruser.go @@ -0,0 +1,49 @@ +package cli + +import ( + "fmt" + + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/cmd/syft/cli/poweruser" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/config" + "github.com/spf13/cobra" + "github.com/spf13/viper" +) + +const powerUserExample = ` {{.appName}} {{.command}} + DEPRECATED - THIS COMMAND WILL BE REMOVED in v1.0.0 + Only image sources are supported (e.g. docker: , podman: , docker-archive: , oci: , etc.), the directory source (dir:) is not supported, template outputs are not supported. + All behavior is controlled via application configuration and environment variables (see https://github.com/anchore/syft#configuration) +` + +func PowerUser(v *viper.Viper, app *config.Application, ro *options.RootOptions) *cobra.Command { + cmd := &cobra.Command{ + Use: "power-user [IMAGE]", + Short: "Run bulk operations on container images", + Example: internal.Tprintf(powerUserExample, map[string]interface{}{ + "appName": internal.ApplicationName, + "command": "power-user", + }), + Args: func(cmd *cobra.Command, args []string) error { + if err := app.LoadAllValues(v, ro.Config); err != nil { + return fmt.Errorf("invalid application config: %v", err) + } + // configure logging for command + newLogWrapper(app) + logApplicationConfig(app) + return validateArgs(cmd, args) + }, + Hidden: true, + SilenceUsage: true, + SilenceErrors: true, + RunE: func(cmd *cobra.Command, args []string) error { + if app.CheckForAppUpdate { + checkForApplicationUpdate() + } + return poweruser.Run(cmd.Context(), app, args) + }, + } + + return cmd +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/poweruser/poweruser.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/poweruser/poweruser.go new file mode 100644 index 0000000000000000000000000000000000000000..1908a1650b5f38e67ee2939eb16bbfb27beabd3f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/poweruser/poweruser.go @@ -0,0 +1,117 @@ +package poweruser + +import ( + "context" + "fmt" + "os" + + "github.com/anchore/stereoscope" + "github.com/anchore/syft/cmd/syft/cli/eventloop" + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/cmd/syft/cli/packages" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/internal/formats/syftjson" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/internal/ui" + "github.com/anchore/syft/internal/version" + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" + "github.com/gookit/color" + "github.com/wagoodman/go-partybus" +) + +func Run(ctx context.Context, app *config.Application, args []string) error { + writer, err := sbom.NewWriter(sbom.WriterOption{ + Format: syftjson.Format(), + Path: app.File, + }) + if err != nil { + return err + } + + defer func() { + if err := writer.Close(); err != nil { + log.Warnf("unable to write to report destination: %+v", err) + } + + // inform user at end of run that command will be removed + deprecated := color.Style{color.Red, color.OpBold}.Sprint("DEPRECATED: This command will be removed in v1.0.0") + fmt.Fprintln(os.Stderr, deprecated) + }() + + userInput := args[0] + si, err := source.ParseInput(userInput, app.Platform, true) + if err != nil { + return fmt.Errorf("could not generate source input for packages command: %w", err) + } + + eventBus := partybus.NewBus() + stereoscope.SetBus(eventBus) + syft.SetBus(eventBus) + subscription := eventBus.Subscribe() + + return eventloop.EventLoop( + execWorker(app, *si, writer), + eventloop.SetupSignals(), + subscription, + stereoscope.Cleanup, + ui.Select(options.IsVerbose(app), app.Quiet)..., + ) +} + +func execWorker(app *config.Application, si source.Input, writer sbom.Writer) <-chan error { + errs := make(chan error) + go func() { + defer close(errs) + + app.Secrets.Cataloger.Enabled = true + app.FileMetadata.Cataloger.Enabled = true + app.FileContents.Cataloger.Enabled = true + app.FileClassification.Cataloger.Enabled = true + tasks, err := eventloop.Tasks(app) + if err != nil { + errs <- err + return + } + + src, cleanup, err := source.New(si, app.Registry.ToOptions(), app.Exclusions) + if err != nil { + errs <- err + return + } + if cleanup != nil { + defer cleanup() + } + + s := sbom.SBOM{ + Source: src.Metadata, + Descriptor: sbom.Descriptor{ + Name: internal.ApplicationName, + Version: version.FromBuild().Version, + Configuration: app, + }, + } + + var relationships []<-chan artifact.Relationship + for _, task := range tasks { + c := make(chan artifact.Relationship) + relationships = append(relationships, c) + + go eventloop.RunTask(task, &s.Artifacts, src, c, errs) + } + + s.Relationships = append(s.Relationships, packages.MergeRelationships(relationships...)...) + + bus.Publish(partybus.Event{ + Type: event.Exit, + Value: func() error { return writer.Write(s) }, + }) + }() + + return errs +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/version.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/version.go new file mode 100644 index 0000000000000000000000000000000000000000..078fb0057816099f77d0b6b246e449357a853c04 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/cli/version.go @@ -0,0 +1,71 @@ +package cli + +import ( + "encoding/json" + "fmt" + "log" + "os" + + "github.com/anchore/syft/cmd/syft/cli/options" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/internal/version" + "github.com/spf13/cobra" + "github.com/spf13/viper" +) + +func Version(v *viper.Viper, app *config.Application) *cobra.Command { + o := &options.VersionOptions{} + cmd := &cobra.Command{ + Use: "version", + Short: "show the version", + RunE: func(cmd *cobra.Command, args []string) error { + return printVersion(o.Output) + }, + } + + err := o.AddFlags(cmd, v) + if err != nil { + log.Fatal(err) + } + + return cmd +} + +func printVersion(output string) error { + versionInfo := version.FromBuild() + + switch output { + case "text": + fmt.Println("Application: ", internal.ApplicationName) + fmt.Println("Version: ", versionInfo.Version) + fmt.Println("JsonSchemaVersion: ", internal.JSONSchemaVersion) + fmt.Println("BuildDate: ", versionInfo.BuildDate) + fmt.Println("GitCommit: ", versionInfo.GitCommit) + fmt.Println("GitDescription: ", versionInfo.GitDescription) + fmt.Println("Platform: ", versionInfo.Platform) + fmt.Println("GoVersion: ", versionInfo.GoVersion) + fmt.Println("Compiler: ", versionInfo.Compiler) + + case "json": + enc := json.NewEncoder(os.Stdout) + enc.SetEscapeHTML(false) + enc.SetIndent("", " ") + err := enc.Encode(&struct { + version.Version + Application string `json:"application"` + }{ + Version: versionInfo, + Application: internal.ApplicationName, + }) + if err != nil { + fmt.Printf("failed to show version information: %+v\n", err) + os.Exit(1) + } + default: + fmt.Printf("unsupported output format: %s\n", output) + os.Exit(1) + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/cmd/syft/main.go b/ci/tools/openeuler-purl/syft-dev/cmd/syft/main.go new file mode 100644 index 0000000000000000000000000000000000000000..51d42fd6d1b0d11ed26590165c649ed2f8709dca --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/cmd/syft/main.go @@ -0,0 +1,18 @@ +package main + +import ( + "log" + + "github.com/anchore/syft/cmd/syft/cli" +) + +func main() { + cli, err := cli.New() + if err != nil { + log.Fatalf("error during command construction: %v", err) + } + + if err := cli.Execute(); err != nil { + log.Fatalf("error during command execution: %v", err) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/go.mod b/ci/tools/openeuler-purl/syft-dev/go.mod new file mode 100644 index 0000000000000000000000000000000000000000..11b64061b497a72c20a039c8da352fd4727f099d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/go.mod @@ -0,0 +1,327 @@ +module github.com/anchore/syft + +go 1.18 + +require ( + github.com/CycloneDX/cyclonedx-go v0.5.2 + github.com/acarl005/stripansi v0.0.0-20180116102854-5a71ef0e047d + github.com/acobaugh/osrelease v0.1.0 + github.com/adrg/xdg v0.3.3 + github.com/alecthomas/jsonschema v0.0.0-20210301060011-54c507b6f074 + github.com/anchore/client-go v0.0.0-20210222170800-9c70f9b80bcf + github.com/anchore/go-macholibre v0.0.0-20220308212642-53e6d0aaf6fb + github.com/anchore/go-testutils v0.0.0-20200925183923-d5f45b0d3c04 + github.com/anchore/go-version v1.2.2-0.20200701162849-18adb9c92b9b + github.com/anchore/packageurl-go v0.1.1-0.20220428202044-a072fa3cb6d7 + github.com/antihax/optional v1.0.0 + github.com/bmatcuk/doublestar/v4 v4.0.2 + github.com/dustin/go-humanize v1.0.0 + github.com/facebookincubator/nvdtools v0.1.4 + github.com/go-test/deep v1.0.8 + github.com/google/go-cmp v0.5.8 + github.com/google/uuid v1.3.0 + github.com/gookit/color v1.4.2 + github.com/hashicorp/go-multierror v1.1.1 + github.com/jinzhu/copier v0.3.2 + github.com/mgutz/ansi v0.0.0-20200706080929-d51e80ef957d // indirect + github.com/mholt/archiver/v3 v3.5.1 + github.com/microsoft/go-rustaudit v0.0.0-20220730194248-4b17361d90a5 + github.com/mitchellh/go-homedir v1.1.0 + github.com/mitchellh/hashstructure/v2 v2.0.2 + github.com/mitchellh/mapstructure v1.5.0 + github.com/olekukonko/tablewriter v0.0.5 + github.com/pelletier/go-toml v1.9.5 + // pinned to pull in 386 arch fix: https://github.com/scylladb/go-set/commit/cc7b2070d91ebf40d233207b633e28f5bd8f03a5 + github.com/scylladb/go-set v1.0.3-0.20200225121959-cc7b2070d91e + github.com/sergi/go-diff v1.2.0 + github.com/sirupsen/logrus v1.9.0 + github.com/spdx/tools-golang v0.2.0 + github.com/spf13/afero v1.8.2 + github.com/spf13/cobra v1.5.0 + github.com/spf13/pflag v1.0.5 + github.com/spf13/viper v1.12.0 + github.com/stretchr/testify v1.8.0 + github.com/vifraa/gopom v0.1.0 + github.com/wagoodman/go-partybus v0.0.0-20210627031916-db1f5573bbc5 + github.com/wagoodman/go-progress v0.0.0-20200731105512-1020f39e6240 + github.com/wagoodman/jotframe v0.0.0-20211129225309-56b0d0a4aebb + github.com/x-cray/logrus-prefixed-formatter v0.5.2 + github.com/xeipuuv/gojsonschema v1.2.0 + golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4 + golang.org/x/net v0.0.0-20220805013720-a33c5aa5df48 + golang.org/x/term v0.0.0-20220526004731-065cf7ba2467 + gopkg.in/yaml.v2 v2.4.0 +) + +require ( + github.com/Masterminds/sprig/v3 v3.2.2 + github.com/anchore/stereoscope v0.0.0-20220829182958-659c89aa659f + github.com/docker/docker v20.10.17+incompatible + github.com/google/go-containerregistry v0.11.0 + github.com/in-toto/in-toto-golang v0.3.4-0.20220709202702-fa494aaa0add + github.com/knqyf263/go-rpmdb v0.0.0-20220629110411-9a3bd2ebb923 + github.com/sassoftware/go-rpmutils v0.2.0 + github.com/sigstore/cosign v1.11.1 + github.com/sigstore/rekor v0.11.0 + github.com/sigstore/sigstore v1.4.0 + github.com/vbatts/go-mtree v0.5.0 + gopkg.in/yaml.v3 v3.0.1 +) + +require ( + bitbucket.org/creachadair/shell v0.0.7 // indirect + cloud.google.com/go/compute v1.7.0 // indirect + github.com/Azure/azure-sdk-for-go v66.0.0+incompatible // indirect + github.com/Azure/go-autorest v14.2.0+incompatible // indirect + github.com/Azure/go-autorest/autorest v0.11.28 // indirect + github.com/Azure/go-autorest/autorest/adal v0.9.20 // indirect + github.com/Azure/go-autorest/autorest/azure/auth v0.5.11 // indirect + github.com/Azure/go-autorest/autorest/azure/cli v0.4.5 // indirect + github.com/Azure/go-autorest/autorest/date v0.3.0 // indirect + github.com/Azure/go-autorest/logger v0.2.1 // indirect + github.com/Azure/go-autorest/tracing v0.6.0 // indirect + github.com/DataDog/zstd v1.4.5 // indirect + github.com/Masterminds/goutils v1.1.1 // indirect + github.com/Masterminds/semver/v3 v3.1.1 // indirect + github.com/Microsoft/go-winio v0.5.2 // indirect + github.com/ThalesIgnite/crypto11 v1.2.5 // indirect + github.com/asaskevich/govalidator v0.0.0-20210307081110-f21760c49a8d // indirect + github.com/aws/aws-sdk-go-v2 v1.16.11 // indirect + github.com/aws/aws-sdk-go-v2/config v1.17.1 // indirect + github.com/aws/aws-sdk-go-v2/credentials v1.12.14 // indirect + github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.12.12 // indirect + github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.18 // indirect + github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.4.12 // indirect + github.com/aws/aws-sdk-go-v2/internal/ini v1.3.19 // indirect + github.com/aws/aws-sdk-go-v2/service/ecr v1.15.0 // indirect + github.com/aws/aws-sdk-go-v2/service/ecrpublic v1.12.0 // indirect + github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.9.12 // indirect + github.com/aws/aws-sdk-go-v2/service/sso v1.11.17 // indirect + github.com/aws/aws-sdk-go-v2/service/sts v1.16.13 // indirect + github.com/aws/smithy-go v1.12.1 // indirect + github.com/awslabs/amazon-ecr-credential-helper/ecr-login v0.0.0-20220517224237-e6f29200ae04 // indirect + github.com/benbjohnson/clock v1.1.0 // indirect + github.com/beorn7/perks v1.0.1 // indirect + github.com/bgentry/speakeasy v0.1.0 // indirect + github.com/blang/semver v3.5.1+incompatible // indirect + github.com/cenkalti/backoff/v4 v4.1.3 // indirect + github.com/census-instrumentation/opencensus-proto v0.3.0 // indirect + github.com/cespare/xxhash/v2 v2.1.2 // indirect + github.com/chrismellard/docker-credential-acr-env v0.0.0-20220119192733-fe33c00cee21 // indirect + github.com/cncf/udpa/go v0.0.0-20210930031921-04548b0d99d4 // indirect + github.com/cncf/xds/go v0.0.0-20211130200136-a8f946100490 // indirect + github.com/common-nighthawk/go-figure v0.0.0-20210622060536-734e95fb86be // indirect + github.com/containerd/containerd v1.5.13 // indirect + github.com/containerd/stargz-snapshotter/estargz v0.12.0 // indirect + github.com/coreos/go-oidc/v3 v3.2.0 // indirect + github.com/coreos/go-semver v0.3.0 // indirect + github.com/coreos/go-systemd/v22 v22.3.2 // indirect + github.com/cpuguy83/go-md2man/v2 v2.0.2 // indirect + github.com/cyberphone/json-canonicalization v0.0.0-20210823021906-dc406ceaf94b // indirect + github.com/davecgh/go-spew v1.1.1 // indirect + github.com/dimchansky/utfbom v1.1.1 // indirect + github.com/docker/cli v20.10.17+incompatible // indirect + github.com/docker/distribution v2.8.1+incompatible // indirect + github.com/docker/docker-credential-helpers v0.6.4 // indirect + github.com/docker/go-connections v0.4.0 // indirect + github.com/docker/go-units v0.4.0 // indirect + github.com/dsnet/compress v0.0.2-0.20210315054119-f66993602bf5 // indirect + github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1 // indirect + github.com/envoyproxy/protoc-gen-validate v0.6.2 // indirect + github.com/fsnotify/fsnotify v1.5.4 // indirect + github.com/fullstorydev/grpcurl v1.8.6 // indirect + github.com/gabriel-vasile/mimetype v1.4.0 // indirect + github.com/go-chi/chi v4.1.2+incompatible // indirect + github.com/go-logr/logr v1.2.3 // indirect + github.com/go-logr/stdr v1.2.2 // indirect + github.com/go-openapi/analysis v0.21.4 // indirect + github.com/go-openapi/errors v0.20.3 // indirect + github.com/go-openapi/jsonpointer v0.19.5 // indirect + github.com/go-openapi/jsonreference v0.20.0 // indirect + github.com/go-openapi/loads v0.21.2 // indirect + github.com/go-openapi/runtime v0.24.1 // indirect + github.com/go-openapi/spec v0.20.7 // indirect + github.com/go-openapi/strfmt v0.21.3 // indirect + github.com/go-openapi/swag v0.22.3 // indirect + github.com/go-openapi/validate v0.22.0 // indirect + github.com/go-piv/piv-go v1.10.0 // indirect + github.com/go-playground/locales v0.14.0 // indirect + github.com/go-playground/universal-translator v0.18.0 // indirect + github.com/go-playground/validator/v10 v10.11.0 // indirect + github.com/go-restruct/restruct v1.2.0-alpha // indirect + github.com/gogo/protobuf v1.3.2 // indirect + github.com/golang-jwt/jwt v3.2.2+incompatible // indirect + github.com/golang-jwt/jwt/v4 v4.4.2 // indirect + github.com/golang/glog v1.0.0 // indirect + github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect + github.com/golang/mock v1.6.0 // indirect + github.com/golang/protobuf v1.5.2 // indirect + github.com/golang/snappy v0.0.4 // indirect + github.com/google/btree v1.0.1 // indirect + github.com/google/certificate-transparency-go v1.1.3 // indirect + github.com/google/go-github/v45 v45.2.0 // indirect + github.com/google/go-querystring v1.1.0 // indirect + github.com/google/gofuzz v1.2.0 // indirect + github.com/google/trillian v1.4.1 // indirect + github.com/googleapis/enterprise-certificate-proxy v0.1.0 // indirect + github.com/googleapis/gnostic v0.5.5 // indirect + github.com/gorilla/websocket v1.4.2 // indirect + github.com/grpc-ecosystem/go-grpc-middleware v1.3.0 // indirect + github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0 // indirect + github.com/grpc-ecosystem/grpc-gateway v1.16.0 // indirect + github.com/grpc-ecosystem/grpc-gateway/v2 v2.11.2 // indirect + github.com/hashicorp/errwrap v1.1.0 // indirect + github.com/hashicorp/go-cleanhttp v0.5.2 // indirect + github.com/hashicorp/go-retryablehttp v0.7.1 // indirect + github.com/hashicorp/hcl v1.0.0 // indirect + github.com/huandu/xstrings v1.3.2 // indirect + github.com/iancoleman/orderedmap v0.0.0-20190318233801-ac98e3ecb4b0 // indirect + github.com/imdario/mergo v0.3.12 // indirect + github.com/inconshreveable/mousetrap v1.0.0 // indirect + github.com/jedisct1/go-minisign v0.0.0-20211028175153-1c139d1cc84b // indirect + github.com/jhump/protoreflect v1.12.0 // indirect + github.com/jmespath/go-jmespath v0.4.0 // indirect + github.com/jonboulle/clockwork v0.3.0 // indirect + github.com/josharian/intern v1.0.0 // indirect + github.com/json-iterator/go v1.1.12 // indirect + github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51 // indirect + github.com/klauspost/compress v1.15.9 // indirect + github.com/klauspost/pgzip v1.2.5 // indirect + github.com/leodido/go-urn v1.2.1 // indirect + github.com/letsencrypt/boulder v0.0.0-20220723181115-27de4befb95e // indirect + github.com/logrusorgru/aurora v0.0.0-20200102142835-e9ef32dff381 // indirect + github.com/magiconair/properties v1.8.6 // indirect + github.com/mailru/easyjson v0.7.7 // indirect + github.com/mattn/go-colorable v0.1.12 // indirect + github.com/mattn/go-isatty v0.0.14 // indirect + github.com/mattn/go-runewidth v0.0.13 // indirect + github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369 // indirect + github.com/miekg/pkcs11 v1.1.1 // indirect + github.com/mitchellh/copystructure v1.2.0 // indirect + github.com/mitchellh/reflectwalk v1.0.2 // indirect + github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect + github.com/modern-go/reflect2 v1.0.2 // indirect + github.com/nwaples/rardecode v1.1.0 // indirect + github.com/oklog/ulid v1.3.1 // indirect + github.com/opencontainers/go-digest v1.0.0 // indirect + github.com/opencontainers/image-spec v1.0.3-0.20220114050600-8b9d41f48198 // indirect + github.com/opentracing/opentracing-go v1.2.0 // indirect + github.com/pelletier/go-toml/v2 v2.0.1 // indirect + github.com/pierrec/lz4/v4 v4.1.15 // indirect + github.com/pmezard/go-difflib v1.0.0 // indirect + github.com/prometheus/client_golang v1.13.0 // indirect + github.com/prometheus/client_model v0.2.0 // indirect + github.com/prometheus/common v0.37.0 // indirect + github.com/prometheus/procfs v0.8.0 // indirect + github.com/remyoudompheng/bigfft v0.0.0-20200410134404-eec4a21b6bb0 // indirect + github.com/rivo/uniseg v0.2.0 // indirect + github.com/russross/blackfriday/v2 v2.1.0 // indirect + github.com/sassoftware/relic v0.0.0-20210427151427-dfb082b79b74 // indirect + github.com/secure-systems-lab/go-securesystemslib v0.4.0 // indirect + github.com/segmentio/ksuid v1.0.4 // indirect + github.com/shibumi/go-pathspec v1.3.0 // indirect + github.com/shopspring/decimal v1.2.0 // indirect + github.com/sigstore/fulcio v0.5.3 // indirect + github.com/skratchdot/open-golang v0.0.0-20200116055534-eef842397966 // indirect + github.com/soheilhy/cmux v0.1.5 // indirect + github.com/spf13/cast v1.5.0 // indirect + github.com/spf13/jwalterweatherman v1.1.0 // indirect + github.com/spiffe/go-spiffe/v2 v2.1.1 // indirect + github.com/stretchr/objx v0.4.0 // indirect + github.com/subosito/gotenv v1.3.0 // indirect + github.com/sylabs/sif/v2 v2.7.2 // indirect + github.com/sylabs/squashfs v0.6.1 // indirect + github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 // indirect + github.com/tent/canonical-json-go v0.0.0-20130607151641-96e4ba3a7613 // indirect + github.com/thales-e-security/pool v0.0.2 // indirect + github.com/therootcompany/xz v1.0.1 // indirect + github.com/theupdateframework/go-tuf v0.3.1 // indirect + github.com/titanous/rocacheck v0.0.0-20171023193734-afe73141d399 // indirect + github.com/tmc/grpc-websocket-proxy v0.0.0-20201229170055-e5319fda7802 // indirect + github.com/transparency-dev/merkle v0.0.1 // indirect + github.com/ulikunitz/xz v0.5.10 // indirect + github.com/urfave/cli v1.22.7 // indirect + github.com/vbatts/tar-split v0.11.2 // indirect + github.com/xanzy/go-gitlab v0.73.1 // indirect + github.com/xeipuuv/gojsonpointer v0.0.0-20190905194746-02993c407bfb // indirect + github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415 // indirect + github.com/xi2/xz v0.0.0-20171230120015-48954b6210f8 // indirect + github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2 // indirect + github.com/xo/terminfo v0.0.0-20210125001918-ca9a967f8778 // indirect + github.com/zeebo/errs v1.2.2 // indirect + go.etcd.io/bbolt v1.3.6 // indirect + go.etcd.io/etcd/api/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/client/pkg/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/client/v2 v2.306.0-alpha.0 // indirect + go.etcd.io/etcd/client/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/etcdctl/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/etcdutl/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/pkg/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/raft/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/server/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/tests/v3 v3.6.0-alpha.0 // indirect + go.etcd.io/etcd/v3 v3.6.0-alpha.0 // indirect + go.mongodb.org/mongo-driver v1.10.0 // indirect + go.opencensus.io v0.23.0 // indirect + go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.28.0 // indirect + go.opentelemetry.io/otel v1.7.0 // indirect + go.opentelemetry.io/otel/exporters/otlp/internal/retry v1.7.0 // indirect + go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.7.0 // indirect + go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.7.0 // indirect + go.opentelemetry.io/otel/sdk v1.7.0 // indirect + go.opentelemetry.io/otel/trace v1.7.0 // indirect + go.opentelemetry.io/proto/otlp v0.16.0 // indirect + go.uber.org/atomic v1.10.0 // indirect + go.uber.org/multierr v1.8.0 // indirect + go.uber.org/zap v1.22.0 // indirect + golang.org/x/oauth2 v0.0.0-20220722155238-128564f6959c // indirect + golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4 // indirect + golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10 // indirect + golang.org/x/text v0.3.8-0.20211004125949-5bd84dd9b33b // indirect + golang.org/x/time v0.0.0-20220722155302-e5dcc9cfc0b9 // indirect + golang.org/x/tools v0.1.11 // indirect + golang.org/x/xerrors v0.0.0-20220609144429-65e65417b02f // indirect + google.golang.org/api v0.93.0 // indirect + google.golang.org/appengine v1.6.7 // indirect + google.golang.org/genproto v0.0.0-20220805133916-01dd62135a58 // indirect + google.golang.org/grpc v1.48.0 // indirect + google.golang.org/protobuf v1.28.1 // indirect + gopkg.in/cheggaaa/pb.v1 v1.0.28 // indirect + gopkg.in/inf.v0 v0.9.1 // indirect + gopkg.in/ini.v1 v1.67.0 // indirect + gopkg.in/natefinch/lumberjack.v2 v2.0.0 // indirect + gopkg.in/square/go-jose.v2 v2.6.0 // indirect + k8s.io/api v0.23.5 // indirect + k8s.io/apimachinery v0.23.5 // indirect + k8s.io/client-go v0.23.5 // indirect + k8s.io/klog/v2 v2.60.1-0.20220317184644-43cc75f9ae89 // indirect + k8s.io/kube-openapi v0.0.0-20220124234850-424119656bbf // indirect + k8s.io/utils v0.0.0-20220210201930-3a6ce19ff2f9 // indirect + lukechampine.com/uint128 v1.1.1 // indirect + modernc.org/cc/v3 v3.36.0 // indirect + modernc.org/ccgo/v3 v3.16.6 // indirect + modernc.org/libc v1.16.7 // indirect + modernc.org/mathutil v1.4.1 // indirect + modernc.org/memory v1.1.1 // indirect + modernc.org/opt v0.1.1 // indirect + modernc.org/sqlite v1.17.3 // indirect + modernc.org/strutil v1.1.1 // indirect + modernc.org/token v1.0.0 // indirect + sigs.k8s.io/json v0.0.0-20211208200746-9f7c6b3444d2 // indirect + sigs.k8s.io/release-utils v0.7.3 // indirect + sigs.k8s.io/structured-merge-diff/v4 v4.2.1 // indirect + sigs.k8s.io/yaml v1.3.0 // indirect +) + +require ( + // we are hinting brotli to latest due to warning when installing archiver v3: + // go: warning: github.com/andybalholm/brotli@v1.0.1: retracted by module author: occasional panics and data corruption + github.com/andybalholm/brotli v1.0.4 // indirect + github.com/pkg/errors v0.9.1 + golang.org/x/crypto v0.0.0-20220722155217-630584e8d5aa // indirect +) + +retract ( + v0.53.2 + v0.53.1 // Published accidentally with incorrect license in depdencies +) diff --git a/ci/tools/openeuler-purl/syft-dev/go.sum b/ci/tools/openeuler-purl/syft-dev/go.sum new file mode 100644 index 0000000000000000000000000000000000000000..acc61d985e33f350d4c59c2c039cef9edfd5f986 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/go.sum @@ -0,0 +1,2952 @@ +4d63.com/gochecknoglobals v0.1.0/go.mod h1:wfdC5ZjKSPr7CybKEcgJhUOgeAQW1+7WcyK8OvUilfo= +bazil.org/fuse v0.0.0-20160811212531-371fbbdaa898/go.mod h1:Xbm+BRKSBEpa4q4hTSxohYNQpsxXPbPry4JJWOB3LB8= +bazil.org/fuse v0.0.0-20180421153158-65cc252bf669/go.mod h1:Xbm+BRKSBEpa4q4hTSxohYNQpsxXPbPry4JJWOB3LB8= +bitbucket.org/creachadair/shell v0.0.6/go.mod h1:8Qqi/cYk7vPnsOePHroKXDJYmb5x7ENhtiFtfZq8K+M= +bitbucket.org/creachadair/shell v0.0.7 h1:Z96pB6DkSb7F3Y3BBnJeOZH2gazyMTWlvecSD4vDqfk= +bitbucket.org/creachadair/shell v0.0.7/go.mod h1:oqtXSSvSYr4624lnnabXHaBsYW6RD80caLi2b3hJk0U= +cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= +cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= +cloud.google.com/go v0.38.0/go.mod h1:990N+gfupTy94rShfmMCWGDn0LpTmnzTp2qbd1dvSRU= +cloud.google.com/go v0.39.0/go.mod h1:rVLT6fkc8chs9sfPtFc1SBH6em7n+ZoXaG+87tDISts= +cloud.google.com/go v0.44.1/go.mod h1:iSa0KzasP4Uvy3f1mN/7PiObzGgflwredwwASm/v6AU= +cloud.google.com/go v0.44.2/go.mod h1:60680Gw3Yr4ikxnPRS/oxxkBccT6SA1yMk63TGekxKY= +cloud.google.com/go v0.44.3/go.mod h1:60680Gw3Yr4ikxnPRS/oxxkBccT6SA1yMk63TGekxKY= +cloud.google.com/go v0.45.1/go.mod h1:RpBamKRgapWJb87xiFSdk4g1CME7QZg3uwTez+TSTjc= +cloud.google.com/go v0.46.3/go.mod h1:a6bKKbmY7er1mI7TEI4lsAkts/mkhTSZK8w33B4RAg0= +cloud.google.com/go v0.50.0/go.mod h1:r9sluTvynVuxRIOHXQEHMFffphuXHOMZMycpNR5e6To= +cloud.google.com/go v0.52.0/go.mod h1:pXajvRH/6o3+F9jDHZWQ5PbGhn+o8w9qiu/CffaVdO4= +cloud.google.com/go v0.53.0/go.mod h1:fp/UouUEsRkN6ryDKNW/Upv/JBKnv6WDthjR6+vze6M= +cloud.google.com/go v0.54.0/go.mod h1:1rq2OEkV3YMf6n/9ZvGWI3GWw0VoqH/1x2nd8Is/bPc= +cloud.google.com/go v0.56.0/go.mod h1:jr7tqZxxKOVYizybht9+26Z/gUq7tiRzu+ACVAMbKVk= +cloud.google.com/go v0.57.0/go.mod h1:oXiQ6Rzq3RAkkY7N6t3TcE6jE+CIBBbA36lwQ1JyzZs= +cloud.google.com/go v0.60.0/go.mod h1:yw2G51M9IfRboUH61Us8GqCeF1PzPblB823Mn2q2eAU= +cloud.google.com/go v0.62.0/go.mod h1:jmCYTdRCQuc1PHIIJ/maLInMho30T/Y0M4hTdTShOYc= +cloud.google.com/go v0.65.0/go.mod h1:O5N8zS7uWy9vkA9vayVHs65eM1ubvY4h553ofrNHObY= +cloud.google.com/go v0.72.0/go.mod h1:M+5Vjvlc2wnp6tjzE102Dw08nGShTscUx2nZMufOKPI= +cloud.google.com/go v0.74.0/go.mod h1:VV1xSbzvo+9QJOxLDaJfTjx5e+MePCpCWwvftOeQmWk= +cloud.google.com/go v0.75.0/go.mod h1:VGuuCn7PG0dwsd5XPVm2Mm3wlh3EL55/79EKB6hlPTY= +cloud.google.com/go v0.78.0/go.mod h1:QjdrLG0uq+YwhjoVOLsS1t7TW8fs36kLs4XO5R5ECHg= +cloud.google.com/go v0.79.0/go.mod h1:3bzgcEeQlzbuEAYu4mrWhKqWjmpprinYgKJLgKHnbb8= +cloud.google.com/go v0.81.0/go.mod h1:mk/AM35KwGk/Nm2YSeZbxXdrNK3KZOYHmLkOqC2V6E0= +cloud.google.com/go v0.83.0/go.mod h1:Z7MJUsANfY0pYPdw0lbnivPx4/vhy/e2FEkSkF7vAVY= +cloud.google.com/go v0.84.0/go.mod h1:RazrYuxIK6Kb7YrzzhPoLmCVzl7Sup4NrbKPg8KHSUM= +cloud.google.com/go v0.87.0/go.mod h1:TpDYlFy7vuLzZMMZ+B6iRiELaY7z/gJPaqbMx6mlWcY= +cloud.google.com/go v0.90.0/go.mod h1:kRX0mNRHe0e2rC6oNakvwQqzyDmg57xJ+SZU1eT2aDQ= +cloud.google.com/go v0.93.3/go.mod h1:8utlLll2EF5XMAV15woO4lSbWQlk8rer9aLOfLh7+YI= +cloud.google.com/go v0.94.1/go.mod h1:qAlAugsXlC+JWO+Bke5vCtc9ONxjQT3drlTTnAplMW4= +cloud.google.com/go v0.97.0/go.mod h1:GF7l59pYBVlXQIBLx3a761cZ41F9bBH3JUlihCt2Udc= +cloud.google.com/go v0.99.0/go.mod h1:w0Xx2nLzqWJPuozYQX+hFfCSI8WioryfRDzkoI/Y2ZA= +cloud.google.com/go v0.100.1/go.mod h1:fs4QogzfH5n2pBXBP9vRiU+eCny7lD2vmFZy79Iuw1U= +cloud.google.com/go v0.100.2/go.mod h1:4Xra9TjzAeYHrl5+oeLlzbM2k3mjVhZh4UqTZ//w99A= +cloud.google.com/go v0.102.0/go.mod h1:oWcCzKlqJ5zgHQt9YsaeTY9KzIvjyy0ArmiBUgpQ+nc= +cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o= +cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNFKH1/VBDHE= +cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc= +cloud.google.com/go/bigquery v1.5.0/go.mod h1:snEHRnqQbz117VIFhE8bmtwIDY80NLUZUMb4Nv6dBIg= +cloud.google.com/go/bigquery v1.7.0/go.mod h1://okPTzCYNXSlb24MZs83e2Do+h+VXtc4gLoIoXIAPc= +cloud.google.com/go/bigquery v1.8.0/go.mod h1:J5hqkt3O0uAFnINi6JXValWIb1v0goeZM77hZzJN/fQ= +cloud.google.com/go/bigquery v1.17.0/go.mod h1:pUlbH9kNOnp6ayShsqKLB6w49z14ILAaq0hrjh93Ajw= +cloud.google.com/go/compute v0.1.0/go.mod h1:GAesmwr110a34z04OlxYkATPBEfVhkymfTBXtfbBFow= +cloud.google.com/go/compute v1.3.0/go.mod h1:cCZiE1NHEtai4wiufUhW8I8S1JKkAnhnQJWM7YD99wM= +cloud.google.com/go/compute v1.5.0/go.mod h1:9SMHyhJlzhlkJqrPAc839t2BZFTSk6Jdj6mkzQJeu0M= +cloud.google.com/go/compute v1.6.0/go.mod h1:T29tfhtVbq1wvAPo0E3+7vhgmkOYeXjhFvz/FMzPu0s= +cloud.google.com/go/compute v1.6.1/go.mod h1:g85FgpzFvNULZ+S8AYq87axRKuf2Kh7deLqV/jJ3thU= +cloud.google.com/go/compute v1.7.0 h1:v/k9Eueb8aAJ0vZuxKMrgm6kPhCLZU9HxFU+AFDs9Uk= +cloud.google.com/go/compute v1.7.0/go.mod h1:435lt8av5oL9P3fv1OEzSbSUe+ybHXGMPQHHZWZxy9U= +cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7TKLgZqpHYE= +cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk= +cloud.google.com/go/datastore v1.5.0/go.mod h1:RGUNM0FFAVkYA94BLTxoXBgfIyY1Riq67TwaBXH0lwc= +cloud.google.com/go/firestore v1.1.0/go.mod h1:ulACoGHTpvq5r8rxGJ4ddJZBZqakUQqClKRT5SZwBmk= +cloud.google.com/go/firestore v1.6.0/go.mod h1:afJwI0vaXwAG54kI7A//lP/lSPDkQORQuMkv56TxEPU= +cloud.google.com/go/iam v0.1.1/go.mod h1:CKqrcnI/suGpybEHxZ7BMehL0oA4LpdyJdUlTl9jVMw= +cloud.google.com/go/iam v0.3.0/go.mod h1:XzJPvDayI+9zsASAFO68Hk07u3z+f+JrT2xXNdp4bnY= +cloud.google.com/go/monitoring v1.1.0/go.mod h1:L81pzz7HKn14QCMaCs6NTQkdBnE87TElyanS95vIcl4= +cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I= +cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw= +cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA= +cloud.google.com/go/pubsub v1.3.1/go.mod h1:i+ucay31+CNRpDW4Lu78I4xXG+O1r/MAHgjpRVR+TSU= +cloud.google.com/go/pubsub v1.5.0/go.mod h1:ZEwJccE3z93Z2HWvstpri00jOg7oO4UZDtKhwDwqF0w= +cloud.google.com/go/pubsub v1.11.0-beta.schemas/go.mod h1:llNLsvx+RnsZJoY481TzC1XcdB2hWdR6gSWM5O4vgfs= +cloud.google.com/go/spanner v1.7.0/go.mod h1:sd3K2gZ9Fd0vMPLXzeCrF6fq4i63Q7aTLW/lBIfBkIk= +cloud.google.com/go/spanner v1.17.0/go.mod h1:+17t2ixFwRG4lWRwE+5kipDR9Ef07Jkmc8z0IbMDKUs= +cloud.google.com/go/spanner v1.18.0/go.mod h1:LvAjUXPeJRGNuGpikMULjhLj/t9cRvdc+fxRoLiugXA= +cloud.google.com/go/spanner v1.31.0/go.mod h1:ztDJVUZgEA2xc7HjSNQG+d+2L0bOSsw876/5Hnr78U8= +cloud.google.com/go/storage v1.0.0/go.mod h1:IhtSnM/ZTZV8YYJWCY8RULGVqBDmpoyjwiyrjsg+URw= +cloud.google.com/go/storage v1.5.0/go.mod h1:tpKbwo567HUNpVclU5sGELwQWBDZ8gh0ZeosJ0Rtdos= +cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohlUTyfDhBk= +cloud.google.com/go/storage v1.8.0/go.mod h1:Wv1Oy7z6Yz3DshWRJFhqM/UCfaWIRTdp0RXyy7KQOVs= +cloud.google.com/go/storage v1.10.0/go.mod h1:FLPqc6j+Ki4BU591ie1oL6qBQGu2Bl/tZ9ullr3+Kg0= +cloud.google.com/go/storage v1.14.0/go.mod h1:GrKmX003DSIwi9o29oFT7YDnHYwZoctc3fOKtUw0Xmo= +cloud.google.com/go/storage v1.15.0/go.mod h1:mjjQMoxxyGH7Jr8K5qrx6N2O0AHsczI61sMNn03GIZI= +cloud.google.com/go/storage v1.22.1/go.mod h1:S8N1cAStu7BOeFfE8KAQzmyyLkK8p/vmRq6kuBTW58Y= +cloud.google.com/go/trace v1.0.0/go.mod h1:4iErSByzxkyHWzzlAj63/Gmjz0NH1ASqhJguHpGcr6A= +code.gitea.io/sdk/gitea v0.11.3/go.mod h1:z3uwDV/b9Ls47NGukYM9XhnHtqPh/J+t40lsUrR6JDY= +contrib.go.opencensus.io/exporter/aws v0.0.0-20181029163544-2befc13012d0/go.mod h1:uu1P0UCM/6RbsMrgPa98ll8ZcHM858i/AD06a9aLRCA= +contrib.go.opencensus.io/exporter/ocagent v0.5.0/go.mod h1:ImxhfLRpxoYiSq891pBrLVhN+qmP8BTVvdH2YLs7Gl0= +contrib.go.opencensus.io/exporter/stackdriver v0.12.1/go.mod h1:iwB6wGarfphGGe/e5CWqyUk/cLzKnWsOKPVW3no6OTw= +contrib.go.opencensus.io/exporter/stackdriver v0.13.4/go.mod h1:aXENhDJ1Y4lIg4EUaVTwzvYETVNZk10Pu26tevFKLUc= +contrib.go.opencensus.io/exporter/stackdriver v0.13.5/go.mod h1:aXENhDJ1Y4lIg4EUaVTwzvYETVNZk10Pu26tevFKLUc= +contrib.go.opencensus.io/exporter/stackdriver v0.13.12/go.mod h1:mmxnWlrvrFdpiOHOhxBaVi1rkc0WOqhgfknj4Yg0SeQ= +contrib.go.opencensus.io/integrations/ocsql v0.1.4/go.mod h1:8DsSdjz3F+APR+0z0WkU1aRorQCFfRxvqjUUPMbF3fE= +contrib.go.opencensus.io/resource v0.1.1/go.mod h1:F361eGI91LCmW1I/Saf+rX0+OFcigGlFvXwEGEnkRLA= +dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU= +github.com/Antonboom/errname v0.1.5/go.mod h1:DugbBstvPFQbv/5uLcRRzfrNqKE9tVdVCqWCLp6Cifo= +github.com/Antonboom/nilnil v0.1.0/go.mod h1:PhHLvRPSghY5Y7mX4TW+BHZQYo1A8flE5H20D3IPZBo= +github.com/Azure/azure-amqp-common-go/v2 v2.1.0/go.mod h1:R8rea+gJRuJR6QxTir/XuEd+YuKoUiazDC/N96FiDEU= +github.com/Azure/azure-pipeline-go v0.2.1/go.mod h1:UGSo8XybXnIGZ3epmeBw7Jdz+HiUVpqIlpz/HKHylF4= +github.com/Azure/azure-sdk-for-go v16.2.1+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc= +github.com/Azure/azure-sdk-for-go v29.0.0+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc= +github.com/Azure/azure-sdk-for-go v30.1.0+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc= +github.com/Azure/azure-sdk-for-go v46.4.0+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc= +github.com/Azure/azure-sdk-for-go v66.0.0+incompatible h1:bmmC38SlE8/E81nNADlgmVGurPWMHDX2YNXVQMrBpEE= +github.com/Azure/azure-sdk-for-go v66.0.0+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc= +github.com/Azure/azure-service-bus-go v0.9.1/go.mod h1:yzBx6/BUGfjfeqbRZny9AQIbIe3AcV9WZbAdpkoXOa0= +github.com/Azure/azure-storage-blob-go v0.8.0/go.mod h1:lPI3aLPpuLTeUwh1sViKXFxwl2B6teiRqI0deQUvsw0= +github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78/go.mod h1:LmzpDX56iTiv29bbRTIsUNlaFfuhWRQBWjQdVyAevI8= +github.com/Azure/go-ansiterm v0.0.0-20210617225240-d185dfc1b5a1 h1:UQHMgLO+TxOElx5B5HZ4hJQsoJ/PvUvKRhJHDQXO8P8= +github.com/Azure/go-autorest v10.8.1+incompatible/go.mod h1:r+4oMnoxhatjLLJ6zxSWATqVooLgysK6ZNox3g/xq24= +github.com/Azure/go-autorest v12.0.0+incompatible/go.mod h1:r+4oMnoxhatjLLJ6zxSWATqVooLgysK6ZNox3g/xq24= +github.com/Azure/go-autorest v14.2.0+incompatible h1:V5VMDjClD3GiElqLWO7mz2MxNAK/vTfRHdAubSIPRgs= +github.com/Azure/go-autorest v14.2.0+incompatible/go.mod h1:r+4oMnoxhatjLLJ6zxSWATqVooLgysK6ZNox3g/xq24= +github.com/Azure/go-autorest/autorest v0.11.1/go.mod h1:JFgpikqFJ/MleTTxwepExTKnFUKKszPS8UavbQYUMuw= +github.com/Azure/go-autorest/autorest v0.11.6/go.mod h1:V6p3pKZx1KKkJubbxnDWrzNhEIfOy/pTGasLqzHIPHs= +github.com/Azure/go-autorest/autorest v0.11.8/go.mod h1:V6p3pKZx1KKkJubbxnDWrzNhEIfOy/pTGasLqzHIPHs= +github.com/Azure/go-autorest/autorest v0.11.18/go.mod h1:dSiJPy22c3u0OtOKDNttNgqpNFY/GeWa7GH/Pz56QRA= +github.com/Azure/go-autorest/autorest v0.11.24/go.mod h1:G6kyRlFnTuSbEYkQGawPfsCswgme4iYf6rfSKUDzbCc= +github.com/Azure/go-autorest/autorest v0.11.28 h1:ndAExarwr5Y+GaHE6VCaY1kyS/HwwGGyuimVhWsHOEM= +github.com/Azure/go-autorest/autorest v0.11.28/go.mod h1:MrkzG3Y3AH668QyF9KRk5neJnGgmhQ6krbhR8Q5eMvA= +github.com/Azure/go-autorest/autorest/adal v0.9.0/go.mod h1:/c022QCutn2P7uY+/oQWWNcK9YU+MH96NgK+jErpbcg= +github.com/Azure/go-autorest/autorest/adal v0.9.4/go.mod h1:/3SMAM86bP6wC9Ev35peQDUeqFZBMH07vvUOmg4z/fE= +github.com/Azure/go-autorest/autorest/adal v0.9.5/go.mod h1:B7KF7jKIeC9Mct5spmyCB/A8CG/sEz1vwIRGv/bbw7A= +github.com/Azure/go-autorest/autorest/adal v0.9.13/go.mod h1:W/MM4U6nLxnIskrw4UwWzlHfGjwUS50aOsc/I3yuU8M= +github.com/Azure/go-autorest/autorest/adal v0.9.18/go.mod h1:XVVeme+LZwABT8K5Lc3hA4nAe8LDBVle26gTrguhhPQ= +github.com/Azure/go-autorest/autorest/adal v0.9.20 h1:gJ3E98kMpFB1MFqQCvA1yFab8vthOeD4VlFRQULxahg= +github.com/Azure/go-autorest/autorest/adal v0.9.20/go.mod h1:XVVeme+LZwABT8K5Lc3hA4nAe8LDBVle26gTrguhhPQ= +github.com/Azure/go-autorest/autorest/azure/auth v0.5.2/go.mod h1:q98IH4qgc3eWM4/WOeR5+YPmBuy8Lq0jNRDwSM0CuFk= +github.com/Azure/go-autorest/autorest/azure/auth v0.5.11 h1:P6bYXFoao05z5uhOQzbC3Qd8JqF3jUoocoTeIxkp2cA= +github.com/Azure/go-autorest/autorest/azure/auth v0.5.11/go.mod h1:84w/uV8E37feW2NCJ08uT9VBfjfUHpgLVnG2InYD6cg= +github.com/Azure/go-autorest/autorest/azure/cli v0.4.1/go.mod h1:JfDgiIO1/RPu6z42AdQTyjOoCM2MFhLqSBDvMEkDgcg= +github.com/Azure/go-autorest/autorest/azure/cli v0.4.5 h1:0W/yGmFdTIT77fvdlGZ0LMISoLHFJ7Tx4U0yeB+uFs4= +github.com/Azure/go-autorest/autorest/azure/cli v0.4.5/go.mod h1:ADQAXrkgm7acgWVUNamOgh8YNrv4p27l3Wc55oVfpzg= +github.com/Azure/go-autorest/autorest/date v0.3.0 h1:7gUk1U5M/CQbp9WoqinNzJar+8KY+LPI6wiWrP/myHw= +github.com/Azure/go-autorest/autorest/date v0.3.0/go.mod h1:BI0uouVdmngYNUzGWeSYnokU+TrmwEsOqdt8Y6sso74= +github.com/Azure/go-autorest/autorest/mocks v0.4.0/go.mod h1:LTp+uSrOhSkaKrUy935gNZuuIPPVsHlr9DSOxSayd+k= +github.com/Azure/go-autorest/autorest/mocks v0.4.1/go.mod h1:LTp+uSrOhSkaKrUy935gNZuuIPPVsHlr9DSOxSayd+k= +github.com/Azure/go-autorest/autorest/mocks v0.4.2 h1:PGN4EDXnuQbojHbU0UWoNvmu9AGVwYHG9/fkDYhtAfw= +github.com/Azure/go-autorest/autorest/mocks v0.4.2/go.mod h1:Vy7OitM9Kei0i1Oj+LvyAWMXJHeKH1MVlzFugfVrmyU= +github.com/Azure/go-autorest/autorest/to v0.4.0 h1:oXVqrxakqqV1UZdSazDOPOLvOIz+XA683u8EctwboHk= +github.com/Azure/go-autorest/autorest/validation v0.3.1 h1:AgyqjAd94fwNAoTjl/WQXg4VvFeRFpO+UhNyRXqF1ac= +github.com/Azure/go-autorest/logger v0.2.0/go.mod h1:T9E3cAhj2VqvPOtCYAvby9aBXkZmbF5NWuPV8+WeEW8= +github.com/Azure/go-autorest/logger v0.2.1 h1:IG7i4p/mDa2Ce4TRyAO8IHnVhAVF3RFU+ZtXWSmf4Tg= +github.com/Azure/go-autorest/logger v0.2.1/go.mod h1:T9E3cAhj2VqvPOtCYAvby9aBXkZmbF5NWuPV8+WeEW8= +github.com/Azure/go-autorest/tracing v0.6.0 h1:TYi4+3m5t6K48TGI9AUdb+IzbnSxvnvUMfuitfgcfuo= +github.com/Azure/go-autorest/tracing v0.6.0/go.mod h1:+vhtPC754Xsa23ID7GlGsrdKBpUA79WCAKPPZVC2DeU= +github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= +github.com/BurntSushi/toml v0.4.1 h1:GaI7EiDXDRfa8VshkTj7Fym7ha+y8/XxIgD2okUIjLw= +github.com/BurntSushi/toml v0.4.1/go.mod h1:CxXYINrC8qIiEnFrOxCa7Jy5BFHlXnUU2pbicEuybxQ= +github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo= +github.com/CycloneDX/cyclonedx-go v0.5.2 h1:CkdGw2R/tZWmEbSypJVZG+3+2SAsDjJirfIrG/RbIVg= +github.com/CycloneDX/cyclonedx-go v0.5.2/go.mod h1:nQCiF4Tvrg5Ieu8qPhYMvzPGMu5I7fANZkrSsJjl5mg= +github.com/DataDog/zstd v1.4.5 h1:EndNeuB0l9syBZhut0wns3gV1hL8zX8LIu6ZiVHWLIQ= +github.com/DataDog/zstd v1.4.5/go.mod h1:1jcaCB/ufaK+sKp1NBhlGmpz41jOoPQ35bpF36t7BBo= +github.com/Djarvur/go-err113 v0.0.0-20210108212216-aea10b59be24/go.mod h1:4UJr5HIiMZrwgkSPdsjy2uOQExX/WEILpIrO9UPGuXs= +github.com/GoogleCloudPlatform/cloudsql-proxy v0.0.0-20191009163259-e802c2cb94ae/go.mod h1:mjwGPas4yKduTyubHvD1Atl9r1rUq8DfVy+gkVvZ+oo= +github.com/GoogleCloudPlatform/docker-credential-gcr v2.0.5+incompatible/go.mod h1:BB1eHdMLYEFuFdBlRMb0N7YGVdM5s6Pt0njxgvfbGGs= +github.com/Knetic/govaluate v3.0.1-0.20171022003610-9aa49832a739+incompatible/go.mod h1:r7JcOSlj0wfOMncg0iLm8Leh48TZaKVeNIfJntJ2wa0= +github.com/Masterminds/goutils v1.1.0/go.mod h1:8cTjp+g8YejhMuvIA5y2vz3BpJxksy863GQaJW2MFNU= +github.com/Masterminds/goutils v1.1.1 h1:5nUrii3FMTL5diU80unEVvNevw1nH4+ZV4DSLVJLSYI= +github.com/Masterminds/goutils v1.1.1/go.mod h1:8cTjp+g8YejhMuvIA5y2vz3BpJxksy863GQaJW2MFNU= +github.com/Masterminds/semver v1.4.2/go.mod h1:MB6lktGJrhw8PrUyiEoblNEGEQ+RzHPF078ddwwvV3Y= +github.com/Masterminds/semver v1.5.0/go.mod h1:MB6lktGJrhw8PrUyiEoblNEGEQ+RzHPF078ddwwvV3Y= +github.com/Masterminds/semver/v3 v3.0.3/go.mod h1:VPu/7SZ7ePZ3QOrcuXROw5FAcLl4a0cBrbBpGY/8hQs= +github.com/Masterminds/semver/v3 v3.1.0/go.mod h1:VPu/7SZ7ePZ3QOrcuXROw5FAcLl4a0cBrbBpGY/8hQs= +github.com/Masterminds/semver/v3 v3.1.1 h1:hLg3sBzpNErnxhQtUy/mmLR2I9foDujNK030IGemrRc= +github.com/Masterminds/semver/v3 v3.1.1/go.mod h1:VPu/7SZ7ePZ3QOrcuXROw5FAcLl4a0cBrbBpGY/8hQs= +github.com/Masterminds/sprig v2.15.0+incompatible/go.mod h1:y6hNFY5UBTIWBxnzTeuNhlNS5hqE0NB0E6fgfo2Br3o= +github.com/Masterminds/sprig v2.22.0+incompatible/go.mod h1:y6hNFY5UBTIWBxnzTeuNhlNS5hqE0NB0E6fgfo2Br3o= +github.com/Masterminds/sprig/v3 v3.2.2 h1:17jRggJu518dr3QaafizSXOjKYp94wKfABxUmyxvxX8= +github.com/Masterminds/sprig/v3 v3.2.2/go.mod h1:UoaO7Yp8KlPnJIYWTFkMaqPUYKTfGFPhxNuwnnxkKlk= +github.com/Microsoft/go-winio v0.4.11/go.mod h1:VhR8bwka0BXejwEJY73c50VrPtXAaKcyvVC4A4RozmA= +github.com/Microsoft/go-winio v0.4.14/go.mod h1:qXqCSQ3Xa7+6tgxaGTIe4Kpcdsi+P8jBhyzoq1bpyYA= +github.com/Microsoft/go-winio v0.4.15-0.20190919025122-fc70bd9a86b5/go.mod h1:tTuCMEN+UleMWgg9dVx4Hu52b1bJo+59jBh3ajtinzw= +github.com/Microsoft/go-winio v0.4.16-0.20201130162521-d1ffc52c7331/go.mod h1:XB6nPKklQyQ7GC9LdcBEcBl8PF76WugXOPRXwdLnMv0= +github.com/Microsoft/go-winio v0.4.16/go.mod h1:XB6nPKklQyQ7GC9LdcBEcBl8PF76WugXOPRXwdLnMv0= +github.com/Microsoft/go-winio v0.4.17-0.20210211115548-6eac466e5fa3/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= +github.com/Microsoft/go-winio v0.4.17-0.20210324224401-5516f17a5958/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= +github.com/Microsoft/go-winio v0.4.17/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= +github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= +github.com/Microsoft/go-winio v0.5.2 h1:a9IhgEQBCUEk6QCdml9CiJGhAws+YwffDHEMp1VMrpA= +github.com/Microsoft/go-winio v0.5.2/go.mod h1:WpS1mjBmmwHBEWmogvA2mj8546UReBk4v8QkMxJ6pZY= +github.com/Microsoft/hcsshim v0.8.6/go.mod h1:Op3hHsoHPAvb6lceZHDtd9OkTew38wNoXnJs8iY7rUg= +github.com/Microsoft/hcsshim v0.8.7-0.20190325164909-8abdbb8205e4/go.mod h1:Op3hHsoHPAvb6lceZHDtd9OkTew38wNoXnJs8iY7rUg= +github.com/Microsoft/hcsshim v0.8.7/go.mod h1:OHd7sQqRFrYd3RmSgbgji+ctCwkbq2wbEYNSzOYtcBQ= +github.com/Microsoft/hcsshim v0.8.9/go.mod h1:5692vkUqntj1idxauYlpoINNKeqCiG6Sg38RRsjT5y8= +github.com/Microsoft/hcsshim v0.8.14/go.mod h1:NtVKoYxQuTLx6gEq0L96c9Ju4JbRJ4nY2ow3VK6a9Lg= +github.com/Microsoft/hcsshim v0.8.15/go.mod h1:x38A4YbHbdxJtc0sF6oIz+RG0npwSCAvn69iY6URG00= +github.com/Microsoft/hcsshim v0.8.16/go.mod h1:o5/SZqmR7x9JNKsW3pu+nqHm0MF8vbA+VxGOoXdC600= +github.com/Microsoft/hcsshim v0.8.21/go.mod h1:+w2gRZ5ReXQhFOrvSQeNfhrYB/dg3oDwTOcER2fw4I4= +github.com/Microsoft/hcsshim v0.8.24/go.mod h1:4zegtUJth7lAvFyc6cH2gGQ5B3OFQim01nnU2M8jKDg= +github.com/Microsoft/hcsshim/test v0.0.0-20201218223536-d3e5debf77da/go.mod h1:5hlzMzRKMLyo42nCZ9oml8AdTlq/0cvIaBv6tK1RehU= +github.com/Microsoft/hcsshim/test v0.0.0-20210227013316-43a75bb4edd3/go.mod h1:mw7qgWloBUl75W/gVH3cQszUg1+gUITj7D6NY7ywVnY= +github.com/NYTimes/gziphandler v0.0.0-20170623195520-56545f4a5d46/go.mod h1:3wb06e3pkSAbeQ52E9H9iFoQsEEwGN64994WTCIhntQ= +github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU= +github.com/OpenPeeDeeP/depguard v1.0.1/go.mod h1:xsIw86fROiiwelg+jB2uM9PiKihMMmUx/1V+TNhjQvM= +github.com/ProtonMail/go-crypto v0.0.0-20220824120805-4b6e5c587895/go.mod h1:UBYPn8k0D56RtnR8RFQMjmh4KrZzWJ5o7Z9SYjossQ8= +github.com/PuerkitoBio/purell v1.1.1/go.mod h1:c11w/QuzBsJSee3cPx9rAFu61PvFxuPbtSwDGJws/X0= +github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578/go.mod h1:uGdkoq3SwY9Y+13GIhn11/XLaGBb4BfwItxLd5jeuXE= +github.com/Shopify/logrus-bugsnag v0.0.0-20171204204709-577dee27f20d/go.mod h1:HI8ITrYtUY+O+ZhtlqUnD8+KwNPOyugEhfP9fdUIaEQ= +github.com/Shopify/sarama v1.19.0/go.mod h1:FVkBWblsNy7DGZRfXLU0O9RCGt5g3g3yEuWXgklEdEo= +github.com/Shopify/toxiproxy v2.1.4+incompatible/go.mod h1:OXgGpZ6Cli1/URJOF1DMxUHB2q5Ap20/P/eIdh4G0pI= +github.com/StackExchange/wmi v1.2.1/go.mod h1:rcmrprowKIVzvc+NUiLncP2uuArMWLCbu9SBzvHz7e8= +github.com/ThalesIgnite/crypto11 v1.2.5 h1:1IiIIEqYmBvUYFeMnHqRft4bwf/O36jryEUpY+9ef8E= +github.com/ThalesIgnite/crypto11 v1.2.5/go.mod h1:ILDKtnCKiQ7zRoNxcp36Y1ZR8LBPmR2E23+wTQe/MlE= +github.com/VividCortex/gohistogram v1.0.0/go.mod h1:Pf5mBqqDxYaXu3hDrrU+w6nw50o/4+TcAqDqk/vUH7g= +github.com/acarl005/stripansi v0.0.0-20180116102854-5a71ef0e047d h1:licZJFw2RwpHMqeKTCYkitsPqHNxTmd4SNR5r94FGM8= +github.com/acarl005/stripansi v0.0.0-20180116102854-5a71ef0e047d/go.mod h1:asat636LX7Bqt5lYEZ27JNDcqxfjdBQuJ/MM4CN/Lzo= +github.com/acobaugh/osrelease v0.1.0 h1:Yb59HQDGGNhCj4suHaFQQfBps5wyoKLSSX/J/+UifRE= +github.com/acobaugh/osrelease v0.1.0/go.mod h1:4bFEs0MtgHNHBrmHCt67gNisnabCRAlzdVasCEGHTWY= +github.com/adrg/xdg v0.3.3 h1:s/tV7MdqQnzB1nKY8aqHvAMD+uCiuEDzVB5HLRY849U= +github.com/adrg/xdg v0.3.3/go.mod h1:61xAR2VZcggl2St4O9ohF5qCKe08+JDmE4VNzPFQvOQ= +github.com/afex/hystrix-go v0.0.0-20180502004556-fa1af6a1f4f5/go.mod h1:SkGFH1ia65gfNATL8TAiHDNxPzPdmEL5uirI2Uyuz6c= +github.com/alcortesm/tgz v0.0.0-20161220082320-9c5fe88206d7/go.mod h1:6zEj6s6u/ghQa61ZWa/C2Aw3RkjiTBOix7dkqa1VLIs= +github.com/alecthomas/jsonschema v0.0.0-20210301060011-54c507b6f074 h1:Lw9q+WyJLFOR+AULchS5/2GKfM+6gOh4szzizdfH3MU= +github.com/alecthomas/jsonschema v0.0.0-20210301060011-54c507b6f074/go.mod h1:/n6+1/DWPltRLWL/VKyUxg6tzsl5kHUCcraimt4vr60= +github.com/alecthomas/kingpin v2.2.6+incompatible/go.mod h1:59OFYbFVLKQKq+mqrL6Rw5bR0c3ACQaawgXx0QYndlE= +github.com/alecthomas/template v0.0.0-20160405071501-a0175ee3bccc/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc= +github.com/alecthomas/template v0.0.0-20190718012654-fb15b899a751/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc= +github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0= +github.com/alecthomas/units v0.0.0-20190717042225-c3de453c63f4/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0= +github.com/alecthomas/units v0.0.0-20190924025748-f65c72e2690d/go.mod h1:rBZYJk541a8SKzHPHnH3zbiI+7dagKZ0cgpgrD7Fyho= +github.com/alexflint/go-filemutex v0.0.0-20171022225611-72bdc8eae2ae/go.mod h1:CgnQgUtFrFz9mxFNtED3jI5tLDjKlOM+oUF/sTk6ps0= +github.com/alexkohler/prealloc v1.0.0/go.mod h1:VetnK3dIgFBBKmg0YnD9F9x6Icjd+9cvfHR56wJVlKE= +github.com/anchore/client-go v0.0.0-20210222170800-9c70f9b80bcf h1:DYssiUV1pBmKqzKsm4mqXx8artqC0Q8HgZsVI3lMsAg= +github.com/anchore/client-go v0.0.0-20210222170800-9c70f9b80bcf/go.mod h1:FaODhIA06mxO1E6R32JE0TL1JWZZkmjRIAd4ULvHUKk= +github.com/anchore/go-macholibre v0.0.0-20220308212642-53e6d0aaf6fb h1:iDMnx6LIjtjZ46C0akqveX83WFzhpTD3eqOthawb5vU= +github.com/anchore/go-macholibre v0.0.0-20220308212642-53e6d0aaf6fb/go.mod h1:DmTY2Mfcv38hsHbG78xMiTDdxFtkHpgYNVDPsF2TgHk= +github.com/anchore/go-testutils v0.0.0-20200925183923-d5f45b0d3c04 h1:VzprUTpc0vW0nnNKJfJieyH/TZ9UYAnTZs5/gHTdAe8= +github.com/anchore/go-testutils v0.0.0-20200925183923-d5f45b0d3c04/go.mod h1:6dK64g27Qi1qGQZ67gFmBFvEHScy0/C8qhQhNe5B5pQ= +github.com/anchore/go-version v1.2.2-0.20200701162849-18adb9c92b9b h1:e1bmaoJfZVsCYMrIZBpFxwV26CbsuoEh5muXD5I1Ods= +github.com/anchore/go-version v1.2.2-0.20200701162849-18adb9c92b9b/go.mod h1:Bkc+JYWjMCF8OyZ340IMSIi2Ebf3uwByOk6ho4wne1E= +github.com/anchore/packageurl-go v0.1.1-0.20220428202044-a072fa3cb6d7 h1:kDrYkTSM9uIxaX/P9s0F4nKYNM+hnSgLJdLpqvsaQ/g= +github.com/anchore/packageurl-go v0.1.1-0.20220428202044-a072fa3cb6d7/go.mod h1:Blo6OgJNiYF41ufcgHKkbCKF2MDOMlrqhXv/ij6ocR4= +github.com/anchore/stereoscope v0.0.0-20220829182958-659c89aa659f h1:ekyERd7HC9ylQL6CutrFkP6u6aHfy1wz6LugRzDP6Qs= +github.com/anchore/stereoscope v0.0.0-20220829182958-659c89aa659f/go.mod h1:QjCxOPxjv7RqJm0pMIvB7P3rKHn7/uMBU7mnmM7ijTU= +github.com/andreyvit/diff v0.0.0-20170406064948-c7f18ee00883/go.mod h1:rCTlJbsFo29Kk6CurOXKm700vrz8f0KW0JNfpkRJY/8= +github.com/andybalholm/brotli v1.0.1/go.mod h1:loMXtMfwqflxFJPmdbJO0a3KNoPuLBgiu3qAvBg8x/Y= +github.com/andybalholm/brotli v1.0.2/go.mod h1:loMXtMfwqflxFJPmdbJO0a3KNoPuLBgiu3qAvBg8x/Y= +github.com/andybalholm/brotli v1.0.3/go.mod h1:fO7iG3H7G2nSZ7m0zPUDn85XEX2GTukHGRSepvi9Eig= +github.com/andybalholm/brotli v1.0.4 h1:V7DdXeJtZscaqfNuAdSRuRFzuiKlHSC/Zh3zl9qY3JY= +github.com/andybalholm/brotli v1.0.4/go.mod h1:fO7iG3H7G2nSZ7m0zPUDn85XEX2GTukHGRSepvi9Eig= +github.com/anmitsu/go-shlex v0.0.0-20161002113705-648efa622239/go.mod h1:2FmKhYUyUczH0OGQWaF5ceTx0UBShxjsH6f8oGKYe2c= +github.com/antihax/optional v0.0.0-20180407024304-ca021399b1a6/go.mod h1:V8iCPQYkqmusNa815XgQio277wI47sdRh1dUOLdyC6Q= +github.com/antihax/optional v1.0.0 h1:xK2lYat7ZLaVVcIuj82J8kIro4V6kDe0AUDFboUCwcg= +github.com/antihax/optional v1.0.0/go.mod h1:uupD/76wgC+ih3iEmQUL+0Ugr19nfwCT1kdvxnR2qWY= +github.com/aokoli/goutils v1.0.1/go.mod h1:SijmP0QR8LtwsmDs8Yii5Z/S4trXFGFC2oO5g9DP+DQ= +github.com/apache/beam v2.28.0+incompatible/go.mod h1:/8NX3Qi8vGstDLLaeaU7+lzVEu/ACaQhYjeefzQ0y1o= +github.com/apache/beam/sdks/v2 v2.0.0-20211012030016-ef4364519c94/go.mod h1:/kOom7hCyHVzAC/Z7HbZywkZZv6ywF+wb4CvgDVdcB8= +github.com/apache/thrift v0.12.0/go.mod h1:cp2SuWMxlEZw2r+iP2GNCdIi4C1qmUzdZFSVb+bacwQ= +github.com/apache/thrift v0.13.0/go.mod h1:cp2SuWMxlEZw2r+iP2GNCdIi4C1qmUzdZFSVb+bacwQ= +github.com/apex/log v1.1.4/go.mod h1:AlpoD9aScyQfJDVHmLMEcx4oU6LqzkWp4Mg9GdAcEvQ= +github.com/apex/logs v0.0.4/go.mod h1:XzxuLZ5myVHDy9SAmYpamKKRNApGj54PfYLcFrXqDwo= +github.com/aphistic/golf v0.0.0-20180712155816-02c07f170c5a/go.mod h1:3NqKYiepwy8kCu4PNA+aP7WUV72eXWJeP9/r3/K9aLE= +github.com/aphistic/sweet v0.2.0/go.mod h1:fWDlIh/isSE9n6EPsRmC0det+whmX6dJid3stzu0Xys= +github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o= +github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8= +github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY= +github.com/armon/go-metrics v0.4.0 h1:yCQqn7dwca4ITXb+CbubHmedzaQYHhNhrEXLYUeEe8Q= +github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8= +github.com/armon/go-radix v1.0.0 h1:F4z6KzEeeQIMeLFa97iZU6vupzoecKdU5TX24SNppXI= +github.com/armon/go-radix v1.0.0/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8= +github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5/go.mod h1:wHh0iHkYZB8zMSxRWpUBQtwG5a7fFgvEO+odwuTv2gs= +github.com/aryann/difflib v0.0.0-20170710044230-e206f873d14a/go.mod h1:DAHtR1m6lCRdSC2Tm3DSWRPvIPr6xNKyeHdqDQSQT+A= +github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a/go.mod h1:lB+ZfQJz7igIIfQNfa7Ml4HSf2uFQQRzpGGRXenZAgY= +github.com/asaskevich/govalidator v0.0.0-20200907205600-7a23bdc65eef/go.mod h1:WaHUgvxTVq04UNunO+XhnAqY/wQc+bxr74GqbsZ/Jqw= +github.com/asaskevich/govalidator v0.0.0-20210307081110-f21760c49a8d h1:Byv0BzEl3/e6D5CLfI0j/7hiIEtvGVFPCZ7Ei2oq8iQ= +github.com/asaskevich/govalidator v0.0.0-20210307081110-f21760c49a8d/go.mod h1:WaHUgvxTVq04UNunO+XhnAqY/wQc+bxr74GqbsZ/Jqw= +github.com/ashanbrown/forbidigo v1.2.0/go.mod h1:vVW7PEdqEFqapJe95xHkTfB1+XvZXBFg8t0sG2FIxmI= +github.com/ashanbrown/makezero v0.0.0-20210520155254-b6261585ddde/go.mod h1:oG9Dnez7/ESBqc4EdrdNlryeo7d0KcW1ftXHm7nU/UU= +github.com/aws/aws-lambda-go v1.13.3/go.mod h1:4UKl9IzQMoD+QF79YdCuzCwp8VbmG4VAQwij/eHl5CU= +github.com/aws/aws-sdk-go v1.15.11/go.mod h1:mFuSZ37Z9YOHbQEwBWztmVzqXrEkub65tZoCYDt7FT0= +github.com/aws/aws-sdk-go v1.15.27/go.mod h1:mFuSZ37Z9YOHbQEwBWztmVzqXrEkub65tZoCYDt7FT0= +github.com/aws/aws-sdk-go v1.19.18/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= +github.com/aws/aws-sdk-go v1.19.45/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= +github.com/aws/aws-sdk-go v1.20.6/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= +github.com/aws/aws-sdk-go v1.23.20/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= +github.com/aws/aws-sdk-go v1.25.11/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= +github.com/aws/aws-sdk-go v1.25.37/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= +github.com/aws/aws-sdk-go v1.27.0/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= +github.com/aws/aws-sdk-go v1.36.30/go.mod h1:hcU610XS61/+aQV88ixoOzUoG7v3b31pl2zKMmprdro= +github.com/aws/aws-sdk-go v1.37.0/go.mod h1:hcU610XS61/+aQV88ixoOzUoG7v3b31pl2zKMmprdro= +github.com/aws/aws-sdk-go-v2 v0.18.0/go.mod h1:JWVYvqSMppoMJC0x5wdwiImzgXTI9FuZwxzkQq9wy+g= +github.com/aws/aws-sdk-go-v2 v1.7.1/go.mod h1:L5LuPC1ZgDr2xQS7AmIec/Jlc7O/Y1u2KxJyNVab250= +github.com/aws/aws-sdk-go-v2 v1.14.0/go.mod h1:ZA3Y8V0LrlWj63MQAnRHgKf/5QB//LSZCPNWlWrNGLU= +github.com/aws/aws-sdk-go-v2 v1.16.11 h1:xM1ZPSvty3xVmdxiGr7ay/wlqv+MWhH0rMlyLdbC0YQ= +github.com/aws/aws-sdk-go-v2 v1.16.11/go.mod h1:WTACcleLz6VZTp7fak4EO5b9Q4foxbn+8PIz3PmyKlo= +github.com/aws/aws-sdk-go-v2/config v1.5.0/go.mod h1:RWlPOAW3E3tbtNAqTwvSW54Of/yP3oiZXMI0xfUdjyA= +github.com/aws/aws-sdk-go-v2/config v1.17.1 h1:BWxTjokU/69BZ4DnLrZco6OvBDii6ToEdfBL/y5I1nA= +github.com/aws/aws-sdk-go-v2/config v1.17.1/go.mod h1:uOxDHjBemNTF2Zos+fgG0NNfE86wn1OAHDTGxjMEYi0= +github.com/aws/aws-sdk-go-v2/credentials v1.3.1/go.mod h1:r0n73xwsIVagq8RsxmZbGSRQFj9As3je72C2WzUIToc= +github.com/aws/aws-sdk-go-v2/credentials v1.12.14 h1:AtVG/amkjbDBfnPr/tuW2IG18HGNznP6L12Dx0rLz+Q= +github.com/aws/aws-sdk-go-v2/credentials v1.12.14/go.mod h1:opAndTyq+YN7IpVG57z2CeNuXSQMqTYxGGlYH0m0RMY= +github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.3.0/go.mod h1:2LAuqPx1I6jNfaGDucWfA2zqQCYCOMCDHiCOciALyNw= +github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.12.12 h1:wgJBHO58Pc1V1QAnzdVM3JK3WbE/6eUF0JxCZ+/izz0= +github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.12.12/go.mod h1:aZ4vZnyUuxedC7eD4JyEHpGnCz+O2sHQEx3VvAwklSE= +github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.5/go.mod h1:2hXc8ooJqF2nAznsbJQIn+7h851/bu8GVC80OVTTqf8= +github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.18 h1:OmiwoVyLKEqqD5GvB683dbSqxiOfvx4U2lDZhG2Esc4= +github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.18/go.mod h1:348MLhzV1GSlZSMusdwQpXKbhD7X2gbI/TxwAPKkYZQ= +github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.3.0/go.mod h1:miRSv9l093jX/t/j+mBCaLqFHo9xKYzJ7DGm1BsGoJM= +github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.4.12 h1:5mvQDtNWtI6H56+E4LUnLWEmATMB7oEh+Z9RurtIuC0= +github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.4.12/go.mod h1:ckaCVTEdGAxO6KwTGzgskxR1xM+iJW4lxMyDFVda2Fc= +github.com/aws/aws-sdk-go-v2/internal/ini v1.1.1/go.mod h1:Zy8smImhTdOETZqfyn01iNOe0CNggVbPjCajyaz6Gvg= +github.com/aws/aws-sdk-go-v2/internal/ini v1.3.19 h1:g5qq9sgtEzt2szMaDqQO6fqKe026T6dHTFJp5NsPzkQ= +github.com/aws/aws-sdk-go-v2/internal/ini v1.3.19/go.mod h1:cVHo8KTuHjShb9V8/VjH3S/8+xPu16qx8fdGwmotJhE= +github.com/aws/aws-sdk-go-v2/service/ecr v1.4.1/go.mod h1:FglZcyeiBqcbvyinl+n14aT/EWC7S1MIH+Gan2iizt0= +github.com/aws/aws-sdk-go-v2/service/ecr v1.15.0 h1:lY2Z2sBP+zSbJ6CvvmnFgPcgknoQ0OJV88AwVetRRFk= +github.com/aws/aws-sdk-go-v2/service/ecr v1.15.0/go.mod h1:4zYI85WiYDhFaU1jPFVfkD7HlBcdnITDE3QxDwy4Kus= +github.com/aws/aws-sdk-go-v2/service/ecrpublic v1.4.1/go.mod h1:eD5Eo4drVP2FLTw0G+SMIPWNWvQRGGTtIZR2XeAagoA= +github.com/aws/aws-sdk-go-v2/service/ecrpublic v1.12.0 h1:LsqBpyRofMG6eDs6YGud6FhdGyIyXelAasPOZ6wWLro= +github.com/aws/aws-sdk-go-v2/service/ecrpublic v1.12.0/go.mod h1:IArQ3IBR00FkuraKwudKZZU32OxJfdTdwV+W5iZh3Y4= +github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.2.1/go.mod h1:zceowr5Z1Nh2WVP8bf/3ikB41IZW59E4yIYbg+pC6mw= +github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.9.12 h1:7iPTTX4SAI2U2VOogD7/gmHlsgnYSgoNHt7MSQXtG2M= +github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.9.12/go.mod h1:1TODGhheLWjpQWSuhYuAUWYTCKwEjx2iblIFKDHjeTc= +github.com/aws/aws-sdk-go-v2/service/kms v1.18.4 h1:tsokBawk9+eD3RfMbJJRla/y8FinZ79Ylj5tZ3Ayxcw= +github.com/aws/aws-sdk-go-v2/service/sso v1.3.1/go.mod h1:J3A3RGUvuCZjvSuZEcOpHDnzZP/sKbhDWV2T1EOzFIM= +github.com/aws/aws-sdk-go-v2/service/sso v1.11.17 h1:pXxu9u2z1UqSbjO9YA8kmFJBhFc1EVTDaf7A+S+Ivq8= +github.com/aws/aws-sdk-go-v2/service/sso v1.11.17/go.mod h1:mS5xqLZc/6kc06IpXn5vRxdLaED+jEuaSRv5BxtnsiY= +github.com/aws/aws-sdk-go-v2/service/sts v1.6.0/go.mod h1:q7o0j7d7HrJk/vr9uUt3BVRASvcU7gYZB9PUgPiByXg= +github.com/aws/aws-sdk-go-v2/service/sts v1.16.13 h1:dl8T0PJlN92rvEGOEUiD0+YPYdPEaCZK0TqHukvSfII= +github.com/aws/aws-sdk-go-v2/service/sts v1.16.13/go.mod h1:Ru3QVMLygVs/07UQ3YDur1AQZZp2tUNje8wfloFttC0= +github.com/aws/smithy-go v1.6.0/go.mod h1:SObp3lf9smib00L/v3U2eAKG8FyQ7iLrJnQiAmR5n+E= +github.com/aws/smithy-go v1.11.0/go.mod h1:3xHYmszWVx2c0kIwQeEVf9uSm4fYZt67FBJnwub1bgM= +github.com/aws/smithy-go v1.12.1 h1:yQRC55aXN/y1W10HgwHle01DRuV9Dpf31iGkotjt3Ag= +github.com/aws/smithy-go v1.12.1/go.mod h1:Tg+OJXh4MB2R/uN61Ko2f6hTZwB/ZYGOtib8J3gBHzA= +github.com/awslabs/amazon-ecr-credential-helper/ecr-login v0.0.0-20220517224237-e6f29200ae04 h1:p2I85zYI9z5/c/3Q0LiO3RtNXcmXHTtJfml/hV16zNg= +github.com/awslabs/amazon-ecr-credential-helper/ecr-login v0.0.0-20220517224237-e6f29200ae04/go.mod h1:Z+bXnIbhKJYSvxNwsNnwde7pDKxuqlEZCbUBoTwAqf0= +github.com/aybabtme/rgbterm v0.0.0-20170906152045-cc83f3b3ce59/go.mod h1:q/89r3U2H7sSsE2t6Kca0lfwTK8JdoNGS/yzM/4iH5I= +github.com/beevik/etree v1.1.0/go.mod h1:r8Aw8JqVegEf0w2fDnATrX9VpkMcyFeM0FhwO62wh+A= +github.com/benbjohnson/clock v1.0.3/go.mod h1:bGMdMPoPVvcYyt1gHDf4J2KE153Yf9BuiUKYMaxlTDM= +github.com/benbjohnson/clock v1.1.0 h1:Q92kusRqC1XV2MjkWETPvjJVqKetz1OzxZB7mHJLju8= +github.com/benbjohnson/clock v1.1.0/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA= +github.com/beorn7/perks v0.0.0-20160804104726-4c0e84591b9a/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q= +github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q= +github.com/beorn7/perks v1.0.0/go.mod h1:KWe93zE9D1o94FZ5RNwFwVgaQK1VOXiVxmqh+CedLV8= +github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM= +github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= +github.com/bgentry/speakeasy v0.1.0 h1:ByYyxL9InA1OWqxJqqp2A5pYHUrCiAL6K3J+LKSsQkY= +github.com/bgentry/speakeasy v0.1.0/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs= +github.com/bitly/go-simplejson v0.5.0/go.mod h1:cXHtHw4XUPsvGaxgjIAn8PhEWG9NfngEKAMDJEczWVA= +github.com/bits-and-blooms/bitset v1.2.0/go.mod h1:gIdJ4wp64HaoK2YrL1Q5/N7Y16edYb8uY+O0FJTyyDA= +github.com/bketelsen/crypt v0.0.3-0.20200106085610-5cbc8cc4026c/go.mod h1:MKsuJmJgSg28kpZDP6UIiPt0e0Oz0kqKNGyRaWEPv84= +github.com/bketelsen/crypt v0.0.4/go.mod h1:aI6NrJ0pMGgvZKL1iVgXLnfIFJtfV+bKCoqOes/6LfM= +github.com/bkielbasa/cyclop v1.2.0/go.mod h1:qOI0yy6A7dYC4Zgsa72Ppm9kONl0RoIlPbzot9mhmeI= +github.com/blakesmith/ar v0.0.0-20190502131153-809d4375e1fb/go.mod h1:PkYb9DJNAwrSvRx5DYA+gUcOIgTGVMNkfSCbZM8cWpI= +github.com/blang/semver v3.1.0+incompatible/go.mod h1:kRBLl5iJ+tD4TcOOxsy/0fnwebNt5EWlYSAyrTnjyyk= +github.com/blang/semver v3.5.1+incompatible h1:cQNTCjp13qL8KC3Nbxr/y2Bqb63oX6wdnnjpJbkM4JQ= +github.com/blang/semver v3.5.1+incompatible/go.mod h1:kRBLl5iJ+tD4TcOOxsy/0fnwebNt5EWlYSAyrTnjyyk= +github.com/blizzy78/varnamelen v0.3.0/go.mod h1:hbwRdBvoBqxk34XyQ6HA0UH3G0/1TKuv5AC4eaBT0Ec= +github.com/bmatcuk/doublestar/v4 v4.0.2 h1:X0krlUVAVmtr2cRoTqR8aDMrDqnB36ht8wpWTiQ3jsA= +github.com/bmatcuk/doublestar/v4 v4.0.2/go.mod h1:xBQ8jztBU6kakFMg+8WGxn0c6z1fTSPVIjEY1Wr7jzc= +github.com/bmizerany/assert v0.0.0-20160611221934-b7ed37b82869/go.mod h1:Ekp36dRnpXw/yCqJaO+ZrUyxD+3VXMFFr56k5XYrpB4= +github.com/bombsimon/wsl/v3 v3.3.0/go.mod h1:st10JtZYLE4D5sC7b8xV4zTKZwAQjCH/Hy2Pm1FNZIc= +github.com/bradfitz/gomemcache v0.0.0-20190913173617-a41fca850d0b/go.mod h1:H0wQNHz2YrLsuXOZozoeDmnHXkNCRmMW0gwFWDfEZDA= +github.com/bradleyjkemp/cupaloy/v2 v2.7.0 h1:AT0vOjO68RcLyenLCHOGZzSNiuto7ziqzq6Q1/3xzMQ= +github.com/bradleyjkemp/cupaloy/v2 v2.7.0/go.mod h1:bm7JXdkRd4BHJk9HpwqAI8BoAY1lps46Enkdqw6aRX0= +github.com/breml/bidichk v0.1.1/go.mod h1:zbfeitpevDUGI7V91Uzzuwrn4Vls8MoBMrwtt78jmso= +github.com/bshuster-repo/logrus-logstash-hook v0.4.1/go.mod h1:zsTqEiSzDgAa/8GZR7E1qaXrhYNDKBYy5/dWPTIflbk= +github.com/buger/jsonparser v0.0.0-20180808090653-f4dd9f5a6b44/go.mod h1:bbYlZJ7hK1yFx9hf58LP0zeX7UjIGs20ufpu3evjr+s= +github.com/bugsnag/bugsnag-go v0.0.0-20141110184014-b1d153021fcd/go.mod h1:2oa8nejYd4cQ/b0hMIopN0lCRxU0bueqREvZLWFrtK8= +github.com/bugsnag/osext v0.0.0-20130617224835-0dd3f918b21b/go.mod h1:obH5gd0BsqsP2LwDJ9aOkm/6J86V6lyAXCoQWGw3K50= +github.com/bugsnag/panicwrap v0.0.0-20151223152923-e2c28503fcd0/go.mod h1:D/8v3kj0zr8ZAKg1AQ6crr+5VwKN5eIywRkfhyM/+dE= +github.com/butuzov/ireturn v0.1.1/go.mod h1:Wh6Zl3IMtTpaIKbmwzqi6olnM9ptYQxxVacMsOEFPoc= +github.com/bwesterb/go-ristretto v1.2.0/go.mod h1:fUIoIZaG73pV5biE2Blr2xEzDoMj7NFEuV9ekS419A0= +github.com/caarlos0/ctrlc v1.0.0/go.mod h1:CdXpj4rmq0q/1Eb44M9zi2nKB0QraNKuRGYGrrHhcQw= +github.com/campoy/unique v0.0.0-20180121183637-88950e537e7e/go.mod h1:9IOqJGCPMSc6E5ydlp5NIonxObaeu/Iub/X03EKPVYo= +github.com/casbin/casbin/v2 v2.1.2/go.mod h1:YcPU1XXisHhLzuxH9coDNf2FbKpjGlbCg3n9yuLkIJQ= +github.com/cavaliercoder/go-cpio v0.0.0-20180626203310-925f9528c45e/go.mod h1:oDpT4efm8tSYHXV5tHSdRvBet/b/QzxZ+XyyPehvm3A= +github.com/cenkalti/backoff v2.2.1+incompatible h1:tNowT99t7UNflLxfYYSlKYsBpXdEet03Pg2g16Swow4= +github.com/cenkalti/backoff v2.2.1+incompatible/go.mod h1:90ReRw6GdpyfrHakVjL/QHaoyV4aDUVVkXQJJJ3NXXM= +github.com/cenkalti/backoff/v3 v3.2.2 h1:cfUAAO3yvKMYKPrvhDuHSwQnhZNk/RMHKdZqKTxfm6M= +github.com/cenkalti/backoff/v4 v4.1.1/go.mod h1:scbssz8iZGpm3xbr14ovlUdkxfGXNInqkPWOWmG2CLw= +github.com/cenkalti/backoff/v4 v4.1.3 h1:cFAlzYUlVYDysBEH2T5hyJZMh3+5+WCBvSnK6Q8UtC4= +github.com/cenkalti/backoff/v4 v4.1.3/go.mod h1:scbssz8iZGpm3xbr14ovlUdkxfGXNInqkPWOWmG2CLw= +github.com/census-instrumentation/opencensus-proto v0.2.0/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= +github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= +github.com/census-instrumentation/opencensus-proto v0.3.0 h1:t/LhUZLVitR1Ow2YOnduCsavhwFUklBMoGVYUCqmCqk= +github.com/census-instrumentation/opencensus-proto v0.3.0/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= +github.com/certifi/gocertifi v0.0.0-20191021191039-0944d244cd40/go.mod h1:sGbDF6GwGcLpkNXPUTkMRoywsNa/ol15pxFe6ERfguA= +github.com/certifi/gocertifi v0.0.0-20200922220541-2c3bb06c6054 h1:uH66TXeswKn5PW5zdZ39xEwfS9an067BirqA+P4QaLI= +github.com/certifi/gocertifi v0.0.0-20200922220541-2c3bb06c6054/go.mod h1:sGbDF6GwGcLpkNXPUTkMRoywsNa/ol15pxFe6ERfguA= +github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc= +github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= +github.com/cespare/xxhash/v2 v2.1.2 h1:YRXhKfTDauu4ajMg1TPgFO5jnlC2HCbmLXMcTG5cbYE= +github.com/cespare/xxhash/v2 v2.1.2/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= +github.com/charithe/durationcheck v0.0.9/go.mod h1:SSbRIBVfMjCi/kEB6K65XEA83D6prSM8ap1UCpNKtgg= +github.com/chavacava/garif v0.0.0-20210405164556-e8a0a408d6af/go.mod h1:Qjyv4H3//PWVzTeCezG2b9IRn6myJxJSr4TD/xo6ojU= +github.com/checkpoint-restore/go-criu/v4 v4.1.0/go.mod h1:xUQBLp4RLc5zJtWY++yjOoMoB5lihDt7fai+75m+rGw= +github.com/checkpoint-restore/go-criu/v5 v5.0.0/go.mod h1:cfwC0EG7HMUenopBsUf9d89JlCLQIfgVcNsNN0t6T2M= +github.com/chrismellard/docker-credential-acr-env v0.0.0-20220119192733-fe33c00cee21 h1:XlpL9EHrPOBJMLDDOf35/G4t5rGAFNNAZQ3cDcWavtc= +github.com/chrismellard/docker-credential-acr-env v0.0.0-20220119192733-fe33c00cee21/go.mod h1:Zlre/PVxuSI9y6/UV4NwGixQ48RHQDSPiUkofr6rbMU= +github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= +github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI= +github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU= +github.com/cilium/ebpf v0.0.0-20200110133405-4032b1d8aae3/go.mod h1:MA5e5Lr8slmEg9bt0VpxxWqJlO4iwu3FBdHUzV7wQVg= +github.com/cilium/ebpf v0.0.0-20200702112145-1c8d4c9ef775/go.mod h1:7cR51M8ViRLIdUjrmSXlK9pkrsDlLHbO8jiB8X8JnOc= +github.com/cilium/ebpf v0.2.0/go.mod h1:To2CFviqOWL/M0gIMsvSMlqe7em/l1ALkX1PyjrX2Qs= +github.com/cilium/ebpf v0.4.0/go.mod h1:4tRaxcgiL706VnOzHOdBlY8IEAIdxINsQBcU4xJJXRs= +github.com/cilium/ebpf v0.6.2/go.mod h1:4tRaxcgiL706VnOzHOdBlY8IEAIdxINsQBcU4xJJXRs= +github.com/clbanning/x2j v0.0.0-20191024224557-825249438eec/go.mod h1:jMjuTZXRI4dUb/I5gc9Hdhagfvm9+RyrPryS/auMzxE= +github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw= +github.com/cloudflare/circl v1.1.0/go.mod h1:prBCrKB9DV4poKZY1l9zBXg2QJY7mvgRvtMxxK7fi4I= +github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= +github.com/cncf/udpa/go v0.0.0-20200629203442-efcf912fb354/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk= +github.com/cncf/udpa/go v0.0.0-20201120205902-5459f2c99403/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk= +github.com/cncf/udpa/go v0.0.0-20210930031921-04548b0d99d4 h1:hzAQntlaYRkVSFEfj9OTWlVV1H155FMD8BTKktLv0QI= +github.com/cncf/udpa/go v0.0.0-20210930031921-04548b0d99d4/go.mod h1:6pvJx4me5XPnfI9Z40ddWsdw2W/uZgQLFXToKeRcDiI= +github.com/cncf/xds/go v0.0.0-20210312221358-fbca930ec8ed/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20210805033703-aa0b78936158/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20210922020428-25de7278fc84/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20211001041855-01bcc9b48dfe/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20211011173535-cb28da3451f1/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20211130200136-a8f946100490 h1:KwaoQzs/WeUxxJqiJsZ4euOly1Az/IgZXXSxlD/UBNk= +github.com/cncf/xds/go v0.0.0-20211130200136-a8f946100490/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= +github.com/cockroachdb/datadriven v0.0.0-20200714090401-bf6692d28da5 h1:xD/lrqdvwsc+O2bjSSi3YqY73Ke3LAiSCx49aCesA0E= +github.com/cockroachdb/datadriven v0.0.0-20200714090401-bf6692d28da5/go.mod h1:h6jFvWxBdQXxjopDMZyH2UVceIRfR84bdzbkoKrsWNo= +github.com/cockroachdb/errors v1.2.4 h1:Lap807SXTH5tri2TivECb/4abUkMZC9zRoLarvcKDqs= +github.com/cockroachdb/errors v1.2.4/go.mod h1:rQD95gz6FARkaKkQXUksEje/d9a6wBJoCr5oaCLELYA= +github.com/cockroachdb/logtags v0.0.0-20190617123548-eb05cc24525f h1:o/kfcElHqOiXqcou5a3rIlMc7oJbMQkeLk0VQJ7zgqY= +github.com/cockroachdb/logtags v0.0.0-20190617123548-eb05cc24525f/go.mod h1:i/u985jwjWRlyHXQbwatDASoW0RMlZ/3i9yJHE2xLkI= +github.com/codahale/hdrhistogram v0.0.0-20161010025455-3a0bb77429bd/go.mod h1:sE/e/2PUdi/liOCUjSTXgM1o87ZssimdTWN964YiIeI= +github.com/codahale/rfc6979 v0.0.0-20141003034818-6a90f24967eb h1:EDmT6Q9Zs+SbUoc7Ik9EfrFqcylYqgPZ9ANSbTAntnE= +github.com/common-nighthawk/go-figure v0.0.0-20210622060536-734e95fb86be h1:J5BL2kskAlV9ckgEsNQXscjIaLiOYiZ75d4e94E6dcQ= +github.com/common-nighthawk/go-figure v0.0.0-20210622060536-734e95fb86be/go.mod h1:mk5IQ+Y0ZeO87b858TlA645sVcEcbiX6YqP98kt+7+w= +github.com/containerd/aufs v0.0.0-20200908144142-dab0cbea06f4/go.mod h1:nukgQABAEopAHvB6j7cnP5zJ+/3aVcE7hCYqvIwAHyE= +github.com/containerd/aufs v0.0.0-20201003224125-76a6863f2989/go.mod h1:AkGGQs9NM2vtYHaUen+NljV0/baGCAPELGm2q9ZXpWU= +github.com/containerd/aufs v0.0.0-20210316121734-20793ff83c97/go.mod h1:kL5kd6KM5TzQjR79jljyi4olc1Vrx6XBlcyj3gNv2PU= +github.com/containerd/aufs v1.0.0/go.mod h1:kL5kd6KM5TzQjR79jljyi4olc1Vrx6XBlcyj3gNv2PU= +github.com/containerd/btrfs v0.0.0-20201111183144-404b9149801e/go.mod h1:jg2QkJcsabfHugurUvvPhS3E08Oxiuh5W/g1ybB4e0E= +github.com/containerd/btrfs v0.0.0-20210316141732-918d888fb676/go.mod h1:zMcX3qkXTAi9GI50+0HOeuV8LU2ryCE/V2vG/ZBiTss= +github.com/containerd/btrfs v1.0.0/go.mod h1:zMcX3qkXTAi9GI50+0HOeuV8LU2ryCE/V2vG/ZBiTss= +github.com/containerd/cgroups v0.0.0-20190717030353-c4b9ac5c7601/go.mod h1:X9rLEHIqSf/wfK8NsPqxJmeZgW4pcfzdXITDrUSJ6uI= +github.com/containerd/cgroups v0.0.0-20190919134610-bf292b21730f/go.mod h1:OApqhQ4XNSNC13gXIwDjhOQxjWa/NxkwZXJ1EvqT0ko= +github.com/containerd/cgroups v0.0.0-20200531161412-0dbf7f05ba59/go.mod h1:pA0z1pT8KYB3TCXK/ocprsh7MAkoW8bZVzPdih9snmM= +github.com/containerd/cgroups v0.0.0-20200710171044-318312a37340/go.mod h1:s5q4SojHctfxANBDvMeIaIovkq29IP48TKAxnhYRxvo= +github.com/containerd/cgroups v0.0.0-20200824123100-0b889c03f102/go.mod h1:s5q4SojHctfxANBDvMeIaIovkq29IP48TKAxnhYRxvo= +github.com/containerd/cgroups v0.0.0-20210114181951-8a68de567b68/go.mod h1:ZJeTFisyysqgcCdecO57Dj79RfL0LNeGiFUqLYQRYLE= +github.com/containerd/cgroups v1.0.1/go.mod h1:0SJrPIenamHDcZhEcJMNBB85rHcUsw4f25ZfBiPYRkU= +github.com/containerd/cgroups v1.0.3/go.mod h1:/ofk34relqNjSGyqPrmEULrO4Sc8LJhvJmWbUCUKqj8= +github.com/containerd/console v0.0.0-20180822173158-c12b1e7919c1/go.mod h1:Tj/on1eG8kiEhd0+fhSDzsPAFESxzBBvdyEgyryXffw= +github.com/containerd/console v0.0.0-20181022165439-0650fd9eeb50/go.mod h1:Tj/on1eG8kiEhd0+fhSDzsPAFESxzBBvdyEgyryXffw= +github.com/containerd/console v0.0.0-20191206165004-02ecf6a7291e/go.mod h1:8Pf4gM6VEbTNRIT26AyyU7hxdQU3MvAvxVI0sc00XBE= +github.com/containerd/console v1.0.1/go.mod h1:XUsP6YE/mKtz6bxc+I8UiKKTP04qjQL4qcS3XoQ5xkw= +github.com/containerd/console v1.0.2/go.mod h1:ytZPjGgY2oeTkAONYafi2kSj0aYggsf8acV1PGKCbzQ= +github.com/containerd/containerd v1.2.10/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.3.0-beta.2.0.20190828155532-0293cbd26c69/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.3.0/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.3.1-0.20191213020239-082f7e3aed57/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.3.2/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.4.0-beta.2.0.20200729163537-40b22ef07410/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.4.1/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.4.3/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.4.9/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= +github.com/containerd/containerd v1.5.0-beta.1/go.mod h1:5HfvG1V2FsKesEGQ17k5/T7V960Tmcumvqn8Mc+pCYQ= +github.com/containerd/containerd v1.5.0-beta.3/go.mod h1:/wr9AVtEM7x9c+n0+stptlo/uBBoBORwEx6ardVcmKU= +github.com/containerd/containerd v1.5.0-beta.4/go.mod h1:GmdgZd2zA2GYIBZ0w09ZvgqEq8EfBp/m3lcVZIvPHhI= +github.com/containerd/containerd v1.5.0-rc.0/go.mod h1:V/IXoMqNGgBlabz3tHD2TWDoTJseu1FGOKuoA4nNb2s= +github.com/containerd/containerd v1.5.1/go.mod h1:0DOxVqwDy2iZvrZp2JUx/E+hS0UNTVn7dJnIOwtYR4g= +github.com/containerd/containerd v1.5.7/go.mod h1:gyvv6+ugqY25TiXxcZC3L5yOeYgEw0QMhscqVp1AR9c= +github.com/containerd/containerd v1.5.13 h1:XqvKw9i4P7/mFrC3TSM7yV5cwFZ9avXe6M3YANKnzEE= +github.com/containerd/containerd v1.5.13/go.mod h1:3AlCrzKROjIuP3JALsY14n8YtntaUDBu7vek+rPN5Vc= +github.com/containerd/continuity v0.0.0-20190426062206-aaeac12a7ffc/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= +github.com/containerd/continuity v0.0.0-20190815185530-f2a389ac0a02/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= +github.com/containerd/continuity v0.0.0-20191127005431-f65d91d395eb/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= +github.com/containerd/continuity v0.0.0-20200710164510-efbc4488d8fe/go.mod h1:cECdGN1O8G9bgKTlLhuPJimka6Xb/Gg7vYzCTNVxhvo= +github.com/containerd/continuity v0.0.0-20201208142359-180525291bb7/go.mod h1:kR3BEg7bDFaEddKm54WSmrol1fKWDU1nKYkgrcgZT7Y= +github.com/containerd/continuity v0.0.0-20210208174643-50096c924a4e/go.mod h1:EXlVlkqNba9rJe3j7w3Xa924itAMLgZH4UD/Q4PExuQ= +github.com/containerd/continuity v0.1.0/go.mod h1:ICJu0PwR54nI0yPEnJ6jcS+J7CZAUXrLh8lPo2knzsM= +github.com/containerd/fifo v0.0.0-20180307165137-3d5202aec260/go.mod h1:ODA38xgv3Kuk8dQz2ZQXpnv/UZZUHUCL7pnLehbXgQI= +github.com/containerd/fifo v0.0.0-20190226154929-a9fb20d87448/go.mod h1:ODA38xgv3Kuk8dQz2ZQXpnv/UZZUHUCL7pnLehbXgQI= +github.com/containerd/fifo v0.0.0-20200410184934-f15a3290365b/go.mod h1:jPQ2IAeZRCYxpS/Cm1495vGFww6ecHmMk1YJH2Q5ln0= +github.com/containerd/fifo v0.0.0-20201026212402-0724c46b320c/go.mod h1:jPQ2IAeZRCYxpS/Cm1495vGFww6ecHmMk1YJH2Q5ln0= +github.com/containerd/fifo v0.0.0-20210316144830-115abcc95a1d/go.mod h1:ocF/ME1SX5b1AOlWi9r677YJmCPSwwWnQ9O123vzpE4= +github.com/containerd/fifo v1.0.0/go.mod h1:ocF/ME1SX5b1AOlWi9r677YJmCPSwwWnQ9O123vzpE4= +github.com/containerd/go-cni v1.0.1/go.mod h1:+vUpYxKvAF72G9i1WoDOiPGRtQpqsNW/ZHtSlv++smU= +github.com/containerd/go-cni v1.0.2/go.mod h1:nrNABBHzu0ZwCug9Ije8hL2xBCYh/pjfMb1aZGrrohk= +github.com/containerd/go-runc v0.0.0-20180907222934-5a6d9f37cfa3/go.mod h1:IV7qH3hrUgRmyYrtgEeGWJfWbgcHL9CSRruz2Vqcph0= +github.com/containerd/go-runc v0.0.0-20190911050354-e029b79d8cda/go.mod h1:IV7qH3hrUgRmyYrtgEeGWJfWbgcHL9CSRruz2Vqcph0= +github.com/containerd/go-runc v0.0.0-20200220073739-7016d3ce2328/go.mod h1:PpyHrqVs8FTi9vpyHwPwiNEGaACDxT/N/pLcvMSRA9g= +github.com/containerd/go-runc v0.0.0-20201020171139-16b287bc67d0/go.mod h1:cNU0ZbCgCQVZK4lgG3P+9tn9/PaJNmoDXPpoJhDR+Ok= +github.com/containerd/go-runc v1.0.0/go.mod h1:cNU0ZbCgCQVZK4lgG3P+9tn9/PaJNmoDXPpoJhDR+Ok= +github.com/containerd/imgcrypt v1.0.1/go.mod h1:mdd8cEPW7TPgNG4FpuP3sGBiQ7Yi/zak9TYCG3juvb0= +github.com/containerd/imgcrypt v1.0.4-0.20210301171431-0ae5c75f59ba/go.mod h1:6TNsg0ctmizkrOgXRNQjAPFWpMYRWuiB6dSF4Pfa5SA= +github.com/containerd/imgcrypt v1.1.1-0.20210312161619-7ed62a527887/go.mod h1:5AZJNI6sLHJljKuI9IHnw1pWqo/F0nGDOuR9zgTs7ow= +github.com/containerd/imgcrypt v1.1.1/go.mod h1:xpLnwiQmEUJPvQoAapeb2SNCxz7Xr6PJrXQb0Dpc4ms= +github.com/containerd/nri v0.0.0-20201007170849-eb1350a75164/go.mod h1:+2wGSDGFYfE5+So4M5syatU0N0f0LbWpuqyMi4/BE8c= +github.com/containerd/nri v0.0.0-20210316161719-dbaa18c31c14/go.mod h1:lmxnXF6oMkbqs39FiCt1s0R2HSMhcLel9vNL3m4AaeY= +github.com/containerd/nri v0.1.0/go.mod h1:lmxnXF6oMkbqs39FiCt1s0R2HSMhcLel9vNL3m4AaeY= +github.com/containerd/stargz-snapshotter/estargz v0.10.0/go.mod h1:aE5PCyhFMwR8sbrErO5eM2GcvkyXTTJremG883D4qF0= +github.com/containerd/stargz-snapshotter/estargz v0.12.0 h1:idtwRTLjk2erqiYhPWy2L844By8NRFYEwYHcXhoIWPM= +github.com/containerd/stargz-snapshotter/estargz v0.12.0/go.mod h1:AIQ59TewBFJ4GOPEQXujcrJ/EKxh5xXZegW1rkR1P/M= +github.com/containerd/ttrpc v0.0.0-20190828154514-0e0f228740de/go.mod h1:PvCDdDGpgqzQIzDW1TphrGLssLDZp2GuS+X5DkEJB8o= +github.com/containerd/ttrpc v0.0.0-20190828172938-92c8520ef9f8/go.mod h1:PvCDdDGpgqzQIzDW1TphrGLssLDZp2GuS+X5DkEJB8o= +github.com/containerd/ttrpc v0.0.0-20191028202541-4f1b8fe65a5c/go.mod h1:LPm1u0xBw8r8NOKoOdNMeVHSawSsltak+Ihv+etqsE8= +github.com/containerd/ttrpc v1.0.1/go.mod h1:UAxOpgT9ziI0gJrmKvgcZivgxOp8iFPSk8httJEt98Y= +github.com/containerd/ttrpc v1.0.2/go.mod h1:UAxOpgT9ziI0gJrmKvgcZivgxOp8iFPSk8httJEt98Y= +github.com/containerd/ttrpc v1.1.0/go.mod h1:XX4ZTnoOId4HklF4edwc4DcqskFZuvXB1Evzy5KFQpQ= +github.com/containerd/typeurl v0.0.0-20180627222232-a93fcdb778cd/go.mod h1:Cm3kwCdlkCfMSHURc+r6fwoGH6/F1hH3S4sg0rLFWPc= +github.com/containerd/typeurl v0.0.0-20190911142611-5eb25027c9fd/go.mod h1:GeKYzf2pQcqv7tJ0AoCuuhtnqhva5LNU3U+OyKxxJpk= +github.com/containerd/typeurl v1.0.1/go.mod h1:TB1hUtrpaiO88KEK56ijojHS1+NeF0izUACaJW2mdXg= +github.com/containerd/typeurl v1.0.2/go.mod h1:9trJWW2sRlGub4wZJRTW83VtbOLS6hwcDZXTn6oPz9s= +github.com/containerd/zfs v0.0.0-20200918131355-0a33824f23a2/go.mod h1:8IgZOBdv8fAgXddBT4dBXJPtxyRsejFIpXoklgxgEjw= +github.com/containerd/zfs v0.0.0-20210301145711-11e8f1707f62/go.mod h1:A9zfAbMlQwE+/is6hi0Xw8ktpL+6glmqZYtevJgaB8Y= +github.com/containerd/zfs v0.0.0-20210315114300-dde8f0fda960/go.mod h1:m+m51S1DvAP6r3FcmYCp54bQ34pyOwTieQDNRIRHsFY= +github.com/containerd/zfs v0.0.0-20210324211415-d5c4544f0433/go.mod h1:m+m51S1DvAP6r3FcmYCp54bQ34pyOwTieQDNRIRHsFY= +github.com/containerd/zfs v1.0.0/go.mod h1:m+m51S1DvAP6r3FcmYCp54bQ34pyOwTieQDNRIRHsFY= +github.com/containernetworking/cni v0.7.1/go.mod h1:LGwApLUm2FpoOfxTDEeq8T9ipbpZ61X79hmU3w8FmsY= +github.com/containernetworking/cni v0.8.0/go.mod h1:LGwApLUm2FpoOfxTDEeq8T9ipbpZ61X79hmU3w8FmsY= +github.com/containernetworking/cni v0.8.1/go.mod h1:LGwApLUm2FpoOfxTDEeq8T9ipbpZ61X79hmU3w8FmsY= +github.com/containernetworking/plugins v0.8.6/go.mod h1:qnw5mN19D8fIwkqW7oHHYDHVlzhJpcY6TQxn/fUyDDM= +github.com/containernetworking/plugins v0.9.1/go.mod h1:xP/idU2ldlzN6m4p5LmGiwRDjeJr6FLK6vuiUwoH7P8= +github.com/containers/ocicrypt v1.0.1/go.mod h1:MeJDzk1RJHv89LjsH0Sp5KTY3ZYkjXO/C+bKAeWFIrc= +github.com/containers/ocicrypt v1.1.0/go.mod h1:b8AOe0YR67uU8OqfVNcznfFpAzu3rdgUV4GP9qXPfu4= +github.com/containers/ocicrypt v1.1.1/go.mod h1:Dm55fwWm1YZAjYRaJ94z2mfZikIyIN4B0oB3dj3jFxY= +github.com/coreos/bbolt v1.3.2/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk= +github.com/coreos/etcd v3.3.10+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= +github.com/coreos/etcd v3.3.13+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= +github.com/coreos/go-etcd v2.0.0+incompatible/go.mod h1:Jez6KQU2B/sWsbdaef3ED8NzMklzPG4d5KIOhIy30Tk= +github.com/coreos/go-iptables v0.4.5/go.mod h1:/mVI274lEDI2ns62jHCDnCyBF9Iwsmekav8Dbxlm1MU= +github.com/coreos/go-iptables v0.5.0/go.mod h1:/mVI274lEDI2ns62jHCDnCyBF9Iwsmekav8Dbxlm1MU= +github.com/coreos/go-oidc v2.1.0+incompatible/go.mod h1:CgnwVTmzoESiwO9qyAFEMiHoZ1nMCKZlZ9V6mm3/LKc= +github.com/coreos/go-oidc/v3 v3.2.0 h1:2eR2MGR7thBXSQ2YbODlF0fcmgtliLCfr9iX6RW11fc= +github.com/coreos/go-oidc/v3 v3.2.0/go.mod h1:rEJ/idjfUyfkBit1eI1fvyr+64/g9dcKpAm8MJMesvo= +github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= +github.com/coreos/go-semver v0.3.0 h1:wkHLiw0WNATZnSG7epLsujiMCgPAc9xhjJ4tgnAxmfM= +github.com/coreos/go-semver v0.3.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= +github.com/coreos/go-systemd v0.0.0-20161114122254-48702e0da86b/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= +github.com/coreos/go-systemd v0.0.0-20180511133405-39ca1b05acc7/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= +github.com/coreos/go-systemd v0.0.0-20190321100706-95778dfbb74e/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= +github.com/coreos/go-systemd v0.0.0-20190620071333-e64a0ec8b42a/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= +github.com/coreos/go-systemd/v22 v22.0.0/go.mod h1:xO0FLkIi5MaZafQlIrOotqXZ90ih+1atmu1JpKERPPk= +github.com/coreos/go-systemd/v22 v22.1.0/go.mod h1:xO0FLkIi5MaZafQlIrOotqXZ90ih+1atmu1JpKERPPk= +github.com/coreos/go-systemd/v22 v22.3.2 h1:D9/bQk5vlXQFZ6Kwuu6zaiXJ9oTPe68++AzAJc1DzSI= +github.com/coreos/go-systemd/v22 v22.3.2/go.mod h1:Y58oyj3AT4RCenI/lSvhwexgC+NSVTIJ3seZv2GcEnc= +github.com/coreos/pkg v0.0.0-20160727233714-3ac0863d7acf/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= +github.com/coreos/pkg v0.0.0-20180928190104-399ea9e2e55f/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= +github.com/cpuguy83/go-md2man v1.0.10/go.mod h1:SmD6nW6nTyfqj6ABTjUi3V3JVMnlJmwcJI5acqYI6dE= +github.com/cpuguy83/go-md2man/v2 v2.0.0-20190314233015-f79a8a8ca69d/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU= +github.com/cpuguy83/go-md2man/v2 v2.0.0/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU= +github.com/cpuguy83/go-md2man/v2 v2.0.1/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o= +github.com/cpuguy83/go-md2man/v2 v2.0.2 h1:p1EgwI/C7NhT0JmVkwCD2ZBK8j4aeHQX2pMHHBfMQ6w= +github.com/cpuguy83/go-md2man/v2 v2.0.2/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o= +github.com/creack/pty v1.1.7/go.mod h1:lj5s0c3V2DBrqTV7llrYr5NG6My20zk30Fl46Y7DoTY= +github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= +github.com/creack/pty v1.1.11/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= +github.com/cyberphone/json-canonicalization v0.0.0-20210823021906-dc406ceaf94b h1:lMzA7yYThpwx7iYNpTeiQnRH6h5JSfSYMJdz+pxZOW8= +github.com/cyberphone/json-canonicalization v0.0.0-20210823021906-dc406ceaf94b/go.mod h1:uzvlm1mxhHkdfqitSA92i7Se+S9ksOn3a3qmv/kyOCw= +github.com/cyphar/filepath-securejoin v0.2.2/go.mod h1:FpkQEhXnPnOthhzymB7CGsFk2G9VLXONKD9G7QGMM+4= +github.com/d2g/dhcp4 v0.0.0-20170904100407-a1d1b6c41b1c/go.mod h1:Ct2BUK8SB0YC1SMSibvLzxjeJLnrYEVLULFNiHY9YfQ= +github.com/d2g/dhcp4client v1.0.0/go.mod h1:j0hNfjhrt2SxUOw55nL0ATM/z4Yt3t2Kd1mW34z5W5s= +github.com/d2g/dhcp4server v0.0.0-20181031114812-7d4a0a7f59a5/go.mod h1:Eo87+Kg/IX2hfWJfwxMzLyuSZyxSoAug2nGa1G2QAi8= +github.com/d2g/hardwareaddr v0.0.0-20190221164911-e7d9fbe030e4/go.mod h1:bMl4RjIciD2oAxI7DmWRx6gbeqrkoLqv3MV0vzNad+I= +github.com/daixiang0/gci v0.2.9/go.mod h1:+4dZ7TISfSmqfAGv59ePaHfNzgGtIkHAhhdKggP1JAc= +github.com/danieljoos/wincred v1.0.2/go.mod h1:SnuYRW9lp1oJrZX/dXJqr0cPK5gYXqx3EJbmjhLdK9U= +github.com/danieljoos/wincred v1.1.0/go.mod h1:XYlo+eRTsVA9aHGp7NGjFkPla4m+DCL7hqDjlFjiygg= +github.com/davecgh/go-spew v0.0.0-20161028175848-04cdfd42973b/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= +github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/denis-tingajkin/go-header v0.4.2/go.mod h1:eLRHAVXzE5atsKAnNRDB90WHCFFnBUn4RN0nRcs1LJA= +github.com/denverdino/aliyungo v0.0.0-20190125010748-a747050bb1ba/go.mod h1:dV8lFg6daOBZbT6/BDGIz6Y3WFGn8juu6G+CQ6LHtl0= +github.com/depcheck-test/depcheck-test v0.0.0-20220607135614-199033aaa936 h1:foGzavPWwtoyBvjWyKJYDYsyzy+23iBV7NKTwdk+LRY= +github.com/devigned/tab v0.1.1/go.mod h1:XG9mPq0dFghrYvoBF3xdRrJzSTX1b7IQrvaL9mzjeJY= +github.com/dgrijalva/jwt-go v0.0.0-20170104182250-a601269ab70c/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ= +github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ= +github.com/dgryski/go-sip13 v0.0.0-20181026042036-e10d5fee7954/go.mod h1:vAd38F8PWV+bWy6jNmig1y/TA+kYO4g3RSRF0IAv0no= +github.com/dimchansky/utfbom v1.1.0/go.mod h1:rO41eb7gLfo8SF1jd9F8HplJm1Fewwi4mQvIirEdv+8= +github.com/dimchansky/utfbom v1.1.1 h1:vV6w1AhK4VMnhBno/TPVCoK9U/LP0PkLCS9tbxHdi/U= +github.com/dimchansky/utfbom v1.1.1/go.mod h1:SxdoEBH5qIqFocHMyGOXVAybYJdr71b1Q/j0mACtrfE= +github.com/dnaeon/go-vcr v1.0.1/go.mod h1:aBB1+wY4s93YsC3HHjMBMrwTj2R9FHDzUr9KyGc8n1E= +github.com/docker/cli v20.10.10+incompatible/go.mod h1:JLrzqnKDaYBop7H2jaqPtU4hHvMKP+vjCwu2uszcLI8= +github.com/docker/cli v20.10.12+incompatible/go.mod h1:JLrzqnKDaYBop7H2jaqPtU4hHvMKP+vjCwu2uszcLI8= +github.com/docker/cli v20.10.17+incompatible h1:eO2KS7ZFeov5UJeaDmIs1NFEDRf32PaqRpvoEkKBy5M= +github.com/docker/cli v20.10.17+incompatible/go.mod h1:JLrzqnKDaYBop7H2jaqPtU4hHvMKP+vjCwu2uszcLI8= +github.com/docker/distribution v0.0.0-20190905152932-14b96e55d84c/go.mod h1:0+TTO4EOBfRPhZXAeF1Vu+W3hHZ8eLp8PgKVZlcvtFY= +github.com/docker/distribution v2.7.1-0.20190205005809-0d3efadf0154+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w= +github.com/docker/distribution v2.7.1+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w= +github.com/docker/distribution v2.8.0+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w= +github.com/docker/distribution v2.8.1+incompatible h1:Q50tZOPR6T/hjNsyc9g8/syEs6bk8XXApsHjKukMl68= +github.com/docker/distribution v2.8.1+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w= +github.com/docker/docker v20.10.10+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk= +github.com/docker/docker v20.10.12+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk= +github.com/docker/docker v20.10.17+incompatible h1:JYCuMrWaVNophQTOrMMoSwudOVEfcegoZZrleKc1xwE= +github.com/docker/docker v20.10.17+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk= +github.com/docker/docker-credential-helpers v0.6.3/go.mod h1:WRaJzqw3CTB9bk10avuGsjVBZsD05qeibJ1/TYlvc0Y= +github.com/docker/docker-credential-helpers v0.6.4 h1:axCks+yV+2MR3/kZhAmy07yC56WZ2Pwu/fKWtKuZB0o= +github.com/docker/docker-credential-helpers v0.6.4/go.mod h1:ofX3UI0Gz1TteYBjtgs07O36Pyasyp66D2uKT7H8W1c= +github.com/docker/go-connections v0.4.0 h1:El9xVISelRB7BuFusrZozjnkIM5YnzCViNKohAFqRJQ= +github.com/docker/go-connections v0.4.0/go.mod h1:Gbd7IOopHjR8Iph03tsViu4nIes5XhDvyHbTtUxmeec= +github.com/docker/go-events v0.0.0-20170721190031-9461782956ad/go.mod h1:Uw6UezgYA44ePAFQYUehOuCzmy5zmg/+nl2ZfMWGkpA= +github.com/docker/go-events v0.0.0-20190806004212-e31b211e4f1c/go.mod h1:Uw6UezgYA44ePAFQYUehOuCzmy5zmg/+nl2ZfMWGkpA= +github.com/docker/go-metrics v0.0.0-20180209012529-399ea8c73916/go.mod h1:/u0gXw0Gay3ceNrsHubL3BtdOL2fHf93USgMTe0W5dI= +github.com/docker/go-metrics v0.0.1/go.mod h1:cG1hvH2utMXtqgqqYE9plW6lDxS3/5ayHzueweSI3Vw= +github.com/docker/go-units v0.4.0 h1:3uh0PgVws3nIA0Q+MwDC8yjEPf9zjRfZZWXZYDct3Tw= +github.com/docker/go-units v0.4.0/go.mod h1:fgPhTUdO+D/Jk86RDLlptpiXQzgHJF7gydDDbaIK4Dk= +github.com/docker/libtrust v0.0.0-20150114040149-fa567046d9b1/go.mod h1:cyGadeNEkKy96OOhEzfZl+yxihPEzKnqJwvfuSUqbZE= +github.com/docker/spdystream v0.0.0-20160310174837-449fdfce4d96/go.mod h1:Qh8CwZgvJUkLughtfhJv5dyTYa91l1fOUCrgjqmcifM= +github.com/docopt/docopt-go v0.0.0-20180111231733-ee0de3bc6815/go.mod h1:WwZ+bS3ebgob9U8Nd0kOddGdZWjyMGR8Wziv+TBNwSE= +github.com/dsnet/compress v0.0.2-0.20210315054119-f66993602bf5 h1:iFaUwBSo5Svw6L7HYpRu/0lE3e0BaElwnNO1qkNQxBY= +github.com/dsnet/compress v0.0.2-0.20210315054119-f66993602bf5/go.mod h1:qssHWj60/X5sZFNxpG4HBPDHVqxNm4DfnCKgrbZOT+s= +github.com/dsnet/golib v0.0.0-20171103203638-1ea166775780/go.mod h1:Lj+Z9rebOhdfkVLjJ8T6VcRQv3SXugXy999NBtR9aFY= +github.com/dustin/go-humanize v0.0.0-20171111073723-bb3d318650d4/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= +github.com/dustin/go-humanize v1.0.0 h1:VSnTsYCnlFHaM2/igO1h6X3HA71jcobQuxemgkq4zYo= +github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= +github.com/eapache/go-resiliency v1.1.0/go.mod h1:kFI+JgMyC7bLPUVY133qvEBtVayf5mFgVsvEsIPBvNs= +github.com/eapache/go-xerial-snappy v0.0.0-20180814174437-776d5712da21/go.mod h1:+020luEh2TKB4/GOp8oxxtq0Daoen/Cii55CzbTV6DU= +github.com/eapache/queue v1.1.0/go.mod h1:6eCeP0CKFpHLu8blIFXhExK/dRa7WDZfr6jVFPTqq+I= +github.com/edsrzf/mmap-go v1.0.0/go.mod h1:YO35OhQPt3KJa3ryjFM5Bs14WD66h8eGKpfaBNrHW5M= +github.com/elazarl/goproxy v0.0.0-20180725130230-947c36da3153/go.mod h1:/Zj4wYkgs4iZTTu3o/KG3Itv/qCCa8VVMlb3i9OVuzc= +github.com/emicklei/go-restful v0.0.0-20170410110728-ff4f55a20633/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= +github.com/emicklei/go-restful v2.9.5+incompatible/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= +github.com/emirpasic/gods v1.12.0/go.mod h1:YfzfFFoVP/catgzJb4IKIqXjX78Ha8FMSDh3ymbK86o= +github.com/envoyproxy/go-control-plane v0.6.9/go.mod h1:SBwIajubJHhxtWwsL9s8ss4safvEdbitLhGGK48rN6g= +github.com/envoyproxy/go-control-plane v0.9.0/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= +github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= +github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1mIlRU8Am5FuJP05cCM98= +github.com/envoyproxy/go-control-plane v0.9.7/go.mod h1:cwu0lG7PUMfa9snN8LXBig5ynNVH9qI8YYLbd1fK2po= +github.com/envoyproxy/go-control-plane v0.9.9-0.20201210154907-fd9021fe5dad/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk= +github.com/envoyproxy/go-control-plane v0.9.9-0.20210217033140-668b12f5399d/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk= +github.com/envoyproxy/go-control-plane v0.9.9-0.20210512163311-63b5d3c536b0/go.mod h1:hliV/p42l8fGbc6Y9bQ70uLwIvmJyVE5k4iMKlh8wCQ= +github.com/envoyproxy/go-control-plane v0.9.10-0.20210907150352-cf90f659a021/go.mod h1:AFq3mo9L8Lqqiid3OhADV3RfLJnjiw63cSpi+fDTRC0= +github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1 h1:xvqufLtNVwAhN8NMyWklVgxnWohi+wtMGQMhtxexlm0= +github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1/go.mod h1:KJwIaB5Mv44NWtYuAOFCVOjcI94vtpEz2JU/D2v6IjE= +github.com/envoyproxy/protoc-gen-validate v0.0.14/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= +github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= +github.com/envoyproxy/protoc-gen-validate v0.3.0-java/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= +github.com/envoyproxy/protoc-gen-validate v0.6.2 h1:JiO+kJTpmYGjEodY7O1Zk8oZcNz1+f30UtwtXoFUPzE= +github.com/envoyproxy/protoc-gen-validate v0.6.2/go.mod h1:2t7qjJNvHPx8IjnBOzl9E9/baC+qXE/TeeyBRzgJDws= +github.com/esimonov/ifshort v1.0.3/go.mod h1:yZqNJUrNn20K8Q9n2CrjTKYyVEmX209Hgu+M1LBpeZE= +github.com/etcd-io/gofail v0.0.0-20190801230047-ad7f989257ca/go.mod h1:49H/RkXP8pKaZy4h0d+NW16rSLhyVBt4o6VLJbmOqDE= +github.com/ettle/strcase v0.1.1/go.mod h1:hzDLsPC7/lwKyBOywSHEP89nt2pDgdy+No1NBA9o9VY= +github.com/evanphx/json-patch v4.9.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= +github.com/evanphx/json-patch v4.12.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= +github.com/facebookgo/clock v0.0.0-20150410010913-600d898af40a h1:yDWHCSQ40h88yih2JAcL6Ls/kVkSE8GFACTGVnMPruw= +github.com/facebookgo/limitgroup v0.0.0-20150612190941-6abd8d71ec01 h1:IeaD1VDVBPlx3viJT9Md8if8IxxJnO+x0JCGb054heg= +github.com/facebookgo/muster v0.0.0-20150708232844-fd3d7953fd52 h1:a4DFiKFJiDRGFD1qIcqGLX/WlUMD9dyLSLDt+9QZgt8= +github.com/facebookincubator/nvdtools v0.1.4 h1:x1Ucw9+bSkMd8DJJN4jNQ1Lk4PSFlJarGOxp9D6WUMo= +github.com/facebookincubator/nvdtools v0.1.4/go.mod h1:0/FIVnSEl9YHXLq3tKBPpKaI0iUceDhdSHPlIwIX44Y= +github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= +github.com/fatih/color v1.9.0/go.mod h1:eQcE1qtQxscV5RaZvpXrrb8Drkc3/DdQ+uUYCNjL+zU= +github.com/fatih/color v1.10.0/go.mod h1:ELkj/draVOlAH/xkhN6mQ50Qd0MPOk5AAr3maGEBuJM= +github.com/fatih/color v1.13.0 h1:8LOYc1KYPPmyKMuN8QV2DNRWNbLo6LZ0iLs8+mlH53w= +github.com/fatih/color v1.13.0/go.mod h1:kLAiJbzzSOZDVNGyDpeOxJ47H46qBXwg5ILebYFFOfk= +github.com/fatih/set v0.2.1 h1:nn2CaJyknWE/6txyUDGwysr3G5QC6xWB/PtVjPBbeaA= +github.com/fatih/set v0.2.1/go.mod h1:+RKtMCH+favT2+3YecHGxcc0b4KyVWA1QWWJUs4E0CI= +github.com/fatih/structtag v1.2.0/go.mod h1:mBJUNpUnHmRKrKlQQlmCrh5PuhftFbNv8Ys4/aAZl94= +github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc= +github.com/form3tech-oss/jwt-go v3.2.2+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= +github.com/form3tech-oss/jwt-go v3.2.3+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= +github.com/form3tech-oss/jwt-go v3.2.5+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= +github.com/fortytw2/leaktest v1.2.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g= +github.com/fortytw2/leaktest v1.3.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g= +github.com/franela/goblin v0.0.0-20200105215937-c9ffbefa60db/go.mod h1:7dvUGVsVBjqR7JHJk0brhHOZYGmfBYOrK0ZhYMEtBr4= +github.com/franela/goreq v0.0.0-20171204163338-bcd34c9993f8/go.mod h1:ZhphrRTfi2rbfLwlschooIH4+wKKDR4Pdxhh+TRoA20= +github.com/frankban/quicktest v1.11.3/go.mod h1:wRf/ReqHper53s+kmmSZizM8NamnL3IM0I9ntUbOk+k= +github.com/frankban/quicktest v1.14.3 h1:FJKSZTDHjyhriyC81FLQ0LY93eSai0ZyR/ZIkd3ZUKE= +github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= +github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= +github.com/fsnotify/fsnotify v1.5.1/go.mod h1:T3375wBYaZdLLcVNkcVbzGHY7f1l/uK5T5Ai1i3InKU= +github.com/fsnotify/fsnotify v1.5.4 h1:jRbGcIw6P2Meqdwuo0H1p6JVLbL5DHKAKlYndzMwVZI= +github.com/fsnotify/fsnotify v1.5.4/go.mod h1:OVB6XrOHzAwXMpEM7uPOzcehqUV2UqJxmVXmkdnm1bU= +github.com/fullsailor/pkcs7 v0.0.0-20190404230743-d7302db945fa/go.mod h1:KnogPXtdwXqoenmZCw6S+25EAm2MkxbG0deNDu4cbSA= +github.com/fullstorydev/grpcurl v1.6.0/go.mod h1:ZQ+ayqbKMJNhzLmbpCiurTVlaK2M/3nqZCxaQ2Ze/sM= +github.com/fullstorydev/grpcurl v1.8.0/go.mod h1:Mn2jWbdMrQGJQ8UD62uNyMumT2acsZUCkZIqFxsQf1o= +github.com/fullstorydev/grpcurl v1.8.1/go.mod h1:3BWhvHZwNO7iLXaQlojdg5NA6SxUDePli4ecpK1N7gw= +github.com/fullstorydev/grpcurl v1.8.6 h1:WylAwnPauJIofYSHqqMTC1eEfUIzqzevXyogBxnQquo= +github.com/fullstorydev/grpcurl v1.8.6/go.mod h1:WhP7fRQdhxz2TkL97u+TCb505sxfH78W1usyoB3tepw= +github.com/fzipp/gocyclo v0.3.1/go.mod h1:DJHO6AUmbdqj2ET4Z9iArSuwWgYDRryYt2wASxc7x3E= +github.com/gabriel-vasile/mimetype v1.4.0 h1:Cn9dkdYsMIu56tGho+fqzh7XmvY2YyGU0FnbhiOsEro= +github.com/gabriel-vasile/mimetype v1.4.0/go.mod h1:fA8fi6KUiG7MgQQ+mEWotXoEOvmxRtOJlERCzSmRvr8= +github.com/garyburd/redigo v0.0.0-20150301180006-535138d7bcd7/go.mod h1:NR3MbYisc3/PwhQ00EMzDiPmrwpPxAn5GI05/YaO1SY= +github.com/getkin/kin-openapi v0.76.0/go.mod h1:660oXbgy5JFMKreazJaQTw7o+X00qeSyhcnluiMv+Xg= +github.com/getsentry/raven-go v0.2.0 h1:no+xWJRb5ZI7eE8TWgIq1jLulQiIoLG0IfYxv5JYMGs= +github.com/getsentry/raven-go v0.2.0/go.mod h1:KungGk8q33+aIAZUIVWZDr2OfAEBsO49PX4NzFV5kcQ= +github.com/ghodss/yaml v0.0.0-20150909031657-73d445a93680/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= +github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= +github.com/gliderlabs/ssh v0.2.2/go.mod h1:U7qILu1NlMHj9FlMhZLlkCdDnU1DBEAqr0aevW3Awn0= +github.com/go-chi/chi v4.1.2+incompatible h1:fGFk2Gmi/YKXk0OmGfBh0WgmN3XB8lVnEyNz34tQRec= +github.com/go-chi/chi v4.1.2+incompatible/go.mod h1:eB3wogJHnLi3x/kFX2A+IbTBlXxmMeXJVKy9tTv1XzQ= +github.com/go-critic/go-critic v0.6.1/go.mod h1:SdNCfU0yF3UBjtaZGw6586/WocupMOJuiqgom5DsQxM= +github.com/go-gl/glfw v0.0.0-20190409004039-e6da0acd62b1/go.mod h1:vR7hzQXu2zJy9AVAgeJqvqgH9Q5CA+iKCZ2gyEVpxRU= +github.com/go-gl/glfw/v3.3/glfw v0.0.0-20191125211704-12ad95a8df72/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8= +github.com/go-gl/glfw/v3.3/glfw v0.0.0-20200222043503-6f7a984d4dc4/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8= +github.com/go-ini/ini v1.25.4/go.mod h1:ByCAeIL28uOIIG0E3PJtZPDL8WnHpFKFOtgjp+3Ies8= +github.com/go-kit/kit v0.8.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= +github.com/go-kit/kit v0.9.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= +github.com/go-kit/kit v0.10.0/go.mod h1:xUsJbQ/Fp4kEt7AFgCuvyX4a71u8h9jB8tj/ORgOZ7o= +github.com/go-kit/log v0.1.0/go.mod h1:zbhenjAZHb184qTLMA9ZjW7ThYL0H2mk7Q6pNt4vbaY= +github.com/go-kit/log v0.2.0/go.mod h1:NwTd00d/i8cPZ3xOwwiv2PO5MOcx78fFErGNcVmBjv0= +github.com/go-logfmt/logfmt v0.3.0/go.mod h1:Qt1PoO58o5twSAckw1HlFXLmHsOX5/0LbT9GBnD5lWE= +github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk= +github.com/go-logfmt/logfmt v0.5.0/go.mod h1:wCYkCAKZfumFQihp8CzCvQ3paCTfi41vtzG1KdI/P7A= +github.com/go-logfmt/logfmt v0.5.1/go.mod h1:WYhtIu8zTZfxdn5+rREduYbwxfcBr/Vr6KEVveWlfTs= +github.com/go-logr/logr v0.1.0/go.mod h1:ixOQHD9gLJUVQQ2ZOR7zLEifBX6tGkNJF4QyIY7sIas= +github.com/go-logr/logr v0.2.0/go.mod h1:z6/tIYblkpsD+a4lm/fGIIU9mZ+XfAiaFtq7xTgseGU= +github.com/go-logr/logr v1.2.0/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= +github.com/go-logr/logr v1.2.1/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= +github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= +github.com/go-logr/logr v1.2.3 h1:2DntVwHkVopvECVRSlL5PSo9eG+cAkDCuckLubN+rq0= +github.com/go-logr/logr v1.2.3/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= +github.com/go-logr/stdr v1.2.0/go.mod h1:YkVgnZu1ZjjL7xTxrfm/LLZBfkhTqSR1ydtm6jTKKwI= +github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= +github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE= +github.com/go-ole/go-ole v1.2.5/go.mod h1:pprOEPIfldk/42T2oK7lQ4v4JSDwmV0As9GaiUsvbm0= +github.com/go-ole/go-ole v1.2.6/go.mod h1:pprOEPIfldk/42T2oK7lQ4v4JSDwmV0As9GaiUsvbm0= +github.com/go-openapi/analysis v0.21.2/go.mod h1:HZwRk4RRisyG8vx2Oe6aqeSQcoxRp47Xkp3+K6q+LdY= +github.com/go-openapi/analysis v0.21.4 h1:ZDFLvSNxpDaomuCueM0BlSXxpANBlFYiBvr+GXrvIHc= +github.com/go-openapi/analysis v0.21.4/go.mod h1:4zQ35W4neeZTqh3ol0rv/O8JBbka9QyAgQRPp9y3pfo= +github.com/go-openapi/errors v0.19.8/go.mod h1:cM//ZKUKyO06HSwqAelJ5NsEMMcpa6VpXe8DOa1Mi1M= +github.com/go-openapi/errors v0.19.9/go.mod h1:cM//ZKUKyO06HSwqAelJ5NsEMMcpa6VpXe8DOa1Mi1M= +github.com/go-openapi/errors v0.20.2/go.mod h1:cM//ZKUKyO06HSwqAelJ5NsEMMcpa6VpXe8DOa1Mi1M= +github.com/go-openapi/errors v0.20.3 h1:rz6kiC84sqNQoqrtulzaL/VERgkoCyB6WdEkc2ujzUc= +github.com/go-openapi/errors v0.20.3/go.mod h1:Z3FlZ4I8jEGxjUK+bugx3on2mIAk4txuAOhlsB1FSgk= +github.com/go-openapi/jsonpointer v0.19.2/go.mod h1:3akKfEdA7DF1sugOqz1dVQHBcuDBPKZGEoHC/NkiQRg= +github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= +github.com/go-openapi/jsonpointer v0.19.5 h1:gZr+CIYByUqjcgeLXnQu2gHYQC9o73G2XUeOFYEICuY= +github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= +github.com/go-openapi/jsonreference v0.19.2/go.mod h1:jMjeRr2HHw6nAVajTXJ4eiUwohSTlpa0o73RUL1owJc= +github.com/go-openapi/jsonreference v0.19.3/go.mod h1:rjx6GuL8TTa9VaixXglHmQmIL98+wF9xc8zWvFonSJ8= +github.com/go-openapi/jsonreference v0.19.6/go.mod h1:diGHMEHg2IqXZGKxqyvWdfWU/aim5Dprw5bqpKkTvns= +github.com/go-openapi/jsonreference v0.20.0 h1:MYlu0sBgChmCfJxxUKZ8g1cPWFOB37YSZqewK7OKeyA= +github.com/go-openapi/jsonreference v0.20.0/go.mod h1:Ag74Ico3lPc+zR+qjn4XBUmXymS4zJbYVCZmcgkasdo= +github.com/go-openapi/loads v0.21.1/go.mod h1:/DtAMXXneXFjbQMGEtbamCZb+4x7eGwkvZCvBmwUG+g= +github.com/go-openapi/loads v0.21.2 h1:r2a/xFIYeZ4Qd2TnGpWDIQNcP80dIaZgf704za8enro= +github.com/go-openapi/loads v0.21.2/go.mod h1:Jq58Os6SSGz0rzh62ptiu8Z31I+OTHqmULx5e/gJbNw= +github.com/go-openapi/runtime v0.24.1 h1:Sml5cgQKGYQHF+M7yYSHaH1eOjvTykrddTE/KtQVjqo= +github.com/go-openapi/runtime v0.24.1/go.mod h1:AKurw9fNre+h3ELZfk6ILsfvPN+bvvlaU/M9q/r9hpk= +github.com/go-openapi/spec v0.19.3/go.mod h1:FpwSN1ksY1eteniUU7X0N/BgJ7a4WvBFVA8Lj9mJglo= +github.com/go-openapi/spec v0.20.4/go.mod h1:faYFR1CvsJZ0mNsmsphTMSoRrNV3TEDoAM7FOEWeq8I= +github.com/go-openapi/spec v0.20.6/go.mod h1:2OpW+JddWPrpXSCIX8eOx7lZ5iyuWj3RYR6VaaBKcWA= +github.com/go-openapi/spec v0.20.7 h1:1Rlu/ZrOCCob0n+JKKJAWhNWMPW8bOZRg8FJaY+0SKI= +github.com/go-openapi/spec v0.20.7/go.mod h1:2OpW+JddWPrpXSCIX8eOx7lZ5iyuWj3RYR6VaaBKcWA= +github.com/go-openapi/strfmt v0.21.0/go.mod h1:ZRQ409bWMj+SOgXofQAGTIo2Ebu72Gs+WaRADcS5iNg= +github.com/go-openapi/strfmt v0.21.1/go.mod h1:I/XVKeLc5+MM5oPNN7P6urMOpuLXEcNrCX/rPGuWb0k= +github.com/go-openapi/strfmt v0.21.2/go.mod h1:I/XVKeLc5+MM5oPNN7P6urMOpuLXEcNrCX/rPGuWb0k= +github.com/go-openapi/strfmt v0.21.3 h1:xwhj5X6CjXEZZHMWy1zKJxvW9AfHC9pkyUjLvHtKG7o= +github.com/go-openapi/strfmt v0.21.3/go.mod h1:k+RzNO0Da+k3FrrynSNN8F7n/peCmQQqbbXjtDfvmGg= +github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= +github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= +github.com/go-openapi/swag v0.19.15/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= +github.com/go-openapi/swag v0.21.1/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= +github.com/go-openapi/swag v0.22.3 h1:yMBqmnQ0gyZvEb/+KzuWZOXgllrXT4SADYbvDaXHv/g= +github.com/go-openapi/swag v0.22.3/go.mod h1:UzaqsxGiab7freDnrUUra0MwWfN/q7tE4j+VcZ0yl14= +github.com/go-openapi/validate v0.21.0/go.mod h1:rjnrwK57VJ7A8xqfpAOEKRH8yQSGUriMu5/zuPSQ1hg= +github.com/go-openapi/validate v0.22.0 h1:b0QecH6VslW/TxtpKgzpO1SNG7GU2FsaqKdP1E2T50Y= +github.com/go-openapi/validate v0.22.0/go.mod h1:rjnrwK57VJ7A8xqfpAOEKRH8yQSGUriMu5/zuPSQ1hg= +github.com/go-piv/piv-go v1.10.0 h1:P1Y1VjBI5DnXW0+YkKmTuh5opWnMIrKriUaIOblee9Q= +github.com/go-piv/piv-go v1.10.0/go.mod h1:NZ2zmjVkfFaL/CF8cVQ/pXdXtuj110zEKGdJM6fJZZM= +github.com/go-playground/assert/v2 v2.0.1 h1:MsBgLAaY856+nPRTKrp3/OZK38U/wa0CcBYNjji3q3A= +github.com/go-playground/assert/v2 v2.0.1/go.mod h1:VDjEfimB/XKnb+ZQfWdccd7VUvScMdVu0Titje2rxJ4= +github.com/go-playground/locales v0.14.0 h1:u50s323jtVGugKlcYeyzC0etD1HifMjqmJqb8WugfUU= +github.com/go-playground/locales v0.14.0/go.mod h1:sawfccIbzZTqEDETgFXqTho0QybSa7l++s0DH+LDiLs= +github.com/go-playground/universal-translator v0.18.0 h1:82dyy6p4OuJq4/CByFNOn/jYrnRPArHwAcmLoJZxyho= +github.com/go-playground/universal-translator v0.18.0/go.mod h1:UvRDBj+xPUEGrFYl+lu/H90nyDXpg0fqeB/AQUGNTVA= +github.com/go-playground/validator/v10 v10.11.0 h1:0W+xRM511GY47Yy3bZUbJVitCNg2BOGlCyvTqsp/xIw= +github.com/go-playground/validator/v10 v10.11.0/go.mod h1:i+3WkQ1FvaUjjxh1kSvIA4dMGDBiPU55YFDl0WbKdWU= +github.com/go-redis/redis v6.15.8+incompatible/go.mod h1:NAIEuMOZ/fxfXJIrKDQDz8wamY7mA7PouImQ2Jvg6kA= +github.com/go-redis/redis v6.15.9+incompatible/go.mod h1:NAIEuMOZ/fxfXJIrKDQDz8wamY7mA7PouImQ2Jvg6kA= +github.com/go-restruct/restruct v1.2.0-alpha h1:2Lp474S/9660+SJjpVxoKuWX09JsXHSrdV7Nv3/gkvc= +github.com/go-restruct/restruct v1.2.0-alpha/go.mod h1:KqrpKpn4M8OLznErihXTGLlsXFGeLxHUrLRRI/1YjGk= +github.com/go-rod/rod v0.109.1 h1:658X/G9xyQKjFUNo5apMsIyHpEb/KJnJ5LkAl6a62AI= +github.com/go-sql-driver/mysql v1.4.0/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w= +github.com/go-sql-driver/mysql v1.4.1/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w= +github.com/go-sql-driver/mysql v1.5.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg= +github.com/go-sql-driver/mysql v1.6.0 h1:BCTh4TKNUYmOmMUcQ3IipzF5prigylS7XXjEkfCHuOE= +github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg= +github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= +github.com/go-stack/stack v1.8.1/go.mod h1:dcoOX6HbPZSZptuspn9bctJ+N/CnF5gGygcUP3XYfe4= +github.com/go-task/slim-sprig v0.0.0-20210107165309-348f09dbbbc0/go.mod h1:fyg7847qk6SyHyPtNmDHnmrv/HOrqktSC+C9fM+CJOE= +github.com/go-test/deep v1.0.8 h1:TDsG77qcSprGbC6vTN8OuXp5g+J+b5Pcguhf7Zt61VM= +github.com/go-test/deep v1.0.8/go.mod h1:5C2ZWiW0ErCdrYzpqxLbTX7MG14M9iiw8DgHncVwcsE= +github.com/go-toolsmith/astcast v1.0.0/go.mod h1:mt2OdQTeAQcY4DQgPSArJjHCcOwlX+Wl/kwN+LbLGQ4= +github.com/go-toolsmith/astcopy v1.0.0/go.mod h1:vrgyG+5Bxrnz4MZWPF+pI4R8h3qKRjjyvV/DSez4WVQ= +github.com/go-toolsmith/astequal v1.0.0/go.mod h1:H+xSiq0+LtiDC11+h1G32h7Of5O3CYFJ99GVbS5lDKY= +github.com/go-toolsmith/astequal v1.0.1/go.mod h1:4oGA3EZXTVItV/ipGiOx7NWkY5veFfcsOJVS2YxltLw= +github.com/go-toolsmith/astfmt v1.0.0/go.mod h1:cnWmsOAuq4jJY6Ct5YWlVLmcmLMn1JUPuQIHCY7CJDw= +github.com/go-toolsmith/astinfo v0.0.0-20180906194353-9809ff7efb21/go.mod h1:dDStQCHtmZpYOmjRP/8gHHnCCch3Zz3oEgCdZVdtweU= +github.com/go-toolsmith/astp v1.0.0/go.mod h1:RSyrtpVlfTFGDYRbrjyWP1pYu//tSFcvdYrA8meBmLI= +github.com/go-toolsmith/pkgload v1.0.0/go.mod h1:5eFArkbO80v7Z0kdngIxsRXRMTaX4Ilcwuh3clNrQJc= +github.com/go-toolsmith/strparse v1.0.0/go.mod h1:YI2nUKP9YGZnL/L1/DLFBfixrcjslWct4wyljWhSRy8= +github.com/go-toolsmith/typep v1.0.0/go.mod h1:JSQCQMUPdRlMZFswiq3TGpNp1GMktqkR2Ns5AIQkATU= +github.com/go-toolsmith/typep v1.0.2/go.mod h1:JSQCQMUPdRlMZFswiq3TGpNp1GMktqkR2Ns5AIQkATU= +github.com/go-xmlfmt/xmlfmt v0.0.0-20191208150333-d5b6f63a941b/go.mod h1:aUCEOzzezBEjDBbFBoSiya/gduyIiWYRP6CnSFIV8AM= +github.com/gobuffalo/attrs v0.0.0-20190224210810-a9411de4debd/go.mod h1:4duuawTqi2wkkpB4ePgWMaai6/Kc6WEz83bhFwpHzj0= +github.com/gobuffalo/depgen v0.0.0-20190329151759-d478694a28d3/go.mod h1:3STtPUQYuzV0gBVOY3vy6CfMm/ljR4pABfrTeHNLHUY= +github.com/gobuffalo/depgen v0.1.0/go.mod h1:+ifsuy7fhi15RWncXQQKjWS9JPkdah5sZvtHc2RXGlg= +github.com/gobuffalo/envy v1.6.15/go.mod h1:n7DRkBerg/aorDM8kbduw5dN3oXGswK5liaSCx4T5NI= +github.com/gobuffalo/envy v1.7.0/go.mod h1:n7DRkBerg/aorDM8kbduw5dN3oXGswK5liaSCx4T5NI= +github.com/gobuffalo/flect v0.1.0/go.mod h1:d2ehjJqGOH/Kjqcoz+F7jHTBbmDb38yXA598Hb50EGs= +github.com/gobuffalo/flect v0.1.1/go.mod h1:8JCgGVbRjJhVgD6399mQr4fx5rRfGKVzFjbj6RE/9UI= +github.com/gobuffalo/flect v0.1.3/go.mod h1:8JCgGVbRjJhVgD6399mQr4fx5rRfGKVzFjbj6RE/9UI= +github.com/gobuffalo/genny v0.0.0-20190329151137-27723ad26ef9/go.mod h1:rWs4Z12d1Zbf19rlsn0nurr75KqhYp52EAGGxTbBhNk= +github.com/gobuffalo/genny v0.0.0-20190403191548-3ca520ef0d9e/go.mod h1:80lIj3kVJWwOrXWWMRzzdhW3DsrdjILVil/SFKBzF28= +github.com/gobuffalo/genny v0.1.0/go.mod h1:XidbUqzak3lHdS//TPu2OgiFB+51Ur5f7CSnXZ/JDvo= +github.com/gobuffalo/genny v0.1.1/go.mod h1:5TExbEyY48pfunL4QSXxlDOmdsD44RRq4mVZ0Ex28Xk= +github.com/gobuffalo/gitgen v0.0.0-20190315122116-cc086187d211/go.mod h1:vEHJk/E9DmhejeLeNt7UVvlSGv3ziL+djtTr3yyzcOw= +github.com/gobuffalo/gogen v0.0.0-20190315121717-8f38393713f5/go.mod h1:V9QVDIxsgKNZs6L2IYiGR8datgMhB577vzTDqypH360= +github.com/gobuffalo/gogen v0.1.0/go.mod h1:8NTelM5qd8RZ15VjQTFkAW6qOMx5wBbW4dSCS3BY8gg= +github.com/gobuffalo/gogen v0.1.1/go.mod h1:y8iBtmHmGc4qa3urIyo1shvOD8JftTtfcKi+71xfDNE= +github.com/gobuffalo/logger v0.0.0-20190315122211-86e12af44bc2/go.mod h1:QdxcLw541hSGtBnhUc4gaNIXRjiDppFGaDqzbrBd3v8= +github.com/gobuffalo/mapi v1.0.1/go.mod h1:4VAGh89y6rVOvm5A8fKFxYG+wIW6LO1FMTG9hnKStFc= +github.com/gobuffalo/mapi v1.0.2/go.mod h1:4VAGh89y6rVOvm5A8fKFxYG+wIW6LO1FMTG9hnKStFc= +github.com/gobuffalo/packd v0.0.0-20190315124812-a385830c7fc0/go.mod h1:M2Juc+hhDXf/PnmBANFCqx4DM3wRbgDvnVWeG2RIxq4= +github.com/gobuffalo/packd v0.1.0/go.mod h1:M2Juc+hhDXf/PnmBANFCqx4DM3wRbgDvnVWeG2RIxq4= +github.com/gobuffalo/packr/v2 v2.0.9/go.mod h1:emmyGweYTm6Kdper+iywB6YK5YzuKchGtJQZ0Odn4pQ= +github.com/gobuffalo/packr/v2 v2.2.0/go.mod h1:CaAwI0GPIAv+5wKLtv8Afwl+Cm78K/I/VCm/3ptBN+0= +github.com/gobuffalo/syncx v0.0.0-20190224160051-33c29581e754/go.mod h1:HhnNqWY95UYwwW3uSASeV7vtgYkT2t16hJgV3AEPUpw= +github.com/gobwas/glob v0.2.3/go.mod h1:d3Ez4x06l9bZtSvzIay5+Yzi0fmZzPgnTbPcKjJAkT8= +github.com/godbus/dbus v0.0.0-20151105175453-c7fdd8b5cd55/go.mod h1:/YcGZj5zSblfDWMMoOzV4fas9FZnQYTkDnsGvmh2Grw= +github.com/godbus/dbus v0.0.0-20180201030542-885f9cc04c9c/go.mod h1:/YcGZj5zSblfDWMMoOzV4fas9FZnQYTkDnsGvmh2Grw= +github.com/godbus/dbus v0.0.0-20190422162347-ade71ed3457e/go.mod h1:bBOAhwG1umN6/6ZUMtDFBMQR8jRg9O75tm9K00oMsK4= +github.com/godbus/dbus v4.1.0+incompatible/go.mod h1:/YcGZj5zSblfDWMMoOzV4fas9FZnQYTkDnsGvmh2Grw= +github.com/godbus/dbus/v5 v5.0.3/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA= +github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA= +github.com/gofrs/flock v0.8.1/go.mod h1:F1TvTiK9OcQqauNUHlbJvyl9Qa1QvF/gOUDKA14jxHU= +github.com/gogo/googleapis v1.1.0/go.mod h1:gf4bu3Q80BeJ6H1S1vYPm8/ELATdvryBaNFGgqEef3s= +github.com/gogo/googleapis v1.2.0/go.mod h1:Njal3psf3qN6dwBtQfUmBZh2ybovJ0tlu3o/AC7HYjU= +github.com/gogo/googleapis v1.4.0/go.mod h1:5YRNX2z1oM5gXdAkurHa942MDgEJyk02w4OecKY87+c= +github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ= +github.com/gogo/protobuf v1.2.0/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ= +github.com/gogo/protobuf v1.2.1/go.mod h1:hp+jE20tsWTFYpLwKvXlhS1hjn+gTNwPg2I6zVXpSg4= +github.com/gogo/protobuf v1.2.2-0.20190723190241-65acae22fc9d/go.mod h1:SlYgWuQ5SjCEi6WLHjHCa1yvBfUnHcTbrrZtXPKa29o= +github.com/gogo/protobuf v1.3.0/go.mod h1:SlYgWuQ5SjCEi6WLHjHCa1yvBfUnHcTbrrZtXPKa29o= +github.com/gogo/protobuf v1.3.1/go.mod h1:SlYgWuQ5SjCEi6WLHjHCa1yvBfUnHcTbrrZtXPKa29o= +github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q= +github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q= +github.com/golang-jwt/jwt v3.2.2+incompatible h1:IfV12K8xAKAnZqdXVzCZ+TOjboZ2keLg81eXfW3O+oY= +github.com/golang-jwt/jwt v3.2.2+incompatible/go.mod h1:8pz2t5EyA70fFQQSrl6XZXzqecmYZeUEB8OUGHkxJ+I= +github.com/golang-jwt/jwt/v4 v4.0.0/go.mod h1:/xlHOz8bRuivTWchD4jCa+NbatV+wEUSzwAxVc6locg= +github.com/golang-jwt/jwt/v4 v4.2.0/go.mod h1:/xlHOz8bRuivTWchD4jCa+NbatV+wEUSzwAxVc6locg= +github.com/golang-jwt/jwt/v4 v4.4.2 h1:rcc4lwaZgFMCZ5jxF9ABolDcIHdBytAFgqFPbSJQAYs= +github.com/golang-jwt/jwt/v4 v4.4.2/go.mod h1:m21LjoU+eqJr34lmDMbreY2eSTRJ1cv77w39/MY0Ch0= +github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q= +github.com/golang/glog v1.0.0 h1:nfP3RFugxnNRyKgeWd4oI1nYvXpxrx8ck8ZrcizshdQ= +github.com/golang/glog v1.0.0/go.mod h1:EWib/APOK0SL3dFbYqvxE3UYd8E6s1ouQ7iEp/0LWV4= +github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/groupcache v0.0.0-20190129154638-5b532d6fd5ef/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/groupcache v0.0.0-20190702054246-869f871628b6/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/groupcache v0.0.0-20191227052852-215e87163ea7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/groupcache v0.0.0-20200121045136-8c9f03a8e57e/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da h1:oI5xCqsCo564l8iNU+DwB5epxmsaqB+rhGL0m5jtYqE= +github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= +github.com/golang/mock v1.2.0/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= +github.com/golang/mock v1.3.1/go.mod h1:sBzyDLLjw3U8JLTeZvSv8jJB+tU5PVekmnlKIyFUx0Y= +github.com/golang/mock v1.4.0/go.mod h1:UOMv5ysSaYNkG+OFQykRIcU/QvvxJf3p21QfJ2Bt3cw= +github.com/golang/mock v1.4.1/go.mod h1:UOMv5ysSaYNkG+OFQykRIcU/QvvxJf3p21QfJ2Bt3cw= +github.com/golang/mock v1.4.3/go.mod h1:UOMv5ysSaYNkG+OFQykRIcU/QvvxJf3p21QfJ2Bt3cw= +github.com/golang/mock v1.4.4/go.mod h1:l3mdAwkq5BuhzHwde/uurv3sEJeZMXNpwsxVWU71h+4= +github.com/golang/mock v1.5.0/go.mod h1:CWnOUgYIOo4TcNZ0wHX3YZCqsaM1I1Jvs6v3mP3KVu8= +github.com/golang/mock v1.6.0 h1:ErTB+efbowRARo13NNdxyJji2egdxLGQhRaY+DUumQc= +github.com/golang/mock v1.6.0/go.mod h1:p6yTPP+5HYm5mzsMV8JkE6ZKdX+/wYM6Hr+LicevLPs= +github.com/golang/protobuf v1.1.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= +github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= +github.com/golang/protobuf v1.3.1/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= +github.com/golang/protobuf v1.3.2/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= +github.com/golang/protobuf v1.3.3/go.mod h1:vzj43D7+SQXF/4pzW/hwtAqwc6iTitCiVSaWz5lYuqw= +github.com/golang/protobuf v1.3.4/go.mod h1:vzj43D7+SQXF/4pzW/hwtAqwc6iTitCiVSaWz5lYuqw= +github.com/golang/protobuf v1.3.5/go.mod h1:6O5/vntMXwX2lRkT1hjjk0nAC1IDOTvTlVgjlRvqsdk= +github.com/golang/protobuf v1.4.0-rc.1/go.mod h1:ceaxUfeHdC40wWswd/P6IGgMaK3YpKi5j83Wpe3EHw8= +github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:xKAWHe0F5eneWXFV3EuXVDTCmh+JuBKY0li0aMyXATA= +github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs= +github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= +github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= +github.com/golang/protobuf v1.4.1/go.mod h1:U8fpvMrcmy5pZrNK1lt4xCsGvpyWQ/VVv6QDs8UjoX8= +github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= +github.com/golang/protobuf v1.4.3/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= +github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= +github.com/golang/protobuf v1.5.1/go.mod h1:DopwsBzvsk0Fs44TXzsVbJyPhcCPeIwnvohx4u74HPM= +github.com/golang/protobuf v1.5.2 h1:ROPKBNFfQgOUMifHyP+KYbvpjbdoFNs+aK7DXlji0Tw= +github.com/golang/protobuf v1.5.2/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY= +github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= +github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= +github.com/golang/snappy v0.0.2/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= +github.com/golang/snappy v0.0.3/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= +github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM= +github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= +github.com/golangci/check v0.0.0-20180506172741-cfe4005ccda2/go.mod h1:k9Qvh+8juN+UKMCS/3jFtGICgW8O96FVaZsaxdzDkR4= +github.com/golangci/dupl v0.0.0-20180902072040-3e9179ac440a/go.mod h1:ryS0uhF+x9jgbj/N71xsEqODy9BN81/GonCZiOzirOk= +github.com/golangci/go-misc v0.0.0-20180628070357-927a3d87b613/go.mod h1:SyvUF2NxV+sN8upjjeVYr5W7tyxaT1JVtvhKhOn2ii8= +github.com/golangci/gofmt v0.0.0-20190930125516-244bba706f1a/go.mod h1:9qCChq59u/eW8im404Q2WWTrnBUQKjpNYKMbU4M7EFU= +github.com/golangci/golangci-lint v1.43.0/go.mod h1:VIFlUqidx5ggxDfQagdvd9E67UjMXtTHBkBQ7sHoC5Q= +github.com/golangci/lint-1 v0.0.0-20191013205115-297bf364a8e0/go.mod h1:66R6K6P6VWk9I95jvqGxkqJxVWGFy9XlDwLwVz1RCFg= +github.com/golangci/maligned v0.0.0-20180506175553-b1d89398deca/go.mod h1:tvlJhZqDe4LMs4ZHD0oMUlt9G2LWuDGoisJTBzLMV9o= +github.com/golangci/misspell v0.3.5/go.mod h1:dEbvlSfYbMQDtrpRMQU675gSDLDNa8sCPPChZ7PhiVA= +github.com/golangci/revgrep v0.0.0-20210930125155-c22e5001d4f2/go.mod h1:LK+zW4MpyytAWQRz0M4xnzEk50lSvqDQKfx304apFkY= +github.com/golangci/unconvert v0.0.0-20180507085042-28b1c447d1f4/go.mod h1:Izgrg8RkN3rCIMLGE9CyYmU9pY2Jer6DgANEnZ/L/cQ= +github.com/google/btree v0.0.0-20180813153112-4030bb1f1f0c/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ= +github.com/google/btree v1.0.0/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ= +github.com/google/btree v1.0.1 h1:gK4Kx5IaGY9CD5sPJ36FHiBJ6ZXl0kilRiiCj+jdYp4= +github.com/google/btree v1.0.1/go.mod h1:xXMiIv4Fb/0kKde4SpL7qlzvu5cMJDRkFDxJfI9uaxA= +github.com/google/certificate-transparency-go v1.0.21/go.mod h1:QeJfpSbVSfYc7RgB3gJFj9cbuQMMchQxrWXz8Ruopmg= +github.com/google/certificate-transparency-go v1.1.1/go.mod h1:FDKqPvSXawb2ecErVRrD+nfy23RCzyl7eqVCEmlT1Zs= +github.com/google/certificate-transparency-go v1.1.2-0.20210422104406-9f33727a7a18/go.mod h1:6CKh9dscIRoqc2kC6YUFICHZMT9NrClyPrRVFrdw1QQ= +github.com/google/certificate-transparency-go v1.1.2-0.20210512142713-bed466244fa6/go.mod h1:aF2dp7Dh81mY8Y/zpzyXps4fQW5zQbDu2CxfpJB6NkI= +github.com/google/certificate-transparency-go v1.1.3 h1:WEb38wcTe0EuAvg7USzgklnOjjnlMaahYO3faaqnCn8= +github.com/google/certificate-transparency-go v1.1.3/go.mod h1:S9FT/VzOUzhOGG0iLrzDs+f5Ml/zm7IYY/w+IlHz01M= +github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M= +github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= +github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= +github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.4.1/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.1/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.2/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.3/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.7/go.mod h1:n+brtR0CgQNWTVd5ZUFpTBC8YFBDLK/h/bpaJ8/DtOE= +github.com/google/go-cmp v0.5.8 h1:e6P7q2lk1O+qJJb4BtCQXlK8vWEO8V1ZeuEdJNOqZyg= +github.com/google/go-cmp v0.5.8/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= +github.com/google/go-containerregistry v0.7.0/go.mod h1:2zaoelrL0d08gGbpdP3LqyUuBmhWbpD6IOe2s9nLS2k= +github.com/google/go-containerregistry v0.11.0 h1:Xt8x1adcREjFcmDoDK8OdOsjxu90PHkGuwNP8GiHMLM= +github.com/google/go-containerregistry v0.11.0/go.mod h1:BBaYtsHPHA42uEgAvd/NejvAfPSlz281sJWqupjSxfk= +github.com/google/go-github/v28 v28.1.1/go.mod h1:bsqJWQX05omyWVmc00nEUql9mhQyv38lDZ8kPZcQVoM= +github.com/google/go-github/v45 v45.2.0 h1:5oRLszbrkvxDDqBCNj2hjDZMKmvexaZ1xw/FCD+K3FI= +github.com/google/go-github/v45 v45.2.0/go.mod h1:FObaZJEDSTa/WGCzZ2Z3eoCDXWJKMenWWTrd8jrta28= +github.com/google/go-licenses v0.0.0-20210329231322-ce1d9163b77d/go.mod h1:+TYOmkVoJOpwnS0wfdsJCV9CoD5nJYsHoFk/0CrTK4M= +github.com/google/go-querystring v1.0.0/go.mod h1:odCYkC5MyYFN7vkCjXpyrEuKhc/BUO6wN/zVPAxq5ck= +github.com/google/go-querystring v1.1.0 h1:AnCroh3fv4ZBgVIf1Iwtovgjaw/GiKJo8M8yD/fhyJ8= +github.com/google/go-querystring v1.1.0/go.mod h1:Kcdr2DB4koayq7X8pmAG4sNG59So17icRSOU623lUBU= +github.com/google/go-replayers/grpcreplay v0.1.0/go.mod h1:8Ig2Idjpr6gifRd6pNVggX6TC1Zw6Jx74AKp7QNH2QE= +github.com/google/go-replayers/httpreplay v0.1.0/go.mod h1:YKZViNhiGgqdBlUbI2MwGpq4pXxNmhJLPHQ7cv2b5no= +github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= +github.com/google/gofuzz v1.1.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= +github.com/google/gofuzz v1.2.0 h1:xRy4A+RhZaiKjJ1bPfwQ8sedCA+YS2YcCHW6ec7JMi0= +github.com/google/gofuzz v1.2.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= +github.com/google/licenseclassifier v0.0.0-20210325184830-bb04aff29e72/go.mod h1:qsqn2hxC+vURpyBRygGUuinTO42MFRLcsmQ/P8v94+M= +github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs= +github.com/google/martian v2.1.1-0.20190517191504-25dcb96d9e51+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs= +github.com/google/martian/v3 v3.0.0/go.mod h1:y5Zk1BBys9G+gd6Jrk0W3cC1+ELVxBWuIGO+w/tUAp0= +github.com/google/martian/v3 v3.1.0/go.mod h1:y5Zk1BBys9G+gd6Jrk0W3cC1+ELVxBWuIGO+w/tUAp0= +github.com/google/martian/v3 v3.2.1/go.mod h1:oBOf6HBosgwRXnUGWUB05QECsc6uvmMiJ3+6W4l/CUk= +github.com/google/pprof v0.0.0-20181206194817-3ea8567a2e57/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc= +github.com/google/pprof v0.0.0-20190515194954-54271f7e092f/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc= +github.com/google/pprof v0.0.0-20191218002539-d4f498aebedc/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= +github.com/google/pprof v0.0.0-20200212024743-f11f1df84d12/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= +github.com/google/pprof v0.0.0-20200229191704-1ebb73c60ed3/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= +github.com/google/pprof v0.0.0-20200430221834-fc25d7d30c6d/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= +github.com/google/pprof v0.0.0-20200507031123-427632fa3b1c/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= +github.com/google/pprof v0.0.0-20200708004538-1a94d8640e99/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= +github.com/google/pprof v0.0.0-20201023163331-3e6fc7fc9c4c/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= +github.com/google/pprof v0.0.0-20201203190320-1bf35d6f28c2/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= +github.com/google/pprof v0.0.0-20201218002935-b9804c9f04c2/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= +github.com/google/pprof v0.0.0-20210122040257-d980be63207e/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= +github.com/google/pprof v0.0.0-20210226084205-cbba55b83ad5/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= +github.com/google/pprof v0.0.0-20210601050228-01bbb1931b22/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= +github.com/google/pprof v0.0.0-20210609004039-a478d1d731e9/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= +github.com/google/pprof v0.0.0-20210720184732-4bb14d4b1be1/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= +github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= +github.com/google/rpmpack v0.0.0-20191226140753-aa36bfddb3a0/go.mod h1:RaTPr0KUf2K7fnZYLNDrr8rxAamWs3iNywJLtQ2AzBg= +github.com/google/subcommands v1.0.1/go.mod h1:ZjhPrFU+Olkh9WazFPsl27BQ4UPiG37m3yTrtFlrHVk= +github.com/google/trillian v1.3.11/go.mod h1:0tPraVHrSDkA3BO6vKX67zgLXs6SsOAbHEivX+9mPgw= +github.com/google/trillian v1.3.14-0.20210409160123-c5ea3abd4a41/go.mod h1:1dPv0CUjNQVFEDuAUFhZql16pw/VlPgaX8qj+g5pVzQ= +github.com/google/trillian v1.3.14-0.20210511103300-67b5f349eefa/go.mod h1:s4jO3Ai4NSvxucdvqUHON0bCqJyoya32eNw6XJwsmNc= +github.com/google/trillian v1.4.1 h1:r/LV2L6uq6ijSSQNSyxnLXFU/JY7DaT6AILx1sOx2+8= +github.com/google/trillian v1.4.1/go.mod h1:43IVCsGXxP5mZK9yFkTQdQrMQm/wryNBV2GNEdqzVz8= +github.com/google/uuid v0.0.0-20161128191214-064e2069ce9c/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.2.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.3.0 h1:t6JiXgmwXMjEs8VusXIJk2BXHsn+wx8BZdTaoZ5fu7I= +github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/wire v0.3.0/go.mod h1:i1DMg/Lu8Sz5yYl25iOdmc5CT5qusaa+zmRWs16741s= +github.com/googleapis/enterprise-certificate-proxy v0.0.0-20220520183353-fd19c99a87aa/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= +github.com/googleapis/enterprise-certificate-proxy v0.1.0 h1:zO8WHNx/MYiAKJ3d5spxZXZE6KHmIQGQcAzwUzV7qQw= +github.com/googleapis/enterprise-certificate-proxy v0.1.0/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= +github.com/googleapis/gax-go v2.0.2+incompatible h1:silFMLAnr330+NRuag/VjIGF7TLp/LBrV2CJKFLWEww= +github.com/googleapis/gax-go v2.0.2+incompatible/go.mod h1:SFVmujtThgffbyetf+mdk2eWhX2bMyUtNHzFKcPA9HY= +github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= +github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk= +github.com/googleapis/gax-go/v2 v2.1.0/go.mod h1:Q3nei7sK6ybPYH7twZdmQpAd1MKb7pfu6SK+H1/DsU0= +github.com/googleapis/gax-go/v2 v2.1.1/go.mod h1:hddJymUZASv3XPyGkUpKj8pPO47Rmb0eJc8R6ouapiM= +github.com/googleapis/gax-go/v2 v2.2.0/go.mod h1:as02EH8zWkzwUoLbBaFeQ+arQaj/OthfcblKl4IGNaM= +github.com/googleapis/gax-go/v2 v2.3.0/go.mod h1:b8LNqSzNabLiUpXKkY7HAR5jr6bIT99EXz9pXxye9YM= +github.com/googleapis/gax-go/v2 v2.4.0 h1:dS9eYAjhrE2RjmzYw2XAPvcXfmcQLtFEQWn0CR82awk= +github.com/googleapis/gax-go/v2 v2.4.0/go.mod h1:XOTVJ59hdnfJLIP/dh8n5CGryZR2LxK9wbMD5+iXC6c= +github.com/googleapis/gnostic v0.4.1/go.mod h1:LRhVm6pbyptWbWbuZ38d1eyptfvIytN3ir6b65WBswg= +github.com/googleapis/gnostic v0.5.1/go.mod h1:6U4PtQXGIEt/Z3h5MAT7FNofLnw9vXk2cUuW7uA/OeU= +github.com/googleapis/gnostic v0.5.5 h1:9fHAtK0uDfpveeqqo1hkEZJcFvYXAiCN3UutL8F9xHw= +github.com/googleapis/gnostic v0.5.5/go.mod h1:7+EbHbldMins07ALC74bsA81Ovc97DwqyJO1AENw9kA= +github.com/googleapis/go-type-adapters v1.0.0/go.mod h1:zHW75FOG2aur7gAO2B+MLby+cLsWGBF62rFAi7WjWO4= +github.com/googleapis/google-cloud-go-testing v0.0.0-20200911160855-bcd43fbb19e8/go.mod h1:dvDLG8qkwmyD9a/MJJN3XJcT3xFxOKAvTZGvuZmac9g= +github.com/gookit/color v1.2.5/go.mod h1:AhIE+pS6D4Ql0SQWbBeXPHw7gY0/sjHoA4s/n1KB7xg= +github.com/gookit/color v1.4.2 h1:tXy44JFSFkKnELV6WaMo/lLfu/meqITX3iAV52do7lk= +github.com/gookit/color v1.4.2/go.mod h1:fqRyamkC1W8uxl+lxCQxOT09l/vYfZ+QeiX3rKQHCoQ= +github.com/gopherjs/gopherjs v0.0.0-20181017120253-0766667cb4d1/go.mod h1:wJfORRmW1u3UXTncJ5qlYoELFm8eSnnEO6hX4iZ3EWY= +github.com/gordonklaus/ineffassign v0.0.0-20200309095847-7953dde2c7bf/go.mod h1:cuNKsD1zp2v6XfE/orVX2QE1LC+i254ceGcVeDT3pTU= +github.com/gordonklaus/ineffassign v0.0.0-20210225214923-2e10b2664254/go.mod h1:M9mZEtGIsR1oDaZagNPNG9iq9n2HrhZ17dsXk73V3Lw= +github.com/goreleaser/goreleaser v0.134.0/go.mod h1:ZT6Y2rSYa6NxQzIsdfWWNWAlYGXGbreo66NmE+3X3WQ= +github.com/goreleaser/nfpm v1.2.1/go.mod h1:TtWrABZozuLOttX2uDlYyECfQX7x5XYkVxhjYcR6G9w= +github.com/gorhill/cronexpr v0.0.0-20180427100037-88b0669f7d75/go.mod h1:g2644b03hfBX9Ov0ZBDgXXens4rxSxmqFBbhvKv2yVA= +github.com/gorilla/context v1.1.1/go.mod h1:kBGZzfjB9CEq2AlWe17Uuf7NDRt0dE0s8S51q0aT7Yg= +github.com/gorilla/handlers v0.0.0-20150720190736-60c7bfde3e33/go.mod h1:Qkdc/uu4tH4g6mTK6auzZ766c4CA0Ng8+o/OAirnOIQ= +github.com/gorilla/mux v1.6.2/go.mod h1:1lud6UwP+6orDFRuTfBEV8e9/aOM/c4fVVCaMa2zaAs= +github.com/gorilla/mux v1.7.2/go.mod h1:1lud6UwP+6orDFRuTfBEV8e9/aOM/c4fVVCaMa2zaAs= +github.com/gorilla/mux v1.7.3/go.mod h1:1lud6UwP+6orDFRuTfBEV8e9/aOM/c4fVVCaMa2zaAs= +github.com/gorilla/mux v1.8.0/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So= +github.com/gorilla/websocket v0.0.0-20170926233335-4201258b820c/go.mod h1:E7qHFY5m1UJ88s3WnNqhKjPHQ0heANvMoAMk2YaljkQ= +github.com/gorilla/websocket v1.4.0/go.mod h1:E7qHFY5m1UJ88s3WnNqhKjPHQ0heANvMoAMk2YaljkQ= +github.com/gorilla/websocket v1.4.1/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= +github.com/gorilla/websocket v1.4.2 h1:+/TMaTYc4QFitKJxsQ7Yye35DkWvkdLcvGKqM+x0Ufc= +github.com/gorilla/websocket v1.4.2/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= +github.com/gostaticanalysis/analysisutil v0.0.0-20190318220348-4088753ea4d3/go.mod h1:eEOZF4jCKGi+aprrirO9e7WKB3beBRtWgqGunKl6pKE= +github.com/gostaticanalysis/analysisutil v0.0.3/go.mod h1:eEOZF4jCKGi+aprrirO9e7WKB3beBRtWgqGunKl6pKE= +github.com/gostaticanalysis/analysisutil v0.1.0/go.mod h1:dMhHRU9KTiDcuLGdy87/2gTR8WruwYZrKdRq9m1O6uw= +github.com/gostaticanalysis/analysisutil v0.4.1/go.mod h1:18U/DLpRgIUd459wGxVHE0fRgmo1UgHDcbw7F5idXu0= +github.com/gostaticanalysis/analysisutil v0.7.1/go.mod h1:v21E3hY37WKMGSnbsw2S/ojApNWb6C1//mXO48CXbVc= +github.com/gostaticanalysis/comment v1.3.0/go.mod h1:xMicKDx7XRXYdVwY9f9wQpDJVnqWxw9wCauCMKp+IBI= +github.com/gostaticanalysis/comment v1.4.1/go.mod h1:ih6ZxzTHLdadaiSnF5WY3dxUoXfXAlTaRzuaNDlSado= +github.com/gostaticanalysis/comment v1.4.2/go.mod h1:KLUTGDv6HOCotCH8h2erHKmpci2ZoR8VPu34YA2uzdM= +github.com/gostaticanalysis/forcetypeassert v0.0.0-20200621232751-01d4955beaa5/go.mod h1:qZEedyP/sY1lTGV1uJ3VhWZ2mqag3IkWsDHVbplHXak= +github.com/gostaticanalysis/nilerr v0.1.1/go.mod h1:wZYb6YI5YAxxq0i1+VJbY0s2YONW0HU0GPE3+5PWN4A= +github.com/gostaticanalysis/testutil v0.3.1-0.20210208050101-bfb5c8eec0e4/go.mod h1:D+FIZ+7OahH3ePw/izIEeH5I06eKs1IKI4Xr64/Am3M= +github.com/gostaticanalysis/testutil v0.4.0/go.mod h1:bLIoPefWXrRi/ssLFWX1dx7Repi5x3CuviD3dgAZaBU= +github.com/gregjones/httpcache v0.0.0-20180305231024-9cad4c3443a7/go.mod h1:FecbI9+v66THATjSRHfNgh1IVFe/9kFxbXtjV0ctIMA= +github.com/gregjones/httpcache v0.0.0-20190611155906-901d90724c79/go.mod h1:FecbI9+v66THATjSRHfNgh1IVFe/9kFxbXtjV0ctIMA= +github.com/grpc-ecosystem/go-grpc-middleware v1.0.0/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs= +github.com/grpc-ecosystem/go-grpc-middleware v1.0.1-0.20190118093823-f849b5445de4/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs= +github.com/grpc-ecosystem/go-grpc-middleware v1.2.2/go.mod h1:EaizFBKfUKtMIF5iaDEhniwNedqGo9FuLFzppDr3uwI= +github.com/grpc-ecosystem/go-grpc-middleware v1.3.0 h1:+9834+KizmvFV7pXQGSXQTsaWhq2GjuNUt0aUU0YBYw= +github.com/grpc-ecosystem/go-grpc-middleware v1.3.0/go.mod h1:z0ButlSOZa5vEBq9m2m2hlwIgKw+rp3sdCBRoJY+30Y= +github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0 h1:Ovs26xHkKqVztRpIrF/92BcuyuQ/YW4NSIpoGtfXNho= +github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk= +github.com/grpc-ecosystem/grpc-gateway v1.8.5/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY= +github.com/grpc-ecosystem/grpc-gateway v1.9.0/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY= +github.com/grpc-ecosystem/grpc-gateway v1.9.2/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY= +github.com/grpc-ecosystem/grpc-gateway v1.9.5/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY= +github.com/grpc-ecosystem/grpc-gateway v1.12.1/go.mod h1:8XEsbTttt/W+VvjtQhLACqCisSPWTxCZ7sBRjU6iH9c= +github.com/grpc-ecosystem/grpc-gateway v1.14.6/go.mod h1:zdiPV4Yse/1gnckTHtghG4GkDEdKCRJduHpTxT3/jcw= +github.com/grpc-ecosystem/grpc-gateway v1.16.0 h1:gmcG1KaJ57LophUzW0Hy8NmPhnMZb4M0+kPpLofRdBo= +github.com/grpc-ecosystem/grpc-gateway v1.16.0/go.mod h1:BDjrQk3hbvj6Nolgz8mAMFbcEtjT1g+wF4CSlocrBnw= +github.com/grpc-ecosystem/grpc-gateway/v2 v2.7.0/go.mod h1:hgWBS7lorOAVIJEQMi4ZsPv9hVvWI6+ch50m39Pf2Ks= +github.com/grpc-ecosystem/grpc-gateway/v2 v2.11.2 h1:BqHID5W5qnMkug0Z8UmL8tN0gAy4jQ+B4WFt8cCgluU= +github.com/grpc-ecosystem/grpc-gateway/v2 v2.11.2/go.mod h1:ZbS3MZTZq/apAfAEHGoB5HbsQQstoqP92SjAqtQ9zeg= +github.com/hashicorp/consul/api v1.1.0/go.mod h1:VmuI/Lkw1nC05EYQWNKwWGbkg+FbDBtguAZLlVdkD9Q= +github.com/hashicorp/consul/api v1.3.0/go.mod h1:MmDNSzIMUjNpY/mQ398R4bk2FnqQLoPndWW5VkKPlCE= +github.com/hashicorp/consul/api v1.10.1/go.mod h1:XjsvQN+RJGWI2TWy1/kqaE16HrR2J/FWgkYjdZQsX9M= +github.com/hashicorp/consul/sdk v0.1.1/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8= +github.com/hashicorp/consul/sdk v0.3.0/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8= +github.com/hashicorp/consul/sdk v0.8.0/go.mod h1:GBvyrGALthsZObzUGsfgHZQDXjg4lOjagTIwIR1vPms= +github.com/hashicorp/errwrap v0.0.0-20141028054710-7554cd9344ce/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= +github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= +github.com/hashicorp/errwrap v1.1.0 h1:OxrOeh75EUXMY8TBjag2fzXGZ40LB6IKw45YeGUDY2I= +github.com/hashicorp/errwrap v1.1.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= +github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= +github.com/hashicorp/go-cleanhttp v0.5.2 h1:035FKYIWjmULyFRBKPs8TBQoi0x6d9G4xc9neXJWAZQ= +github.com/hashicorp/go-cleanhttp v0.5.2/go.mod h1:kO/YDlP8L1346E6Sodw+PrpBSV4/SoxCXGY6BqNFT48= +github.com/hashicorp/go-hclog v0.9.2/go.mod h1:5CU+agLiy3J7N7QjHK5d05KxGsuXiQLrjA0H7acj2lQ= +github.com/hashicorp/go-hclog v0.12.0/go.mod h1:whpDNt7SSdeAju8AWKIWsul05p54N/39EeqMAyrmvFQ= +github.com/hashicorp/go-hclog v1.2.2 h1:ihRI7YFwcZdiSD7SIenIhHfQH3OuDvWerAUBZbeQS3M= +github.com/hashicorp/go-immutable-radix v1.0.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60= +github.com/hashicorp/go-immutable-radix v1.3.1 h1:DKHmCUm2hRBK510BaiZlwvpD40f8bJFeZnpfm2KLowc= +github.com/hashicorp/go-msgpack v0.5.3/go.mod h1:ahLV/dePpqEmjfWmKiqvPkv/twdG7iPBM1vqhUKIvfM= +github.com/hashicorp/go-multierror v0.0.0-20161216184304-ed905158d874/go.mod h1:JMRHfdO9jKNzS/+BTlxCjKNQHg/jZAft8U7LloJvN7I= +github.com/hashicorp/go-multierror v1.0.0/go.mod h1:dHtQlpGsu+cZNNAkkCN/P3hoUDHhCYQXV3UM06sGGrk= +github.com/hashicorp/go-multierror v1.1.0/go.mod h1:spPvp8C1qA32ftKqdAHm4hHTbPw+vmowP0z+KUhOZdA= +github.com/hashicorp/go-multierror v1.1.1 h1:H5DkEtf6CXdFp0N0Em5UCwQpXMWke8IA0+lD48awMYo= +github.com/hashicorp/go-multierror v1.1.1/go.mod h1:iw975J/qwKPdAO1clOe2L8331t/9/fmwbPZ6JB6eMoM= +github.com/hashicorp/go-plugin v1.4.4 h1:NVdrSdFRt3SkZtNckJ6tog7gbpRrcbOjQi/rgF7JYWQ= +github.com/hashicorp/go-retryablehttp v0.6.4/go.mod h1:vAew36LZh98gCBJNLH42IQ1ER/9wtLZZ8meHqQvEYWY= +github.com/hashicorp/go-retryablehttp v0.7.1 h1:sUiuQAnLlbvmExtFQs72iFW/HXeUn8Z1aJLQ4LJJbTQ= +github.com/hashicorp/go-retryablehttp v0.7.1/go.mod h1:vAew36LZh98gCBJNLH42IQ1ER/9wtLZZ8meHqQvEYWY= +github.com/hashicorp/go-rootcerts v1.0.0/go.mod h1:K6zTfqpRlCUIjkwsN4Z+hiSfzSTQa6eBIzfwKfwNnHU= +github.com/hashicorp/go-rootcerts v1.0.2 h1:jzhAVGtqPKbwpyCPELlgNWhE1znq+qwJtW5Oi2viEzc= +github.com/hashicorp/go-rootcerts v1.0.2/go.mod h1:pqUvnprVnM5bf7AOirdbb01K4ccR319Vf4pU3K5EGc8= +github.com/hashicorp/go-secure-stdlib/mlock v0.1.2 h1:p4AKXPPS24tO8Wc8i1gLvSKdmkiSY5xuju57czJ/IJQ= +github.com/hashicorp/go-secure-stdlib/parseutil v0.1.7 h1:UpiO20jno/eV1eVZcxqWnUohyKRe1g8FPV/xH1s/2qs= +github.com/hashicorp/go-secure-stdlib/strutil v0.1.2 h1:kes8mmyCpxJsI7FTwtzRqEy9CdjCtrXrXGuOpxEA7Ts= +github.com/hashicorp/go-sockaddr v1.0.0/go.mod h1:7Xibr9yA9JjQq1JpNB2Vw7kxv8xerXegt+ozgdvDeDU= +github.com/hashicorp/go-sockaddr v1.0.2 h1:ztczhD1jLxIRjVejw8gFomI1BQZOe2WoVOu0SyteCQc= +github.com/hashicorp/go-syslog v1.0.0/go.mod h1:qPfqrKkXGihmCqbJM2mZgkZGvKG1dFdvsLplgctolz4= +github.com/hashicorp/go-uuid v1.0.0/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= +github.com/hashicorp/go-uuid v1.0.1/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= +github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8= +github.com/hashicorp/go-version v1.2.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= +github.com/hashicorp/go-version v1.2.1/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= +github.com/hashicorp/go-version v1.6.0 h1:feTTfFNnjP967rlCxM/I9g701jU+RN74YKx2mOkIeek= +github.com/hashicorp/go.net v0.0.1/go.mod h1:hjKkEWcCURg++eb33jQU7oqQcI9XDCnUzHA0oac0k90= +github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= +github.com/hashicorp/golang-lru v0.5.1/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= +github.com/hashicorp/golang-lru v0.5.4 h1:YDjusn29QI/Das2iO9M0BHnIbxPeyuCHsjMW+lJfyTc= +github.com/hashicorp/golang-lru v0.5.4/go.mod h1:iADmTwqILo4mZ8BN3D2Q6+9jd8WM5uGBxy+E8yxSoD4= +github.com/hashicorp/hcl v1.0.0 h1:0Anlzjpi4vEasTeNFn2mLJgTSwt0+6sfsiTG8qcWGx4= +github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ= +github.com/hashicorp/logutils v1.0.0/go.mod h1:QIAnNjmIWmVIIkWDTG1z5v++HQmx9WQRO+LraFDTW64= +github.com/hashicorp/mdns v1.0.0/go.mod h1:tL+uN++7HEJ6SQLQ2/p+z2pH24WQKWjBPkE0mNTz8vQ= +github.com/hashicorp/mdns v1.0.1/go.mod h1:4gW7WsVCke5TE7EPeYliwHlRUyBtfCwuFwuMg2DmyNY= +github.com/hashicorp/memberlist v0.1.3/go.mod h1:ajVTdAv/9Im8oMAAj5G31PhhMCZJV2pPBoIllUwCN7I= +github.com/hashicorp/memberlist v0.2.2/go.mod h1:MS2lj3INKhZjWNqd3N0m3J+Jxf3DAOnAH9VT3Sh9MUE= +github.com/hashicorp/serf v0.8.2/go.mod h1:6hOLApaqBFA1NXqRQAsxw9QxuDEvNxSQRwA/JwenrHc= +github.com/hashicorp/serf v0.9.5/go.mod h1:UWDWwZeL5cuWDJdl0C6wrvrUwEqtQ4ZKBKKENpqIUyk= +github.com/hashicorp/vault/api v1.7.2 h1:kawHE7s/4xwrdKbkmwQi0wYaIeUhk5ueek7ljuezCVQ= +github.com/hashicorp/vault/sdk v0.5.3 h1:PWY8sq/9pRrK9vUIy75qCH2Jd8oeENAgkaa/qbhzFrs= +github.com/hashicorp/yamux v0.1.0 h1:DzDIF6Sd7GD2sX0kDFpHAsJMY4L+OfTvtuaQsOYXxzk= +github.com/honeycombio/beeline-go v1.1.1 h1:sU8r4ae34uEL3/CguSl8Mr+Asz9DL1nfH9Wwk85Pc7U= +github.com/honeycombio/libhoney-go v1.15.2 h1:5NGcjOxZZma13dmzNcl3OtGbF1hECA0XHJNHEb2t2ck= +github.com/howeyc/gopass v0.0.0-20190910152052-7cb4b85ec19c/go.mod h1:lADxMC39cJJqL93Duh1xhAs4I2Zs8mKS89XWXFGp9cs= +github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= +github.com/huandu/xstrings v1.0.0/go.mod h1:4qWG/gcEcfX4z/mBDHJ++3ReCw9ibxbsNJbcucJdbSo= +github.com/huandu/xstrings v1.2.0/go.mod h1:DvyZB1rfVYsBIigL8HwpZgxHwXozlTgGqn63UyNX5k4= +github.com/huandu/xstrings v1.3.1/go.mod h1:y5/lhBue+AyNmUVz9RLU9xbLR0o4KIIExikq4ovT0aE= +github.com/huandu/xstrings v1.3.2 h1:L18LIDzqlW6xN2rEkpdV8+oL/IXWJ1APd+vsdYy4Wdw= +github.com/huandu/xstrings v1.3.2/go.mod h1:y5/lhBue+AyNmUVz9RLU9xbLR0o4KIIExikq4ovT0aE= +github.com/hudl/fargo v1.3.0/go.mod h1:y3CKSmjA+wD2gak7sUSXTAoopbhU08POFhmITJgmKTg= +github.com/iancoleman/orderedmap v0.0.0-20190318233801-ac98e3ecb4b0 h1:i462o439ZjprVSFSZLZxcsoAe592sZB1rci2Z8j4wdk= +github.com/iancoleman/orderedmap v0.0.0-20190318233801-ac98e3ecb4b0/go.mod h1:N0Wam8K1arqPXNWjMo21EXnBPOPp36vB07FNRdD2geA= +github.com/iancoleman/strcase v0.2.0/go.mod h1:iwCmte+B7n89clKwxIoIXy/HfoL7AsD47ZCWhYzw7ho= +github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= +github.com/ianlancetaylor/demangle v0.0.0-20200824232613-28f6c0f3b639/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= +github.com/imdario/mergo v0.3.4/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA= +github.com/imdario/mergo v0.3.5/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA= +github.com/imdario/mergo v0.3.8/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA= +github.com/imdario/mergo v0.3.9/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA= +github.com/imdario/mergo v0.3.10/go.mod h1:jmQim1M+e3UYxmgPu/WyfjB3N3VflVyUjjjwH0dnCYA= +github.com/imdario/mergo v0.3.11/go.mod h1:jmQim1M+e3UYxmgPu/WyfjB3N3VflVyUjjjwH0dnCYA= +github.com/imdario/mergo v0.3.12 h1:b6R2BslTbIEToALKP7LxUvijTsNI9TAe80pLWN2g/HU= +github.com/imdario/mergo v0.3.12/go.mod h1:jmQim1M+e3UYxmgPu/WyfjB3N3VflVyUjjjwH0dnCYA= +github.com/in-toto/in-toto-golang v0.3.4-0.20220709202702-fa494aaa0add h1:DAh7mHiRT7wc6kKepYdCpH16ElPciMPQWJaJ7H3l/ng= +github.com/in-toto/in-toto-golang v0.3.4-0.20220709202702-fa494aaa0add/go.mod h1:DQI8vlV6h6qSY/tCOoYKtxjWrkyiNpJ3WTV/WoBllmQ= +github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM= +github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8= +github.com/influxdata/influxdb1-client v0.0.0-20191209144304-8bf82d3c094d/go.mod h1:qj24IKcXYK6Iy9ceXlo3Tc+vtHo9lIhSX5JddghvEPo= +github.com/j-keck/arping v0.0.0-20160618110441-2cf9dc699c56/go.mod h1:ymszkNOg6tORTn+6F6j+Jc8TOr5osrynvN6ivFWZ2GA= +github.com/jarcoal/httpmock v1.0.5/go.mod h1:ATjnClrvW/3tijVmpL/va5Z3aAyGvqU3gCT8nX0Txik= +github.com/jbenet/go-context v0.0.0-20150711004518-d14ea06fba99/go.mod h1:1lJo3i6rXxKeerYnT8Nvf0QmHCRC1n8sfWVwXF2Frvo= +github.com/jedisct1/go-minisign v0.0.0-20211028175153-1c139d1cc84b h1:ZGiXF8sz7PDk6RgkP+A/SFfUD0ZR/AgG6SpRNEDKZy8= +github.com/jedisct1/go-minisign v0.0.0-20211028175153-1c139d1cc84b/go.mod h1:hQmNrgofl+IY/8L+n20H6E6PWBBTokdsv+q49j0QhsU= +github.com/jellydator/ttlcache/v2 v2.11.1 h1:AZGME43Eh2Vv3giG6GeqeLeFXxwxn1/qHItqWZl6U64= +github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI= +github.com/jgautheron/goconst v1.5.1/go.mod h1:aAosetZ5zaeC/2EfMeRswtxUFBpe2Hr7HzkgX4fanO4= +github.com/jhump/gopoet v0.0.0-20190322174617-17282ff210b3/go.mod h1:me9yfT6IJSlOL3FCfrg+L6yzUEZ+5jW6WHt4Sk+UPUI= +github.com/jhump/gopoet v0.1.0/go.mod h1:me9yfT6IJSlOL3FCfrg+L6yzUEZ+5jW6WHt4Sk+UPUI= +github.com/jhump/goprotoc v0.5.0/go.mod h1:VrbvcYrQOrTi3i0Vf+m+oqQWk9l72mjkJCYo7UvLHRQ= +github.com/jhump/protoreflect v1.6.1/go.mod h1:RZQ/lnuN+zqeRVpQigTwO6o0AJUkxbnSnpuG7toUTG4= +github.com/jhump/protoreflect v1.8.2/go.mod h1:7GcYQDdMU/O/BBrl/cX6PNHpXh6cenjd8pneu5yW7Tg= +github.com/jhump/protoreflect v1.10.3/go.mod h1:7GcYQDdMU/O/BBrl/cX6PNHpXh6cenjd8pneu5yW7Tg= +github.com/jhump/protoreflect v1.11.0/go.mod h1:U7aMIjN0NWq9swDP7xDdoMfRHb35uiuTd3Z9nFXJf5E= +github.com/jhump/protoreflect v1.12.0 h1:1NQ4FpWMgn3by/n1X0fbeKEUxP1wBt7+Oitpv01HR10= +github.com/jhump/protoreflect v1.12.0/go.mod h1:JytZfP5d0r8pVNLZvai7U/MCuTWITgrI4tTg7puQFKI= +github.com/jingyugao/rowserrcheck v1.1.1/go.mod h1:4yvlZSDb3IyDTUZJUmpZfm2Hwok+Dtp+nu2qOq+er9c= +github.com/jinzhu/copier v0.3.2 h1:QdBOCbaouLDYaIPFfi1bKv5F5tPpeTwXe4sD0jqtz5w= +github.com/jinzhu/copier v0.3.2/go.mod h1:24xnZezI2Yqac9J61UC6/dG/k76ttpq0DdJI3QmUvro= +github.com/jirfag/go-printf-func-name v0.0.0-20200119135958-7558a9eaa5af/go.mod h1:HEWGJkRDzjJY2sqdDwxccsGicWEf9BQOZsq2tV+xzM0= +github.com/jmespath/go-jmespath v0.0.0-20160202185014-0b12d6b521d8/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k= +github.com/jmespath/go-jmespath v0.0.0-20160803190731-bd40a432e4c7/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k= +github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k= +github.com/jmespath/go-jmespath v0.4.0 h1:BEgLn5cpjn8UN1mAw4NjwDrS35OdebyEtFe+9YPoQUg= +github.com/jmespath/go-jmespath v0.4.0/go.mod h1:T8mJZnbsbmF+m6zOOFylbeCJqk5+pHWvzYPziyZiYoo= +github.com/jmespath/go-jmespath/internal/testify v1.5.1 h1:shLQSRRSCCPj3f2gpwzGwWFoC7ycTf1rcQZHOlsJ6N8= +github.com/jmespath/go-jmespath/internal/testify v1.5.1/go.mod h1:L3OGu8Wl2/fWfCI6z80xFu9LTZmf1ZRjMHUOPmWr69U= +github.com/jmhodges/clock v0.0.0-20160418191101-880ee4c33548 h1:dYTbLf4m0a5u0KLmPfB6mgxbcV7588bOCx79hxa5Sr4= +github.com/jmoiron/sqlx v1.2.0/go.mod h1:1FEQNm3xlJgrMD+FBdI9+xvCksHtbpVBBw5dYhBSsks= +github.com/joho/godotenv v1.3.0/go.mod h1:7hK45KPybAkOC6peb+G5yklZfMxEjkZhHbwpqxOKXbg= +github.com/jonboulle/clockwork v0.1.0/go.mod h1:Ii8DK3G1RaLaWxj9trq07+26W01tbo22gdxWY5EU2bo= +github.com/jonboulle/clockwork v0.2.0/go.mod h1:Pkfl5aHPm1nk2H9h0bjmnJD/BcgbGXUBGnn1kMkgxc8= +github.com/jonboulle/clockwork v0.2.2/go.mod h1:Pkfl5aHPm1nk2H9h0bjmnJD/BcgbGXUBGnn1kMkgxc8= +github.com/jonboulle/clockwork v0.3.0 h1:9BSCMi8C+0qdApAp4auwX0RkLGUjs956h0EkuQymUhg= +github.com/jonboulle/clockwork v0.3.0/go.mod h1:Pkfl5aHPm1nk2H9h0bjmnJD/BcgbGXUBGnn1kMkgxc8= +github.com/josharian/intern v1.0.0 h1:vlS4z54oSdjm0bgjRigI+G1HpF+tI+9rE5LLzOg8HmY= +github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y= +github.com/josharian/txtarfs v0.0.0-20210218200122-0702f000015a/go.mod h1:izVPOvVRsHiKkeGCT6tYBNWyDVuzj9wAaBb5R9qamfw= +github.com/jpillora/backoff v0.0.0-20180909062703-3050d21c67d7/go.mod h1:2iMrUgbbvHEiQClaW2NsSzMyGHqN+rDFqY705q49KG0= +github.com/jpillora/backoff v1.0.0/go.mod h1:J/6gKK9jxlEcS3zixgDgUAsiuZ7yrSoa/FX5e0EB2j4= +github.com/json-iterator/go v1.1.6/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU= +github.com/json-iterator/go v1.1.7/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= +github.com/json-iterator/go v1.1.8/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= +github.com/json-iterator/go v1.1.9/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= +github.com/json-iterator/go v1.1.10/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= +github.com/json-iterator/go v1.1.11/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= +github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= +github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= +github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU= +github.com/jstemmer/go-junit-report v0.9.1/go.mod h1:Brl9GWCQeLvo8nXZwPNNblvFj/XSXhF0NWZEnDohbsk= +github.com/jtolds/gls v4.20.0+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU= +github.com/juju/ratelimit v1.0.1/go.mod h1:qapgC/Gy+xNh9UxzV13HGGl/6UXNN+ct+vwSgWNm/qk= +github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w= +github.com/julienschmidt/httprouter v1.3.0/go.mod h1:JR6WtHb+2LUe8TCKY3cZOxFyyO8IZAc4RVcycCCAKdM= +github.com/julz/importas v0.0.0-20210419104244-841f0c0fe66d/go.mod h1:oSFU2R4XK/P7kNBrnL/FEQlDGN1/6WoxXEjSSXO0DV0= +github.com/k0kubun/colorstring v0.0.0-20150214042306-9440f1994b88/go.mod h1:3w7q1U84EfirKl04SVQ/s7nPm1ZPhiXd34z40TNz36k= +github.com/k0kubun/go-ansi v0.0.0-20180517002512-3bf9e2903213/go.mod h1:vNUNkEQ1e29fT/6vq2aBdFsgNPmy8qMdSay1npru+Sw= +github.com/karrick/godirwalk v1.8.0/go.mod h1:H5KPZjojv4lE+QYImBI8xVtrBRgYrIVsaRPx4tDPEn4= +github.com/karrick/godirwalk v1.10.3/go.mod h1:RoGL9dQei4vP9ilrpETWE8CLOZ1kiN0LhBygSwrAsHA= +github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51 h1:Z9n2FFNUXsshfwJMBgNA0RU6/i7WVaAegv3PtuIHPMs= +github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51/go.mod h1:CzGEWj7cYgsdH8dAjBGEr58BoE7ScuLd+fwFZ44+/x8= +github.com/kevinburke/ssh_config v0.0.0-20190725054713-01f96b0aa0cd/go.mod h1:CT57kijsi8u/K/BOFA39wgDQJ9CxiF4nAY/ojJ6r6mM= +github.com/kisielk/errcheck v1.1.0/go.mod h1:EZBBE59ingxPouuu3KfxchcWSUPOHkagtvWXihfKN4Q= +github.com/kisielk/errcheck v1.2.0/go.mod h1:/BMXB+zMLi60iA8Vv6Ksmxu/1UDYcXs4uQLJ+jE2L00= +github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= +github.com/kisielk/errcheck v1.6.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= +github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= +github.com/klauspost/compress v1.4.1/go.mod h1:RyIbtBH6LamlWaDj8nUwkbUhJ87Yi3uG0guNDohfE1A= +github.com/klauspost/compress v1.11.3/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= +github.com/klauspost/compress v1.11.4/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= +github.com/klauspost/compress v1.11.7/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= +github.com/klauspost/compress v1.11.13/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= +github.com/klauspost/compress v1.13.4/go.mod h1:8dP1Hq4DHOhN9w426knH3Rhby4rFm6D8eO+e+Dq5Gzg= +github.com/klauspost/compress v1.13.5/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk= +github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk= +github.com/klauspost/compress v1.15.7/go.mod h1:PhcZ0MbTNciWF3rruxRgKxI5NkcHHrHUDtV4Yw2GlzU= +github.com/klauspost/compress v1.15.9 h1:wKRjX6JRtDdrE9qwa4b/Cip7ACOshUI4smpCQanqjSY= +github.com/klauspost/compress v1.15.9/go.mod h1:PhcZ0MbTNciWF3rruxRgKxI5NkcHHrHUDtV4Yw2GlzU= +github.com/klauspost/cpuid v1.2.0/go.mod h1:Pj4uuM528wm8OyEC2QMXAi2YiTZ96dNQPGgoMS4s3ek= +github.com/klauspost/pgzip v1.2.5 h1:qnWYvvKqedOF2ulHpMG72XQol4ILEJ8k2wwRl/Km8oE= +github.com/klauspost/pgzip v1.2.5/go.mod h1:Ch1tH69qFZu15pkjo5kYi6mth2Zzwzt50oCQKQE9RUs= +github.com/knqyf263/go-rpmdb v0.0.0-20220629110411-9a3bd2ebb923 h1:lANQvsfy2FOuURL6vKO3T4gNpez/3xZt+dx6uWMD42I= +github.com/knqyf263/go-rpmdb v0.0.0-20220629110411-9a3bd2ebb923/go.mod h1:zp6SMcRd0GB+uwNJjr+DkrNZdQZ4er2HMO6KyD0vIGU= +github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= +github.com/konsorten/go-windows-terminal-sequences v1.0.2/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= +github.com/konsorten/go-windows-terminal-sequences v1.0.3/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= +github.com/kr/fs v0.1.0/go.mod h1:FFnZGqtBN9Gxj7eW1uZ42v5BccTP0vu6NEaFoC2HwRg= +github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc= +github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= +github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= +github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= +github.com/kr/pretty v0.3.0 h1:WgNl7dwNpEZ6jJ9k1snq4pZsg7DOEN8hP9Xw0Tsjwk0= +github.com/kr/pretty v0.3.0/go.mod h1:640gp4NfQd8pI5XOwp5fnNeVWj67G7CFk/SaSQn7NBk= +github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= +github.com/kr/pty v1.1.5/go.mod h1:9r2w37qlBe7rQ6e1fg1S/9xpWHSnaqNdHD3WcMdbPDA= +github.com/kr/pty v1.1.8/go.mod h1:O1sed60cT9XZ5uDucP5qwvh+TE3NnUj51EiZO/lmSfw= +github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= +github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= +github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= +github.com/kulti/thelper v0.4.0/go.mod h1:vMu2Cizjy/grP+jmsvOFDx1kYP6+PD1lqg4Yu5exl2U= +github.com/kunwardeep/paralleltest v1.0.3/go.mod h1:vLydzomDFpk7yu5UX02RmP0H8QfRPOV/oFhWN85Mjb4= +github.com/kylelemons/godebug v1.1.0/go.mod h1:9/0rRGxNHcop5bhtWyNeEfOS8JIWk580+fNqagV/RAw= +github.com/kyoh86/exportloopref v0.1.8/go.mod h1:1tUcJeiioIs7VWe5gcOObrux3lb66+sBqGZrRkMwPgg= +github.com/ldez/gomoddirectives v0.2.2/go.mod h1:cpgBogWITnCfRq2qGoDkKMEVSaarhdBr6g8G04uz6d0= +github.com/ldez/tagliatelle v0.2.0/go.mod h1:8s6WJQwEYHbKZDsp/LjArytKOG8qaMrKQQ3mFukHs88= +github.com/leodido/go-urn v1.2.1 h1:BqpAaACuzVSgi/VLzGZIobT2z4v53pjosyNd9Yv6n/w= +github.com/leodido/go-urn v1.2.1/go.mod h1:zt4jvISO2HfUBqxjfIshjdMTYS56ZS/qv49ictyFfxY= +github.com/letsencrypt/boulder v0.0.0-20220723181115-27de4befb95e h1:2ba+yBBeT8ZFyZjRLPDKvkqVrWX4CCYAuR6nuJGojD0= +github.com/letsencrypt/boulder v0.0.0-20220723181115-27de4befb95e/go.mod h1:54WQpg5QI0mpRhxoj9bxysLqA5WJylVsLtXOrb3zAiU= +github.com/letsencrypt/pkcs11key/v4 v4.0.0/go.mod h1:EFUvBDay26dErnNb70Nd0/VW3tJiIbETBPTl9ATXQag= +github.com/lib/pq v1.0.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= +github.com/lib/pq v1.1.1/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= +github.com/lib/pq v1.8.0/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= +github.com/lib/pq v1.9.0/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= +github.com/lib/pq v1.10.3/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= +github.com/lightstep/lightstep-tracer-common/golang/gogo v0.0.0-20190605223551-bc2310a04743/go.mod h1:qklhhLq1aX+mtWk9cPHPzaBjWImj5ULL6C7HFJtXQMM= +github.com/lightstep/lightstep-tracer-go v0.18.1/go.mod h1:jlF1pusYV4pidLvZ+XD0UBX0ZE6WURAspgAczcDHrL4= +github.com/linkedin/goavro v2.1.0+incompatible/go.mod h1:bBCwI2eGYpUI/4820s67MElg9tdeLbINjLjiM2xZFYM= +github.com/logrusorgru/aurora v0.0.0-20181002194514-a7b3b318ed4e/go.mod h1:7rIyQOR62GCctdiQpZ/zOJlFyk6y+94wXzv6RNZgaR4= +github.com/logrusorgru/aurora v0.0.0-20200102142835-e9ef32dff381 h1:bqDmpDG49ZRnB5PcgP0RXtQvnMSgIF14M7CBd2shtXs= +github.com/logrusorgru/aurora v0.0.0-20200102142835-e9ef32dff381/go.mod h1:7rIyQOR62GCctdiQpZ/zOJlFyk6y+94wXzv6RNZgaR4= +github.com/lufia/plan9stats v0.0.0-20211012122336-39d0f177ccd0/go.mod h1:zJYVVT2jmtg6P3p1VtQj7WsuWi/y4VnjVBn7F8KPB3I= +github.com/lyft/protoc-gen-star v0.5.3/go.mod h1:V0xaHgaf5oCCqmcxYcWiDfTiKsZsRc87/1qhoTACD8w= +github.com/lyft/protoc-gen-validate v0.0.13/go.mod h1:XbGvPuh87YZc5TdIa2/I4pLk0QoUACkjt2znoq26NVQ= +github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= +github.com/magiconair/properties v1.8.1/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= +github.com/magiconair/properties v1.8.4/go.mod h1:y3VJvCyxH9uVvJTWEGAELF3aiYNyPKd5NZ3oSwXrF60= +github.com/magiconair/properties v1.8.5/go.mod h1:y3VJvCyxH9uVvJTWEGAELF3aiYNyPKd5NZ3oSwXrF60= +github.com/magiconair/properties v1.8.6 h1:5ibWZ6iY0NctNGWo87LalDlEZ6R41TqbbDamhfG/Qzo= +github.com/magiconair/properties v1.8.6/go.mod h1:y3VJvCyxH9uVvJTWEGAELF3aiYNyPKd5NZ3oSwXrF60= +github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= +github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= +github.com/mailru/easyjson v0.7.0/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs= +github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= +github.com/mailru/easyjson v0.7.7 h1:UGYAvKxe3sBsEDzO8ZeWOSlIQfWFlxbzLZe7hwFURr0= +github.com/mailru/easyjson v0.7.7/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= +github.com/maratori/testpackage v1.0.1/go.mod h1:ddKdw+XG0Phzhx8BFDTKgpWP4i7MpApTE5fXSKAqwDU= +github.com/markbates/oncer v0.0.0-20181203154359-bf2de49a0be2/go.mod h1:Ld9puTsIW75CHf65OeIOkyKbteujpZVXDpWK6YGZbxE= +github.com/markbates/safe v1.0.1/go.mod h1:nAqgmRi7cY2nqMc92/bSEeQA+R4OheNU2T1kNSCBdG0= +github.com/marstr/guid v1.1.0/go.mod h1:74gB1z2wpxxInTG6yaqA7KrtM0NZ+RbrcqDvYHefzho= +github.com/matoous/godox v0.0.0-20210227103229-6504466cf951/go.mod h1:1BELzlh859Sh1c6+90blK8lbYy0kwQf1bYlBhBysy1s= +github.com/matryer/is v1.4.0/go.mod h1:8I/i5uYgLzgsgEloJE1U6xx5HkBQpAZvepWuujKwMRU= +github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU= +github.com/mattn/go-colorable v0.1.1/go.mod h1:FuOcm+DKB9mbwrcAfNl7/TZVBZ6rcnceauSikq3lYCQ= +github.com/mattn/go-colorable v0.1.2/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= +github.com/mattn/go-colorable v0.1.4/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= +github.com/mattn/go-colorable v0.1.6/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= +github.com/mattn/go-colorable v0.1.8/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= +github.com/mattn/go-colorable v0.1.9/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= +github.com/mattn/go-colorable v0.1.11/go.mod h1:u5H1YNBxpqRaxsYJYSkiCWKzEfiAb1Gb520KVy5xxl4= +github.com/mattn/go-colorable v0.1.12 h1:jF+Du6AlPIjs2BiUiQlKOX0rt3SujHxPnksPKZbaA40= +github.com/mattn/go-colorable v0.1.12/go.mod h1:u5H1YNBxpqRaxsYJYSkiCWKzEfiAb1Gb520KVy5xxl4= +github.com/mattn/go-ieproxy v0.0.0-20190610004146-91bb50d98149/go.mod h1:31jz6HNzdxOmlERGGEc4v/dMssOfmp2p5bT/okiKFFc= +github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= +github.com/mattn/go-isatty v0.0.4/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= +github.com/mattn/go-isatty v0.0.5/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= +github.com/mattn/go-isatty v0.0.6/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= +github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= +github.com/mattn/go-isatty v0.0.10/go.mod h1:qgIWMr58cqv1PHHyhnkY9lrL7etaEgOFcMEpPG5Rm84= +github.com/mattn/go-isatty v0.0.11/go.mod h1:PhnuNfih5lzO57/f3n+odYbM4JtupLOxQOAqxQCu2WE= +github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU= +github.com/mattn/go-isatty v0.0.14 h1:yVuAays6BHfxijgZPzw+3Zlu5yQgKGP2/hcQbHb7S9Y= +github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94= +github.com/mattn/go-runewidth v0.0.2/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU= +github.com/mattn/go-runewidth v0.0.4/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU= +github.com/mattn/go-runewidth v0.0.6/go.mod h1:H031xJmbD/WCDINGzjvQ9THkh0rPKHF+m2gUSrubnMI= +github.com/mattn/go-runewidth v0.0.7/go.mod h1:H031xJmbD/WCDINGzjvQ9THkh0rPKHF+m2gUSrubnMI= +github.com/mattn/go-runewidth v0.0.9/go.mod h1:H031xJmbD/WCDINGzjvQ9THkh0rPKHF+m2gUSrubnMI= +github.com/mattn/go-runewidth v0.0.13 h1:lTGmDsbAYt5DmK6OnoV7EuIF1wEIFAcxld6ypU4OSgU= +github.com/mattn/go-runewidth v0.0.13/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w= +github.com/mattn/go-shellwords v1.0.3/go.mod h1:3xCvwCdWdlDJUrvuMn7Wuy9eWs4pE8vqg+NOMyg4B2o= +github.com/mattn/go-shellwords v1.0.10/go.mod h1:EZzvwXDESEeg03EKmM+RmDnNOPKG4lLtQsUlTZDWQ8Y= +github.com/mattn/go-sqlite3 v1.9.0/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc= +github.com/mattn/go-sqlite3 v1.14.10/go.mod h1:NyWgC/yNuGj7Q9rpYnZvas74GogHl5/Z4A/KQRfk6bU= +github.com/mattn/go-sqlite3 v1.14.12 h1:TJ1bhYJPV44phC+IMu1u2K/i5RriLTPe+yc68XDJ1Z0= +github.com/mattn/go-sqlite3 v1.14.12/go.mod h1:NyWgC/yNuGj7Q9rpYnZvas74GogHl5/Z4A/KQRfk6bU= +github.com/mattn/go-zglob v0.0.1/go.mod h1:9fxibJccNxU2cnpIKLRRFA7zX7qhkJIQWBb449FYHOo= +github.com/mattn/goveralls v0.0.2/go.mod h1:8d1ZMHsd7fW6IRPKQh46F2WRpyib5/X4FOpevwGNQEw= +github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0= +github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369 h1:I0XW9+e1XWDxdcEniV4rQAIOPUGDq67JSCiRCgGCZLI= +github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369/go.mod h1:BSXmuO+STAnVfrANrmjBb36TMTDstsz7MSK+HVaYKv4= +github.com/mbilski/exhaustivestruct v1.2.0/go.mod h1:OeTBVxQWoEmB2J2JCHmXWPJ0aksxSUOUy+nvtVEfzXc= +github.com/mgechev/dots v0.0.0-20210922191527-e955255bf517/go.mod h1:KQ7+USdGKfpPjXk4Ga+5XxQM4Lm4e3gAogrreFAYpOg= +github.com/mgechev/revive v1.1.2/go.mod h1:bnXsMr+ZTH09V5rssEI+jHAZ4z+ZdyhgO/zsy3EhK+0= +github.com/mgutz/ansi v0.0.0-20170206155736-9520e82c474b/go.mod h1:01TrycV0kFyexm33Z7vhZRXopbI8J3TDReVlkTgMUxE= +github.com/mgutz/ansi v0.0.0-20200706080929-d51e80ef957d h1:5PJl274Y63IEHC+7izoQE9x6ikvDFZS2mDVS3drnohI= +github.com/mgutz/ansi v0.0.0-20200706080929-d51e80ef957d/go.mod h1:01TrycV0kFyexm33Z7vhZRXopbI8J3TDReVlkTgMUxE= +github.com/mholt/archiver/v3 v3.5.1 h1:rDjOBX9JSF5BvoJGvjqK479aL70qh9DIpZCl+k7Clwo= +github.com/mholt/archiver/v3 v3.5.1/go.mod h1:e3dqJ7H78uzsRSEACH1joayhuSyhnonssnDhppzS1L4= +github.com/microsoft/go-rustaudit v0.0.0-20220730194248-4b17361d90a5 h1:tQRHcLQwnwrPq2j2Qra/NnyjyESBGwdeBeVdAE9kXYg= +github.com/microsoft/go-rustaudit v0.0.0-20220730194248-4b17361d90a5/go.mod h1:vYT9HE7WCvL64iVeZylKmCsWKfE+JZ8105iuh2Trk8g= +github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg= +github.com/miekg/dns v1.1.26/go.mod h1:bPDLeHnStXmXAq1m/Ch/hvfNHr14JKNPMBo3VZKjuso= +github.com/miekg/dns v1.1.35/go.mod h1:KNUDUusw/aVsxyTYZM1oqvCicbwhgbNgztCETuNZ7xM= +github.com/miekg/pkcs11 v1.0.2/go.mod h1:XsNlhZGX73bx86s2hdc/FuaLm2CPZJemRLMA+WTFxgs= +github.com/miekg/pkcs11 v1.0.3-0.20190429190417-a667d056470f/go.mod h1:XsNlhZGX73bx86s2hdc/FuaLm2CPZJemRLMA+WTFxgs= +github.com/miekg/pkcs11 v1.0.3/go.mod h1:XsNlhZGX73bx86s2hdc/FuaLm2CPZJemRLMA+WTFxgs= +github.com/miekg/pkcs11 v1.1.1 h1:Ugu9pdy6vAYku5DEpVWVFPYnzV+bxB+iRdbuFSu7TvU= +github.com/miekg/pkcs11 v1.1.1/go.mod h1:XsNlhZGX73bx86s2hdc/FuaLm2CPZJemRLMA+WTFxgs= +github.com/mistifyio/go-zfs v2.1.2-0.20190413222219-f784269be439+incompatible/go.mod h1:8AuVvqP/mXw1px98n46wfvcGfQ4ci2FwoAjKYxuo3Z4= +github.com/mitchellh/cli v1.0.0/go.mod h1:hNIlj7HEI86fIcpObd7a0FcrxTWetlwJDGcceTlRvqc= +github.com/mitchellh/cli v1.1.0/go.mod h1:xcISNoH86gajksDmfB23e/pu+B+GeFRMYmoHXxx3xhI= +github.com/mitchellh/copystructure v1.0.0/go.mod h1:SNtv71yrdKgLRyLFxmLdkAbkKEFWgYaq1OVrnRcwhnw= +github.com/mitchellh/copystructure v1.2.0 h1:vpKXTN4ewci03Vljg/q9QvCGUDttBOGBIa15WveJJGw= +github.com/mitchellh/copystructure v1.2.0/go.mod h1:qLl+cE2AmVv+CoeAwDPye/v+N2HKCj9FbZEVFJRxO9s= +github.com/mitchellh/go-homedir v1.0.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= +github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y= +github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= +github.com/mitchellh/go-ps v1.0.0/go.mod h1:J4lOc8z8yJs6vUwklHw2XEIiT4z4C40KtWVN3nvg8Pg= +github.com/mitchellh/go-testing-interface v1.0.0/go.mod h1:kRemZodwjscx+RGhAo8eIhFbs2+BFgRtFPeD/KE+zxI= +github.com/mitchellh/go-testing-interface v1.14.1 h1:jrgshOhYAUVNMAJiKbEu7EqAwgJJ2JqpQmpLJOu07cU= +github.com/mitchellh/gox v0.4.0/go.mod h1:Sd9lOJ0+aimLBi73mGofS1ycjY8lL3uZM3JPS42BGNg= +github.com/mitchellh/hashstructure/v2 v2.0.2 h1:vGKWl0YJqUNxE8d+h8f6NJLcCJrgbhC4NcD46KavDd4= +github.com/mitchellh/hashstructure/v2 v2.0.2/go.mod h1:MG3aRVU/N29oo/V/IhBX8GR/zz4kQkprJgF2EVszyDE= +github.com/mitchellh/iochan v1.0.0/go.mod h1:JwYml1nuB7xOzsp52dPpHFffvOCDupsG0QubkSMEySY= +github.com/mitchellh/mapstructure v0.0.0-20160808181253-ca63d7c062ee/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= +github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= +github.com/mitchellh/mapstructure v1.3.3/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= +github.com/mitchellh/mapstructure v1.4.1/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= +github.com/mitchellh/mapstructure v1.4.2/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= +github.com/mitchellh/mapstructure v1.4.3/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= +github.com/mitchellh/mapstructure v1.5.0 h1:jeMsZIYE/09sWLaz43PL7Gy6RuMjD2eJVyuac5Z2hdY= +github.com/mitchellh/mapstructure v1.5.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= +github.com/mitchellh/osext v0.0.0-20151018003038-5e2d6d41470f/go.mod h1:OkQIRizQZAeMln+1tSwduZz7+Af5oFlKirV/MSYes2A= +github.com/mitchellh/reflectwalk v1.0.0/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw= +github.com/mitchellh/reflectwalk v1.0.1/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw= +github.com/mitchellh/reflectwalk v1.0.2 h1:G2LzWKi524PWgd3mLHV8Y5k7s6XUvT0Gef6zxSIeXaQ= +github.com/mitchellh/reflectwalk v1.0.2/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw= +github.com/moby/locker v1.0.1/go.mod h1:S7SDdo5zpBK84bzzVlKr2V0hz+7x9hWbYC/kq7oQppc= +github.com/moby/spdystream v0.2.0/go.mod h1:f7i0iNDQJ059oMTcWxx8MA/zKFIuD/lY+0GqbN2Wy8c= +github.com/moby/sys/mountinfo v0.4.0/go.mod h1:rEr8tzG/lsIZHBtN/JjGG+LMYx9eXgW2JI+6q0qou+A= +github.com/moby/sys/mountinfo v0.4.1/go.mod h1:rEr8tzG/lsIZHBtN/JjGG+LMYx9eXgW2JI+6q0qou+A= +github.com/moby/sys/symlink v0.1.0/go.mod h1:GGDODQmbFOjFsXvfLVn3+ZRxkch54RkSiGqsZeMYowQ= +github.com/moby/term v0.0.0-20200312100748-672ec06f55cd/go.mod h1:DdlQx2hp0Ss5/fLikoLlEeIYiATotOjgB//nb973jeo= +github.com/moby/term v0.0.0-20210619224110-3f7ff695adc6 h1:dcztxKSvZ4Id8iPpHERQBbIJfabdt4wUm5qy3wOL2Zc= +github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= +github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= +github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= +github.com/modern-go/reflect2 v0.0.0-20180701023420-4b7aa43c6742/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= +github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= +github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= +github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= +github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826/go.mod h1:TaXosZuwdSHYgviHp1DAtfrULt5eUgsSMsZf+YrPgl8= +github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe/go.mod h1:wL8QJuTMNUDYhXwkmfOly8iTdp5TEcJFWZD2D7SIkUc= +github.com/moricho/tparallel v0.2.1/go.mod h1:fXEIZxG2vdfl0ZF8b42f5a78EhjjD5mX8qUplsoSU4k= +github.com/morikuni/aec v1.0.0 h1:nP9CBfwrvYnBRgY6qfDQkygYDmYwOilePFkwzv4dU8A= +github.com/morikuni/aec v1.0.0/go.mod h1:BbKIizmSmc5MMPqRYbxO4ZU0S0+P200+tUnFx7PXmsc= +github.com/mozilla/scribe v0.0.0-20180711195314-fb71baf557c1/go.mod h1:FIczTrinKo8VaLxe6PWTPEXRXDIHz2QAwiaBaP5/4a8= +github.com/mozilla/tls-observatory v0.0.0-20210609171429-7bc42856d2e5/go.mod h1:FUqVoUPHSEdDR0MnFM3Dh8AU0pZHLXUD127SAJGER/s= +github.com/mrunalp/fileutils v0.5.0/go.mod h1:M1WthSahJixYnrXQl/DFQuteStB1weuxD2QJNHXfbSQ= +github.com/munnerz/goautoneg v0.0.0-20120707110453-a547fc61f48d/go.mod h1:+n7T8mK8HuQTcFwEeznm/DIxMOiR9yIdICNftLE1DvQ= +github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822/go.mod h1:+n7T8mK8HuQTcFwEeznm/DIxMOiR9yIdICNftLE1DvQ= +github.com/mwitkow/go-conntrack v0.0.0-20161129095857-cc309e4a2223/go.mod h1:qRWi+5nqEBWmkhHvq77mSJWrCKwh8bxhgT7d/eI7P4U= +github.com/mwitkow/go-conntrack v0.0.0-20190716064945-2f068394615f/go.mod h1:qRWi+5nqEBWmkhHvq77mSJWrCKwh8bxhgT7d/eI7P4U= +github.com/mwitkow/go-proto-validators v0.0.0-20180403085117-0950a7990007/go.mod h1:m2XC9Qq0AlmmVksL6FktJCdTYyLk7V3fKyp0sl1yWQo= +github.com/mwitkow/go-proto-validators v0.2.0/go.mod h1:ZfA1hW+UH/2ZHOWvQ3HnQaU0DtnpXu850MZiy+YUgcc= +github.com/mxk/go-flowrate v0.0.0-20140419014527-cca7078d478f/go.mod h1:ZdcZmHo+o7JKHSa8/e818NopupXU1YMK5fe1lsApnBw= +github.com/nakabonne/nestif v0.3.1/go.mod h1:9EtoZochLn5iUprVDmDjqGKPofoUEBL8U4Ngq6aY7OE= +github.com/nats-io/jwt v0.3.0/go.mod h1:fRYCDE99xlTsqUzISS1Bi75UBJ6ljOJQOAAu5VglpSg= +github.com/nats-io/jwt v0.3.2/go.mod h1:/euKqTS1ZD+zzjYrY7pseZrTtWQSjujC7xjPc8wL6eU= +github.com/nats-io/nats-server/v2 v2.1.2/go.mod h1:Afk+wRZqkMQs/p45uXdrVLuab3gwv3Z8C4HTBu8GD/k= +github.com/nats-io/nats.go v1.9.1/go.mod h1:ZjDU1L/7fJ09jvUSRVBR2e7+RnLiiIQyqyzEE/Zbp4w= +github.com/nats-io/nkeys v0.1.0/go.mod h1:xpnFELMwJABBLVhffcfd1MZx6VsNRFpEugbxziKVo7w= +github.com/nats-io/nkeys v0.1.3/go.mod h1:xpnFELMwJABBLVhffcfd1MZx6VsNRFpEugbxziKVo7w= +github.com/nats-io/nuid v1.0.1/go.mod h1:19wcPz3Ph3q0Jbyiqsd0kePYG7A95tJPxeL+1OSON2c= +github.com/nbutton23/zxcvbn-go v0.0.0-20210217022336-fa2cb2858354/go.mod h1:KSVJerMDfblTH7p5MZaTt+8zaT2iEk3AkVb9PQdZuE8= +github.com/ncw/swift v1.0.47/go.mod h1:23YIA4yWVnGwv2dQlN4bB7egfYX6YLn0Yo/S6zZO/ZM= +github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno= +github.com/nightlyone/lockfile v1.0.0/go.mod h1:rywoIealpdNse2r832aiD9jRk8ErCatROs6LzC841CI= +github.com/nishanths/exhaustive v0.2.3/go.mod h1:bhIX678Nx8inLM9PbpvK1yv6oGtoP8BfaIeMzgBNKvc= +github.com/nishanths/predeclared v0.0.0-20190419143655-18a43bb90ffc/go.mod h1:62PewwiQTlm/7Rj+cxVYqZvDIUc+JjZq6GHAC1fsObQ= +github.com/nishanths/predeclared v0.0.0-20200524104333-86fad755b4d3/go.mod h1:nt3d53pc1VYcphSCIaYAJtnPYnr3Zyn8fMq2wvPGPso= +github.com/nishanths/predeclared v0.2.1/go.mod h1:HvkGJcA3naj4lOwnFXFDkFxVtSqQMB9sbB1usJ+xjQE= +github.com/nwaples/rardecode v1.1.0 h1:vSxaY8vQhOcVr4mm5e8XllHWTiM4JF507A0Katqw7MQ= +github.com/nwaples/rardecode v1.1.0/go.mod h1:5DzqNKiOdpKKBH87u8VlvAnPZMXcGRhxWkRpHbbfGS0= +github.com/nxadm/tail v1.4.4/go.mod h1:kenIhsEOeOJmVchQTgglprH7qJGnHDVpk1VPCcaMI8A= +github.com/nxadm/tail v1.4.8 h1:nPr65rt6Y5JFSKQO7qToXr7pePgD6Gwiw05lkbyAQTE= +github.com/nxadm/tail v1.4.8/go.mod h1:+ncqLTQzXmGhMZNUePPaPqPvBxHAIsmXswZKocGu+AU= +github.com/oklog/oklog v0.3.2/go.mod h1:FCV+B7mhrz4o+ueLpx+KqkyXRGMWOYEvfiXtdGtbWGs= +github.com/oklog/run v1.0.0/go.mod h1:dlhp/R75TPv97u0XWUtDeV/lRKWPKSdTuV0TZvrmrQA= +github.com/oklog/run v1.1.0 h1:GEenZ1cK0+q0+wsJew9qUg/DyD8k3JzYsZAi5gYi2mA= +github.com/oklog/ulid v1.3.1 h1:EGfNDEx6MqHz8B3uNV6QAib1UR2Lm97sHi3ocA6ESJ4= +github.com/oklog/ulid v1.3.1/go.mod h1:CirwcVhetQ6Lv90oh/F+FBtV6XMibvdAFo93nm5qn4U= +github.com/olekukonko/tablewriter v0.0.0-20170122224234-a0225b3f23b5/go.mod h1:vsDQFd/mU46D+Z4whnwzcISnGGzXWMclvtLoiIKAKIo= +github.com/olekukonko/tablewriter v0.0.1/go.mod h1:vsDQFd/mU46D+Z4whnwzcISnGGzXWMclvtLoiIKAKIo= +github.com/olekukonko/tablewriter v0.0.2/go.mod h1:rSAaSIOAGT9odnlyGlUfAJaoc5w2fSBUmeGDbRWPxyQ= +github.com/olekukonko/tablewriter v0.0.4/go.mod h1:zq6QwlOf5SlnkVbMSr5EoBv3636FWnp+qbPhuoO21uA= +github.com/olekukonko/tablewriter v0.0.5 h1:P2Ga83D34wi1o9J6Wh1mRuqd4mF/x/lgBS7N7AbDhec= +github.com/olekukonko/tablewriter v0.0.5/go.mod h1:hPp6KlRPjbx+hW8ykQs1w3UBbZlj6HuIJcUGPhkA7kY= +github.com/onsi/ginkgo v0.0.0-20151202141238-7f8ab55aaf3b/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= +github.com/onsi/ginkgo v0.0.0-20170829012221-11459a886d9c/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= +github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= +github.com/onsi/ginkgo v1.7.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= +github.com/onsi/ginkgo v1.10.1/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= +github.com/onsi/ginkgo v1.10.3/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= +github.com/onsi/ginkgo v1.11.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= +github.com/onsi/ginkgo v1.12.1/go.mod h1:zj2OWP4+oCPe1qIXoGWkgMRwljMUYCdkwsT2108oapk= +github.com/onsi/ginkgo v1.14.0/go.mod h1:iSB4RoI2tjJc9BBv4NKIKWKya62Rps+oPG/Lv9klQyY= +github.com/onsi/ginkgo v1.16.4/go.mod h1:dX+/inL/fNMqNlz0e9LfyB9TswhZpCVdJM/Z6Vvnwo0= +github.com/onsi/ginkgo v1.16.5 h1:8xi0RTUf59SOSfEtZMvwTvXYMzG4gV23XVHOZiXNtnE= +github.com/onsi/gomega v0.0.0-20151007035656-2152b45fa28a/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA= +github.com/onsi/gomega v0.0.0-20170829124025-dcabb60a477c/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA= +github.com/onsi/gomega v1.4.3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= +github.com/onsi/gomega v1.5.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= +github.com/onsi/gomega v1.7.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= +github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY= +github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo= +github.com/onsi/gomega v1.10.3/go.mod h1:V9xEwhxec5O8UDM77eCW8vLymOMltsqPVYWrpDsH8xc= +github.com/onsi/gomega v1.16.0/go.mod h1:HnhC7FXeEQY45zxNK3PPoIUhzk/80Xly9PcubAlGdZY= +github.com/onsi/gomega v1.18.1 h1:M1GfJqGRrBrrGGsbxzV5dqM2U2ApXefZCQpkukxYRLE= +github.com/op/go-logging v0.0.0-20160315200505-970db520ece7/go.mod h1:HzydrMdWErDVzsI23lYNej1Htcns9BCg93Dk0bBINWk= +github.com/opencontainers/go-digest v0.0.0-20170106003457-a6d0ee40d420/go.mod h1:cMLVZDEM3+U2I4VmLI6N8jQYUd2OVphdqWwCJHrFt2s= +github.com/opencontainers/go-digest v0.0.0-20180430190053-c9281466c8b2/go.mod h1:cMLVZDEM3+U2I4VmLI6N8jQYUd2OVphdqWwCJHrFt2s= +github.com/opencontainers/go-digest v1.0.0-rc1/go.mod h1:cMLVZDEM3+U2I4VmLI6N8jQYUd2OVphdqWwCJHrFt2s= +github.com/opencontainers/go-digest v1.0.0-rc1.0.20180430190053-c9281466c8b2/go.mod h1:cMLVZDEM3+U2I4VmLI6N8jQYUd2OVphdqWwCJHrFt2s= +github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8Oi/yOhh5U= +github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM= +github.com/opencontainers/image-spec v1.0.0/go.mod h1:BtxoFyWECRxE4U/7sNtV5W15zMzWCbyJoFRP3s7yZA0= +github.com/opencontainers/image-spec v1.0.1/go.mod h1:BtxoFyWECRxE4U/7sNtV5W15zMzWCbyJoFRP3s7yZA0= +github.com/opencontainers/image-spec v1.0.2-0.20210730191737-8e42a01fb1b7/go.mod h1:BtxoFyWECRxE4U/7sNtV5W15zMzWCbyJoFRP3s7yZA0= +github.com/opencontainers/image-spec v1.0.2/go.mod h1:BtxoFyWECRxE4U/7sNtV5W15zMzWCbyJoFRP3s7yZA0= +github.com/opencontainers/image-spec v1.0.3-0.20220114050600-8b9d41f48198 h1:+czc/J8SlhPKLOtVLMQc+xDCFBT73ZStMsRhSsUhsSg= +github.com/opencontainers/image-spec v1.0.3-0.20220114050600-8b9d41f48198/go.mod h1:j4h1pJW6ZcJTgMZWP3+7RlG3zTaP02aDZ/Qw0sppK7Q= +github.com/opencontainers/runc v0.0.0-20190115041553-12f6a991201f/go.mod h1:qT5XzbpPznkRYVz/mWwUaVBUv2rmF59PVA73FjuZG0U= +github.com/opencontainers/runc v0.1.1/go.mod h1:qT5XzbpPznkRYVz/mWwUaVBUv2rmF59PVA73FjuZG0U= +github.com/opencontainers/runc v1.0.0-rc8.0.20190926000215-3e425f80a8c9/go.mod h1:qT5XzbpPznkRYVz/mWwUaVBUv2rmF59PVA73FjuZG0U= +github.com/opencontainers/runc v1.0.0-rc9/go.mod h1:qT5XzbpPznkRYVz/mWwUaVBUv2rmF59PVA73FjuZG0U= +github.com/opencontainers/runc v1.0.0-rc93/go.mod h1:3NOsor4w32B2tC0Zbl8Knk4Wg84SM2ImC1fxBuqJ/H0= +github.com/opencontainers/runc v1.0.2/go.mod h1:aTaHFFwQXuA71CiyxOdFFIorAoemI04suvGRQFzWTD0= +github.com/opencontainers/runtime-spec v0.1.2-0.20190507144316-5b71a03e2700/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0= +github.com/opencontainers/runtime-spec v1.0.1/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0= +github.com/opencontainers/runtime-spec v1.0.2-0.20190207185410-29686dbc5559/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0= +github.com/opencontainers/runtime-spec v1.0.2/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0= +github.com/opencontainers/runtime-spec v1.0.3-0.20200929063507-e6143ca7d51d/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0= +github.com/opencontainers/runtime-spec v1.0.3-0.20210326190908-1c3f411f0417/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0= +github.com/opencontainers/runtime-tools v0.0.0-20181011054405-1d69bd0f9c39/go.mod h1:r3f7wjNzSs2extwzU3Y+6pKfobzPh+kKFJ3ofN+3nfs= +github.com/opencontainers/selinux v1.6.0/go.mod h1:VVGKuOLlE7v4PJyT6h7mNWvq1rzqiriPsEqVhc+svHE= +github.com/opencontainers/selinux v1.8.0/go.mod h1:RScLhm78qiWa2gbVCcGkC7tCGdgk3ogry1nUQF8Evvo= +github.com/opencontainers/selinux v1.8.2/go.mod h1:MUIHuUEvKB1wtJjQdOyYRgOnLD2xAPP8dBsCoU0KuF8= +github.com/opentracing-contrib/go-observer v0.0.0-20170622124052-a52f23424492/go.mod h1:Ngi6UdF0k5OKD5t5wlmGhe/EDKPoUM3BXZSSfIuJbis= +github.com/opentracing/basictracer-go v1.0.0/go.mod h1:QfBfYuafItcjQuMwinw9GhYKwFXS9KnPs5lxoYwgW74= +github.com/opentracing/opentracing-go v1.0.2/go.mod h1:UkNAQd3GIcIGf0SeVgPpRdFStlNbqXla1AfSYxPUl2o= +github.com/opentracing/opentracing-go v1.1.0/go.mod h1:UkNAQd3GIcIGf0SeVgPpRdFStlNbqXla1AfSYxPUl2o= +github.com/opentracing/opentracing-go v1.2.0 h1:uEJPy/1a5RIPAJ0Ov+OIO8OxWu77jEv+1B0VhjKrZUs= +github.com/opentracing/opentracing-go v1.2.0/go.mod h1:GxEUsuufX4nBwe+T+Wl9TAgYrxe9dPLANfrWvHYVTgc= +github.com/openzipkin-contrib/zipkin-go-opentracing v0.4.5/go.mod h1:/wsWhb9smxSfWAKL3wpBW7V8scJMt8N8gnaMCS9E/cA= +github.com/openzipkin/zipkin-go v0.1.6/go.mod h1:QgAqvLzwWbR/WpD4A3cGpPtJrZXNIiJc5AZX7/PBEpw= +github.com/openzipkin/zipkin-go v0.2.1/go.mod h1:NaW6tEwdmWMaCDZzg8sh+IBNOxHMPnhQw8ySjnjRyN4= +github.com/openzipkin/zipkin-go v0.2.2/go.mod h1:NaW6tEwdmWMaCDZzg8sh+IBNOxHMPnhQw8ySjnjRyN4= +github.com/otiai10/copy v1.2.0/go.mod h1:rrF5dJ5F0t/EWSYODDu4j9/vEeYHMkc8jt0zJChqQWw= +github.com/otiai10/curr v0.0.0-20150429015615-9b4961190c95/go.mod h1:9qAhocn7zKJG+0mI8eUu6xqkFDYS2kb2saOteoSB3cE= +github.com/otiai10/curr v1.0.0/go.mod h1:LskTG5wDwr8Rs+nNQ+1LlxRjAtTZZjtJW4rMXl6j4vs= +github.com/otiai10/mint v1.3.0/go.mod h1:F5AjcsTsWUqX+Na9fpHb52P8pcRX2CI6A3ctIT91xUo= +github.com/otiai10/mint v1.3.1/go.mod h1:/yxELlJQ0ufhjUwhshSj+wFjZ78CnZ48/1wtmBH1OTc= +github.com/pact-foundation/pact-go v1.0.4/go.mod h1:uExwJY4kCzNPcHRj+hCR/HBbOOIwwtUjcrb0b5/5kLM= +github.com/pascaldekloe/goe v0.0.0-20180627143212-57f6aae5913c/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc= +github.com/pborman/uuid v1.2.0/go.mod h1:X/NO0urCmaxf9VXbdlT7C2Yzkj2IKimNn4k+gtPdI/k= +github.com/pelletier/go-buffruneio v0.2.0/go.mod h1:JkE26KsDizTr40EUHkXVtNPvgGtbSNq5BcowyYOWdKo= +github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic= +github.com/pelletier/go-toml v1.7.0/go.mod h1:vwGMzjaWMwyfHwgIBhI2YUM4fB6nL6lVAvS1LBMMhTE= +github.com/pelletier/go-toml v1.8.1/go.mod h1:T2/BmBdy8dvIRq1a/8aqjN41wvWlN4lrapLU/GW4pbc= +github.com/pelletier/go-toml v1.9.3/go.mod h1:u1nR/EPcESfeI/szUZKdtJ0xRNbUoANCkoOuaOx1Y+c= +github.com/pelletier/go-toml v1.9.4/go.mod h1:u1nR/EPcESfeI/szUZKdtJ0xRNbUoANCkoOuaOx1Y+c= +github.com/pelletier/go-toml v1.9.5 h1:4yBQzkHv+7BHq2PQUZF3Mx0IYxG7LsP222s7Agd3ve8= +github.com/pelletier/go-toml v1.9.5/go.mod h1:u1nR/EPcESfeI/szUZKdtJ0xRNbUoANCkoOuaOx1Y+c= +github.com/pelletier/go-toml/v2 v2.0.1 h1:8e3L2cCQzLFi2CR4g7vGFuFxX7Jl1kKX8gW+iV0GUKU= +github.com/pelletier/go-toml/v2 v2.0.1/go.mod h1:r9LEWfGN8R5k0VXJ+0BkIe7MYkRdwZOjgMj2KwnJFUo= +github.com/performancecopilot/speed v3.0.0+incompatible/go.mod h1:/CLtqpZ5gBg1M9iaPbIdPPGyKcA8hKdoy6hAWba7Yac= +github.com/peterbourgon/diskv v2.0.1+incompatible/go.mod h1:uqqh8zWWbv1HBMNONnaR/tNboyR3/BZd58JJSHlUSCU= +github.com/phayes/checkstyle v0.0.0-20170904204023-bfd46e6a821d/go.mod h1:3OzsM7FXDQlpCiw2j81fOmAwQLnZnLGXVKUzeKQXIAw= +github.com/pierrec/lz4 v1.0.2-0.20190131084431-473cd7ce01a1/go.mod h1:3/3N9NVKO0jef7pBehbT1qWhCMrIgbYNnFAZCqQ5LRc= +github.com/pierrec/lz4 v2.0.5+incompatible/go.mod h1:pdkljMzZIN41W+lC3N2tnIh5sFi+IEE17M5jbnwPHcY= +github.com/pierrec/lz4 v2.6.1+incompatible h1:9UY3+iC23yxF0UfGaYrGplQ+79Rg+h/q9FV9ix19jjM= +github.com/pierrec/lz4/v4 v4.1.2/go.mod h1:gZWDp/Ze/IJXGXf23ltt2EXimqmTUXEy0GFuRQyBid4= +github.com/pierrec/lz4/v4 v4.1.15 h1:MO0/ucJhngq7299dKLwIMtgTfbkoSPF6AoMYDd8Q4q0= +github.com/pierrec/lz4/v4 v4.1.15/go.mod h1:gZWDp/Ze/IJXGXf23ltt2EXimqmTUXEy0GFuRQyBid4= +github.com/pkg/diff v0.0.0-20210226163009-20ebb0f2a09e/go.mod h1:pJLUxLENpZxwdsKMEsNbx1VGcRFpLqf3715MtcvvzbA= +github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= +github.com/pkg/errors v0.8.1-0.20171018195549-f15c970de5b7/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= +github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= +github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= +github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= +github.com/pkg/profile v1.2.1/go.mod h1:hJw3o1OdXxsrSjjVksARp5W95eeEaEfptyVZyv6JUPA= +github.com/pkg/sftp v1.10.1/go.mod h1:lYOWFsE0bwd1+KfKJaKeuokY15vzFx25BLbzYYoAxZI= +github.com/pkg/sftp v1.13.1/go.mod h1:3HaPG6Dq1ILlpPZRO0HVMrsydcdLt6HRDccSgb87qRg= +github.com/pmezard/go-difflib v0.0.0-20151028094244-d8ed2627bdf0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= +github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/polyfloyd/go-errorlint v0.0.0-20210722154253-910bb7978349/go.mod h1:wi9BfjxjF/bwiZ701TzmfKu6UKC357IOAtNr0Td0Lvw= +github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI= +github.com/posener/complete v1.2.3/go.mod h1:WZIdtGGp+qx0sLrYKtIRAruyNpv6hFCicSgv7Sy7s/s= +github.com/pquerna/cachecontrol v0.0.0-20171018203845-0dec1b30a021/go.mod h1:prYjPmNq4d1NPVmpShWobRqXY3q7Vp+80DqgxxUrUIA= +github.com/prometheus/client_golang v0.0.0-20180209125602-c332b6f63c06/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw= +github.com/prometheus/client_golang v0.9.1/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw= +github.com/prometheus/client_golang v0.9.3-0.20190127221311-3c4408c8b829/go.mod h1:p2iRAGwDERtqlqzRXnrOVns+ignqQo//hLXqYxZYVNs= +github.com/prometheus/client_golang v0.9.3/go.mod h1:/TN21ttK/J9q6uSwhBd54HahCDft0ttaMvbicHlPoso= +github.com/prometheus/client_golang v1.0.0/go.mod h1:db9x61etRT2tGnBNRi70OPL5FsnadC4Ky3P0J6CfImo= +github.com/prometheus/client_golang v1.1.0/go.mod h1:I1FGZT9+L76gKKOs5djB6ezCbFQP1xR9D75/vuwEF3g= +github.com/prometheus/client_golang v1.3.0/go.mod h1:hJaj2vgQTGQmVCsAACORcieXFeDPbaTKGT+JTgUa3og= +github.com/prometheus/client_golang v1.5.1/go.mod h1:e9GMxYsXl05ICDXkRhurwBS4Q3OK1iX/F2sw+iXX5zU= +github.com/prometheus/client_golang v1.7.1/go.mod h1:PY5Wy2awLA44sXw4AOSfFBetzPP4j5+D6mVACh+pe2M= +github.com/prometheus/client_golang v1.10.0/go.mod h1:WJM3cc3yu7XKBKa/I8WeZm+V3eltZnBwfENSU7mdogU= +github.com/prometheus/client_golang v1.11.0/go.mod h1:Z6t4BnS23TR94PD6BsDNk8yVqroYurpAkEiz0P2BEV0= +github.com/prometheus/client_golang v1.11.1/go.mod h1:Z6t4BnS23TR94PD6BsDNk8yVqroYurpAkEiz0P2BEV0= +github.com/prometheus/client_golang v1.12.1/go.mod h1:3Z9XVyYiZYEO+YQWt3RD2R3jrbd179Rt297l4aS6nDY= +github.com/prometheus/client_golang v1.13.0 h1:b71QUfeo5M8gq2+evJdTPfZhYMAU0uKPkyPJ7TPsloU= +github.com/prometheus/client_golang v1.13.0/go.mod h1:vTeo+zgvILHsnnj/39Ou/1fPN5nJFOEMgftOUOmlvYQ= +github.com/prometheus/client_model v0.0.0-20171117100541-99fa1f4be8e5/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo= +github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo= +github.com/prometheus/client_model v0.0.0-20190115171406-56726106282f/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo= +github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= +github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= +github.com/prometheus/client_model v0.1.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= +github.com/prometheus/client_model v0.2.0 h1:uq5h0d+GuxiXLJLNABMgp2qUWDPiLvgCzz2dUR+/W/M= +github.com/prometheus/client_model v0.2.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= +github.com/prometheus/common v0.0.0-20180110214958-89604d197083/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro= +github.com/prometheus/common v0.0.0-20181113130724-41aa239b4cce/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro= +github.com/prometheus/common v0.2.0/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= +github.com/prometheus/common v0.4.0/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= +github.com/prometheus/common v0.4.1/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= +github.com/prometheus/common v0.6.0/go.mod h1:eBmuwkDJBwy6iBfxCBob6t6dR6ENT/y+J+Zk0j9GMYc= +github.com/prometheus/common v0.7.0/go.mod h1:DjGbpBbp5NYNiECxcL/VnbXCCaQpKd3tt26CguLLsqA= +github.com/prometheus/common v0.9.1/go.mod h1:yhUN8i9wzaXS3w1O07YhxHEBxD+W35wd8bs7vj7HSQ4= +github.com/prometheus/common v0.10.0/go.mod h1:Tlit/dnDKsSWFlCLTWaA1cyBgKHSMdTB80sz/V91rCo= +github.com/prometheus/common v0.18.0/go.mod h1:U+gB1OBLb1lF3O42bTCL+FK18tX9Oar16Clt/msog/s= +github.com/prometheus/common v0.26.0/go.mod h1:M7rCNAaPfAosfx8veZJCuw84e35h3Cfd9VFqTh1DIvc= +github.com/prometheus/common v0.32.1/go.mod h1:vu+V0TpY+O6vW9J44gczi3Ap/oXXR10b+M/gUGO4Hls= +github.com/prometheus/common v0.34.0/go.mod h1:gB3sOl7P0TvJabZpLY5uQMpUqRCPPCyRLCZYc7JZTNE= +github.com/prometheus/common v0.37.0 h1:ccBbHCgIiT9uSoFY0vX8H3zsNR5eLt17/RQLUvn8pXE= +github.com/prometheus/common v0.37.0/go.mod h1:phzohg0JFMnBEFGxTDbfu3QyL5GI8gTQJFhYO5B3mfA= +github.com/prometheus/procfs v0.0.0-20180125133057-cb4147076ac7/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= +github.com/prometheus/procfs v0.0.0-20181005140218-185b4288413d/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= +github.com/prometheus/procfs v0.0.0-20190117184657-bf6a532e95b1/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= +github.com/prometheus/procfs v0.0.0-20190507164030-5867b95ac084/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= +github.com/prometheus/procfs v0.0.0-20190522114515-bc1a522cf7b1/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= +github.com/prometheus/procfs v0.0.2/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= +github.com/prometheus/procfs v0.0.3/go.mod h1:4A/X28fw3Fc593LaREMrKMqOKvUAntwMDaekg4FpcdQ= +github.com/prometheus/procfs v0.0.5/go.mod h1:4A/X28fw3Fc593LaREMrKMqOKvUAntwMDaekg4FpcdQ= +github.com/prometheus/procfs v0.0.8/go.mod h1:7Qr8sr6344vo1JqZ6HhLceV9o3AJ1Ff+GxbHq6oeK9A= +github.com/prometheus/procfs v0.1.3/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU= +github.com/prometheus/procfs v0.2.0/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU= +github.com/prometheus/procfs v0.6.0/go.mod h1:cz+aTbrPOrUb4q7XlbU9ygM+/jj0fzG6c1xBZuNvfVA= +github.com/prometheus/procfs v0.7.3/go.mod h1:cz+aTbrPOrUb4q7XlbU9ygM+/jj0fzG6c1xBZuNvfVA= +github.com/prometheus/procfs v0.8.0 h1:ODq8ZFEaYeCaZOJlZZdJA2AbQR98dSHSM1KW/You5mo= +github.com/prometheus/procfs v0.8.0/go.mod h1:z7EfXMXOkbkqb9IINtpCn86r/to3BnA0uaxHdg830/4= +github.com/prometheus/prometheus v2.5.0+incompatible/go.mod h1:oAIUtOny2rjMX0OWN5vPR5/q/twIROJvdqnQKDdil/s= +github.com/prometheus/tsdb v0.7.1/go.mod h1:qhTCs0VvXwvX/y3TZrWD7rabWM+ijKTux40TwIPHuXU= +github.com/pseudomuto/protoc-gen-doc v1.3.2/go.mod h1:y5+P6n3iGrbKG+9O04V5ld71in3v/bX88wUwgt+U8EA= +github.com/pseudomuto/protoc-gen-doc v1.4.1/go.mod h1:exDTOVwqpp30eV/EDPFLZy3Pwr2sn6hBC1WIYH/UbIg= +github.com/pseudomuto/protoc-gen-doc v1.5.1/go.mod h1:XpMKYg6zkcpgfpCfQ8GcWBDRtRxOmMR5w7pz4Xo+dYM= +github.com/pseudomuto/protokit v0.2.0/go.mod h1:2PdH30hxVHsup8KpBTOXTBeMVhJZVio3Q8ViKSAXT0Q= +github.com/quasilyte/go-consistent v0.0.0-20190521200055-c6f3937de18c/go.mod h1:5STLWrekHfjyYwxBRVRXNOSewLJ3PWfDJd1VyTS21fI= +github.com/quasilyte/go-ruleguard v0.3.1-0.20210203134552-1b5a410e1cc8/go.mod h1:KsAh3x0e7Fkpgs+Q9pNLS5XpFSvYCEVl5gP9Pp1xp30= +github.com/quasilyte/go-ruleguard v0.3.13/go.mod h1:Ul8wwdqR6kBVOCt2dipDBkE+T6vAV/iixkrKuRTN1oQ= +github.com/quasilyte/go-ruleguard/dsl v0.3.0/go.mod h1:KeCP03KrjuSO0H1kTuZQCWlQPulDV6YMIXmpQss17rU= +github.com/quasilyte/go-ruleguard/dsl v0.3.10/go.mod h1:KeCP03KrjuSO0H1kTuZQCWlQPulDV6YMIXmpQss17rU= +github.com/quasilyte/go-ruleguard/rules v0.0.0-20201231183845-9e62ed36efe1/go.mod h1:7JTjp89EGyU1d6XfBiXihJNG37wB2VRkd125Q1u7Plc= +github.com/quasilyte/go-ruleguard/rules v0.0.0-20210428214800-545e0d2e0bf7/go.mod h1:4cgAphtvu7Ftv7vOT2ZOYhC6CvBxZixcasr8qIOTA50= +github.com/quasilyte/regex/syntax v0.0.0-20200407221936-30656e2c4a95/go.mod h1:rlzQ04UMyJXu/aOvhd8qT+hvDrFpiwqp8MRXDY9szc0= +github.com/qur/ar v0.0.0-20130629153254-282534b91770/go.mod h1:SjlYv2m9lpV0UW6K7lDqVJwEIIvSjaHbGk7nIfY8Hxw= +github.com/rcrowley/go-metrics v0.0.0-20181016184325-3113b8401b8a/go.mod h1:bCqnVzQkZxMG4s8nGwiZ5l3QUCyqpo9Y+/ZMZ9VjZe4= +github.com/remyoudompheng/bigfft v0.0.0-20200410134404-eec4a21b6bb0 h1:OdAsTTz6OkFY5QxjkYwrChwuRruF69c169dPK26NUlk= +github.com/remyoudompheng/bigfft v0.0.0-20200410134404-eec4a21b6bb0/go.mod h1:qqbHyh8v60DhA7CoWK5oRCqLrMHRGoxYCSS9EjAz6Eo= +github.com/rivo/uniseg v0.2.0 h1:S1pD9weZBuJdFmowNwbpi7BJ8TNftyUImj/0WQi72jY= +github.com/rivo/uniseg v0.2.0/go.mod h1:J6wj4VEh+S6ZtnVlnTBMWIodfgj8LQOQFoIToxlJtxc= +github.com/rogpeppe/fastuuid v0.0.0-20150106093220-6724a57986af/go.mod h1:XWv6SoW27p1b0cqNHllgS5HIMJraePCO15w5zCzIWYg= +github.com/rogpeppe/fastuuid v1.1.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6LYCDYWNEvQ= +github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6LYCDYWNEvQ= +github.com/rogpeppe/go-internal v1.1.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= +github.com/rogpeppe/go-internal v1.2.2/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= +github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= +github.com/rogpeppe/go-internal v1.6.1/go.mod h1:xXDCJY+GAPziupqXw64V24skbSoqbTEfhy4qGm1nDQc= +github.com/rogpeppe/go-internal v1.6.2/go.mod h1:xXDCJY+GAPziupqXw64V24skbSoqbTEfhy4qGm1nDQc= +github.com/rogpeppe/go-internal v1.8.0 h1:FCbCCtXNOY3UtUuHUYaghJg4y7Fd14rXifAYUAtL9R8= +github.com/rogpeppe/go-internal v1.8.0/go.mod h1:WmiCO8CzOY8rg0OYDC4/i/2WRWAB6poM+XZ2dLUbcbE= +github.com/rs/cors v1.7.0/go.mod h1:gFx+x8UowdsKA9AchylcLynDq+nNFfI8FkUZdN/jGCU= +github.com/rs/cors v1.8.2/go.mod h1:XyqrcTp5zjWr1wsJ8PIRZssZ8b/WMcMf71DJnit4EMU= +github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g= +github.com/russross/blackfriday v1.6.0/go.mod h1:ti0ldHuxg49ri4ksnFxlkCfN+hvslNlmVHqNRXXJNAY= +github.com/russross/blackfriday/v2 v2.0.1/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= +github.com/russross/blackfriday/v2 v2.1.0 h1:JIOH55/0cWyOuilr9/qlrm0BSXldqnqwMsf35Ld67mk= +github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= +github.com/ryancurrah/gomodguard v1.2.3/go.mod h1:rYbA/4Tg5c54mV1sv4sQTP5WOPBcoLtnBZ7/TEhXAbg= +github.com/ryanrolds/sqlclosecheck v0.3.0/go.mod h1:1gREqxyTGR3lVtpngyFo3hZAgk0KCtEdgEkHwDbigdA= +github.com/ryanuber/columnize v0.0.0-20160712163229-9b3edd62028f/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts= +github.com/ryanuber/go-glob v1.0.0 h1:iQh3xXAumdQ+4Ufa5b25cRpC5TYKlno6hsv6Cb3pkBk= +github.com/safchain/ethtool v0.0.0-20190326074333-42ed695e3de8/go.mod h1:Z0q5wiBQGYcxhMZ6gUqHn6pYNLypFAvaL3UvgZLR0U4= +github.com/sagikazarmark/crypt v0.1.0/go.mod h1:B/mN0msZuINBtQ1zZLEQcegFJJf9vnYIR88KRMEuODE= +github.com/samuel/go-zookeeper v0.0.0-20190923202752-2cc03de413da/go.mod h1:gi+0XIa01GRL2eRQVjQkKGqKF3SF9vZR/HnPullcV2E= +github.com/sanposhiho/wastedassign/v2 v2.0.6/go.mod h1:KyZ0MWTwxxBmfwn33zh3k1dmsbF2ud9pAAGfoLfjhtI= +github.com/sassoftware/go-rpmutils v0.0.0-20190420191620-a8f1baeba37b/go.mod h1:am+Fp8Bt506lA3Rk3QCmSqmYmLMnPDhdDUcosQCAx+I= +github.com/sassoftware/go-rpmutils v0.1.1/go.mod h1:euhXULoBpvAxqrBHEyJS4Tsu3hHxUmQWNymxoJbzgUY= +github.com/sassoftware/go-rpmutils v0.2.0 h1:pKW0HDYMFWQ5b4JQPiI3WI12hGsVoW0V8+GMoZiI/JE= +github.com/sassoftware/go-rpmutils v0.2.0/go.mod h1:TJJQYtLe/BeEmEjelI3b7xNZjzAukEkeWKmoakvaOoI= +github.com/sassoftware/relic v0.0.0-20210427151427-dfb082b79b74 h1:sUNzanSKA9z/h8xXl+ZJoxIYZL0Qx306MmxqRrvUgr0= +github.com/sassoftware/relic v0.0.0-20210427151427-dfb082b79b74/go.mod h1:YlB8wFIZmFLZ1JllNBfSURzz52fBxbliNgYALk1UDmk= +github.com/satori/go.uuid v1.2.0/go.mod h1:dA0hQrYB0VpLJoorglMZABFdXlWrHn1NEOzdhQKdks0= +github.com/scylladb/go-set v1.0.3-0.20200225121959-cc7b2070d91e h1:7q6NSFZDeGfvvtIRwBrU/aegEYJYmvev0cHAwo17zZQ= +github.com/scylladb/go-set v1.0.3-0.20200225121959-cc7b2070d91e/go.mod h1:DkpGd78rljTxKAnTDPFqXSGxvETQnJyuSOQwsHycqfs= +github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529/go.mod h1:DxrIzT+xaE7yg65j358z/aeFdxmN0P9QXhEzd20vsDc= +github.com/sebdah/goldie/v2 v2.5.3 h1:9ES/mNN+HNUbNWpVAlrzuZ7jE+Nrczbj8uFRjM7624Y= +github.com/sebdah/goldie/v2 v2.5.3/go.mod h1:oZ9fp0+se1eapSRjfYbsV/0Hqhbuu3bJVvKI/NNtssI= +github.com/seccomp/libseccomp-golang v0.9.1/go.mod h1:GbW5+tmTXfcxTToHLXlScSlAvWlF4P2Ca7zGrPiEpWo= +github.com/secure-systems-lab/go-securesystemslib v0.4.0 h1:b23VGrQhTA8cN2CbBw7/FulN9fTtqYUdS5+Oxzt+DUE= +github.com/secure-systems-lab/go-securesystemslib v0.4.0/go.mod h1:FGBZgq2tXWICsxWQW1msNf49F0Pf2Op5Htayx335Qbs= +github.com/securego/gosec/v2 v2.9.1/go.mod h1:oDcDLcatOJxkCGaCaq8lua1jTnYf6Sou4wdiJ1n4iHc= +github.com/segmentio/ksuid v1.0.4 h1:sBo2BdShXjmcugAMwjugoGUdUV0pcxY5mW4xKRn3v4c= +github.com/segmentio/ksuid v1.0.4/go.mod h1:/XUiZBD3kVx5SmUOl55voK5yeAbBNNIed+2O73XgrPE= +github.com/sergi/go-diff v1.0.0/go.mod h1:0CfEIISq7TuYL3j771MWULgwwjU+GofnZX9QAmXWZgo= +github.com/sergi/go-diff v1.1.0/go.mod h1:STckp+ISIX8hZLjrqAeVduY0gWCT9IjLuqbuNXdaHfM= +github.com/sergi/go-diff v1.2.0 h1:XU+rvMAioB0UC3q1MFrIQy4Vo5/4VsRDQQXHsEya6xQ= +github.com/sergi/go-diff v1.2.0/go.mod h1:STckp+ISIX8hZLjrqAeVduY0gWCT9IjLuqbuNXdaHfM= +github.com/shazow/go-diff v0.0.0-20160112020656-b6b7b6733b8c/go.mod h1:/PevMnwAxekIXwN8qQyfc5gl2NlkB3CQlkizAbOkeBs= +github.com/shibumi/go-pathspec v1.3.0 h1:QUyMZhFo0Md5B8zV8x2tesohbb5kfbpTi9rBnKh5dkI= +github.com/shibumi/go-pathspec v1.3.0/go.mod h1:Xutfslp817l2I1cZvgcfeMQJG5QnU2lh5tVaaMCl3jE= +github.com/shirou/gopsutil/v3 v3.21.10/go.mod h1:t75NhzCZ/dYyPQjyQmrAYP6c8+LCdFANeBMdLPCNnew= +github.com/shopspring/decimal v1.2.0 h1:abSATXmQEYyShuxI4/vyW3tV1MrKAJzCZ/0zLUXYbsQ= +github.com/shopspring/decimal v1.2.0/go.mod h1:DKyhrW/HYNuLGql+MJL6WCR6knT2jwCFRcu2hWCYk4o= +github.com/shurcooL/go v0.0.0-20180423040247-9e1955d9fb6e/go.mod h1:TDJrrUr11Vxrven61rcy3hJMUqaf/CLWYhHNPmT14Lk= +github.com/shurcooL/go-goon v0.0.0-20170922171312-37c2f522c041/go.mod h1:N5mDOmsrJOB+vfqUK+7DmDyjhSLIIBnXo9lvZJj3MWQ= +github.com/shurcooL/sanitized_anchor_name v1.0.0/go.mod h1:1NzhyTcUVG4SuEtjjoZeVRXNmyL/1OwPU0+IJeTBvfc= +github.com/sigstore/cosign v1.11.1 h1:y9IlANx0kTe5bt4wVkauJkfgWjMwmFId1H2y782hXmc= +github.com/sigstore/cosign v1.11.1/go.mod h1:PURIOXUUu1KmXTJ1x11DHH/X9CyaoYpa9AxRphagu+s= +github.com/sigstore/fulcio v0.5.3 h1:fwdl2BHv1RjL3GJJ44T+tPsvmQ028zv54psxVhSwUGA= +github.com/sigstore/fulcio v0.5.3/go.mod h1:4yzMqOao6r9Nul1Dgt4LL7loKdkkgbDemLYrXUuAc+Y= +github.com/sigstore/rekor v0.11.0 h1:2x1Sy3fu3VSWbl/2fwTyFPqs5fehY++EqdTFWWT6+Mo= +github.com/sigstore/rekor v0.11.0/go.mod h1:xEfHnfiQJ/yJVCz41/OglUrDID71gICzixJjYFrQeN0= +github.com/sigstore/sigstore v1.4.0 h1:5A3eUhbSQkhiqJNUPi/2UMKdTyb3NKfWcVjaTBkkaJk= +github.com/sigstore/sigstore v1.4.0/go.mod h1:z3kt1jm2A39M+g7emkQ8jdErL/haCMEjkNxvqTf41/k= +github.com/sirupsen/logrus v1.0.4-0.20170822132746-89742aefa4b2/go.mod h1:pMByvHTf9Beacp5x1UXfOR9xyW/9antXMhjMPG0dEzc= +github.com/sirupsen/logrus v1.0.6/go.mod h1:pMByvHTf9Beacp5x1UXfOR9xyW/9antXMhjMPG0dEzc= +github.com/sirupsen/logrus v1.2.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo= +github.com/sirupsen/logrus v1.3.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo= +github.com/sirupsen/logrus v1.4.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo= +github.com/sirupsen/logrus v1.4.1/go.mod h1:ni0Sbl8bgC9z8RoU9G6nDWqqs/fq4eDPysMBDgk/93Q= +github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE= +github.com/sirupsen/logrus v1.6.0/go.mod h1:7uNnSEd1DgxDLC74fIahvMZmmYsHGZGEOFrfsX/uA88= +github.com/sirupsen/logrus v1.7.0/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= +github.com/sirupsen/logrus v1.8.1/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= +github.com/sirupsen/logrus v1.9.0 h1:trlNQbNUG3OdDrDil03MCb1H2o9nJ1x4/5LYw7byDE0= +github.com/sirupsen/logrus v1.9.0/go.mod h1:naHLuLoDiP4jHNo9R0sCBMtWGeIprob74mVsIT4qYEQ= +github.com/sivchari/tenv v1.4.7/go.mod h1:5nF+bITvkebQVanjU6IuMbvIot/7ReNsUV7I5NbprB0= +github.com/skratchdot/open-golang v0.0.0-20200116055534-eef842397966 h1:JIAuq3EEf9cgbU6AtGPK4CTG3Zf6CKMNqf0MHTggAUA= +github.com/skratchdot/open-golang v0.0.0-20200116055534-eef842397966/go.mod h1:sUM3LWHvSMaG192sy56D9F7CNvL7jUJVXoqM1QKLnog= +github.com/smartystreets/assertions v0.0.0-20180927180507-b2de0cb4f26d/go.mod h1:OnSkiWE9lh6wB0YB77sQom3nweQdgAjqCqsofrRNTgc= +github.com/smartystreets/assertions v1.0.0/go.mod h1:kHHU4qYBaI3q23Pp3VPrmWhuIUrLW/7eUrw0BU5VaoM= +github.com/smartystreets/go-aws-auth v0.0.0-20180515143844-0c1422d1fdb9/go.mod h1:SnhjPscd9TpLiy1LpzGSKh3bXCfxxXuqd9xmQJy3slM= +github.com/smartystreets/goconvey v0.0.0-20190330032615-68dc04aab96a/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA= +github.com/smartystreets/goconvey v1.6.4/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA= +github.com/smartystreets/gunit v1.0.0/go.mod h1:qwPWnhz6pn0NnRBP++URONOVyNkPyr4SauJk4cUOwJs= +github.com/soheilhy/cmux v0.1.4/go.mod h1:IM3LyeVVIOuxMH7sFAkER9+bJ4dT7Ms6E4xg4kGIyLM= +github.com/soheilhy/cmux v0.1.5-0.20210205191134-5ec6847320e5/go.mod h1:T7TcVDs9LWfQgPlPsdngu6I6QIoyIFZDDC6sNE1GqG0= +github.com/soheilhy/cmux v0.1.5 h1:jjzc5WVemNEDTLwv9tlmemhC73tI08BNOIGwBOo10Js= +github.com/soheilhy/cmux v0.1.5/go.mod h1:T7TcVDs9LWfQgPlPsdngu6I6QIoyIFZDDC6sNE1GqG0= +github.com/sonatard/noctx v0.0.1/go.mod h1:9D2D/EoULe8Yy2joDHJj7bv3sZoq9AaSb8B4lqBjiZI= +github.com/sony/gobreaker v0.4.1/go.mod h1:ZKptC7FHNvhBz7dN2LGjPVBz2sZJmc0/PkyDJOjmxWY= +github.com/sourcegraph/go-diff v0.6.1/go.mod h1:iBszgVvyxdc8SFZ7gm69go2KDdt3ag071iBaWPF6cjs= +github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= +github.com/spdx/gordf v0.0.0-20201111095634-7098f93598fb/go.mod h1:uKWaldnbMnjsSAXRurWqqrdyZen1R7kxl8TkmWk2OyM= +github.com/spdx/tools-golang v0.2.0 h1:KBNcw7xvVycRWeCWZK/5xQJA+plymW1+rTCs8ekJDro= +github.com/spdx/tools-golang v0.2.0/go.mod h1:RO4Y3IFROJnz+43JKm1YOrbtgQNljW4gAPpA/sY2eqo= +github.com/spf13/afero v1.1.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B0CQ= +github.com/spf13/afero v1.2.2/go.mod h1:9ZxEEn6pIJ8Rxe320qSDBk6AsU0r9pR7Q4OcevTdifk= +github.com/spf13/afero v1.3.3/go.mod h1:5KUK8ByomD5Ti5Artl0RtHeI5pTF7MIDuXL3yY520V4= +github.com/spf13/afero v1.4.1/go.mod h1:Ai8FlHk4v/PARR026UzYexafAt9roJ7LcLMAmO6Z93I= +github.com/spf13/afero v1.6.0/go.mod h1:Ai8FlHk4v/PARR026UzYexafAt9roJ7LcLMAmO6Z93I= +github.com/spf13/afero v1.8.2 h1:xehSyVa0YnHWsJ49JFljMpg1HX19V6NDZ1fkm1Xznbo= +github.com/spf13/afero v1.8.2/go.mod h1:CtAatgMJh6bJEIs48Ay/FOnkljP3WeGUG0MC1RfAqwo= +github.com/spf13/cast v1.3.0/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE= +github.com/spf13/cast v1.3.1/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE= +github.com/spf13/cast v1.4.1/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE= +github.com/spf13/cast v1.5.0 h1:rj3WzYc11XZaIZMPKmwP96zkFEnnAmV8s6XbB2aY32w= +github.com/spf13/cast v1.5.0/go.mod h1:SpXXQ5YoyJw6s3/6cMTQuxvgRl3PCJiyaX9p6b155UU= +github.com/spf13/cobra v0.0.2-0.20171109065643-2da4a54c5cee/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ= +github.com/spf13/cobra v0.0.3/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ= +github.com/spf13/cobra v0.0.5/go.mod h1:3K3wKZymM7VvHMDS9+Akkh4K60UwM26emMESw8tLCHU= +github.com/spf13/cobra v1.0.0/go.mod h1:/6GTrnGXV9HjY+aR4k0oJ5tcvakLuG6EuKReYlHNrgE= +github.com/spf13/cobra v1.1.1/go.mod h1:WnodtKOvamDL/PwE2M4iKs8aMDBZ5Q5klgD3qfVJQMI= +github.com/spf13/cobra v1.1.3/go.mod h1:pGADOWyqRD/YMrPZigI/zbliZ2wVD/23d+is3pSWzOo= +github.com/spf13/cobra v1.2.1/go.mod h1:ExllRjgxM/piMAM+3tAZvg8fsklGAf3tPfi+i8t68Nk= +github.com/spf13/cobra v1.4.0/go.mod h1:Wo4iy3BUC+X2Fybo0PDqwJIv3dNRiZLHQymsfxlB84g= +github.com/spf13/cobra v1.5.0 h1:X+jTBEBqF0bHN+9cSMgmfuvv2VHJ9ezmFNf9Y/XstYU= +github.com/spf13/cobra v1.5.0/go.mod h1:dWXEIy2H428czQCjInthrTRUg7yKbok+2Qi/yBIJoUM= +github.com/spf13/jwalterweatherman v1.0.0/go.mod h1:cQK4TGJAtQXfYWX+Ddv3mKDzgVb68N+wFjFa4jdeBTo= +github.com/spf13/jwalterweatherman v1.1.0 h1:ue6voC5bR5F8YxI5S67j9i582FU4Qvo2bmqnqMYADFk= +github.com/spf13/jwalterweatherman v1.1.0/go.mod h1:aNWZUN0dPAAO/Ljvb5BEdw96iTZ0EXowPYD95IqWIGo= +github.com/spf13/pflag v0.0.0-20170130214245-9ff6c6923cff/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= +github.com/spf13/pflag v1.0.1-0.20171106142849-4c012f6dcd95/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= +github.com/spf13/pflag v1.0.1/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= +github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= +github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA= +github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= +github.com/spf13/viper v1.3.2/go.mod h1:ZiWeW+zYFKm7srdB9IoDzzZXaJaI5eL9QjNiN/DMA2s= +github.com/spf13/viper v1.4.0/go.mod h1:PTJ7Z/lr49W6bUbkmS1V3by4uWynFiR9p7+dSq/yZzE= +github.com/spf13/viper v1.7.0/go.mod h1:8WkrPz2fc9jxqZNCJI/76HCieCp4Q8HaLFoCha5qpdg= +github.com/spf13/viper v1.7.1/go.mod h1:8WkrPz2fc9jxqZNCJI/76HCieCp4Q8HaLFoCha5qpdg= +github.com/spf13/viper v1.8.1/go.mod h1:o0Pch8wJ9BVSWGQMbra6iw0oQ5oktSIBaujf1rJH9Ns= +github.com/spf13/viper v1.9.0/go.mod h1:+i6ajR7OX2XaiBkrcZJFK21htRk7eDeLg7+O6bhUPP4= +github.com/spf13/viper v1.12.0 h1:CZ7eSOd3kZoaYDLbXnmzgQI5RlciuXBMA+18HwHRfZQ= +github.com/spf13/viper v1.12.0/go.mod h1:b6COn30jlNxbm/V2IqWiNWkJ+vZNiMNksliPCiuKtSI= +github.com/spiffe/go-spiffe/v2 v2.1.1 h1:RT9kM8MZLZIsPTH+HKQEP5yaAk3yd/VBzlINaRjXs8k= +github.com/spiffe/go-spiffe/v2 v2.1.1/go.mod h1:5qg6rpqlwIub0JAiF1UK9IMD6BpPTmvG6yfSgDBs5lg= +github.com/src-d/gcfg v1.4.0/go.mod h1:p/UMsR43ujA89BJY9duynAwIpvqEujIH/jFlfL7jWoI= +github.com/ssgreg/nlreturn/v2 v2.2.1/go.mod h1:E/iiPB78hV7Szg2YfRgyIrk1AD6JVMTRkkxBiELzh2I= +github.com/stefanberger/go-pkcs11uri v0.0.0-20201008174630-78d3cae3a980/go.mod h1:AO3tvPzVZ/ayst6UlUKUv6rcPQInYe3IknH3jYhAKu8= +github.com/stoewer/go-strcase v1.2.0/go.mod h1:IBiWB2sKIp3wVVQ3Y035++gc+knqhUQag1KpM8ahLw8= +github.com/streadway/amqp v0.0.0-20190404075320-75d898a42a94/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= +github.com/streadway/amqp v0.0.0-20190827072141-edfb9018d271/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= +github.com/streadway/amqp v1.0.0/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= +github.com/streadway/handy v0.0.0-20190108123426-d5acb3125c2a/go.mod h1:qNTQ5P5JnDBl6z3cMAg/SywNDC5ABu5ApDIw6lUbRmI= +github.com/stretchr/objx v0.0.0-20180129172003-8a3f7159479f/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/objx v0.2.0/go.mod h1:qt09Ya8vawLte6SNmTgCsAVtYtaKzEcn8ATUoHMkEqE= +github.com/stretchr/objx v0.4.0 h1:M2gUjqZET1qApGOWNSnZ49BAIMX4F/1plDv3+l31EJ4= +github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw= +github.com/stretchr/testify v0.0.0-20170130113145-4d4bfba8f1d1/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= +github.com/stretchr/testify v0.0.0-20180303142811-b89eecf5ca5d/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= +github.com/stretchr/testify v1.1.4/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= +github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= +github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= +github.com/stretchr/testify v1.3.1-0.20190311161405-34c6fa2dc709/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= +github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= +github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= +github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.8.0 h1:pSgiaMZlXftHpm5L7V1+rVB+AZJydKsMxsQBIJw4PKk= +github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU= +github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69rRypqCw= +github.com/subosito/gotenv v1.3.0 h1:mjC+YW8QpAdXibNi+vNWgzmgBH4+5l5dCXv8cNysBLI= +github.com/subosito/gotenv v1.3.0/go.mod h1:YzJjq/33h7nrwdY+iHMhEOEEbW0ovIz0tB6t6PwAXzs= +github.com/sylabs/sif/v2 v2.7.2 h1:eCxtl2ub9fPfrO7g2JPagn6HKDhv+Kl92Jz6+ww2Y1Q= +github.com/sylabs/sif/v2 v2.7.2/go.mod h1:LQOdYXC9a8i7BleTKRw9lohi0rTbXkJOeS9u0ebvgyM= +github.com/sylabs/squashfs v0.6.1 h1:4hgvHnD9JGlYWwT0bPYNt9zaz23mAV3Js+VEgQoRGYQ= +github.com/sylabs/squashfs v0.6.1/go.mod h1:ZwpbPCj0ocIvMy2br6KZmix6Gzh6fsGQcCnydMF+Kx8= +github.com/sylvia7788/contextcheck v1.0.4/go.mod h1:vuPKJMQ7MQ91ZTqfdyreNKwZjyUg6KO+IebVyQDedZQ= +github.com/syndtr/gocapability v0.0.0-20170704070218-db04d3cc01c8/go.mod h1:hkRG7XYTFWNJGYcbNJQlaLq0fg1yr4J4t/NcTQtrfww= +github.com/syndtr/gocapability v0.0.0-20180916011248-d98352740cb2/go.mod h1:hkRG7XYTFWNJGYcbNJQlaLq0fg1yr4J4t/NcTQtrfww= +github.com/syndtr/gocapability v0.0.0-20200815063812-42c35b437635/go.mod h1:hkRG7XYTFWNJGYcbNJQlaLq0fg1yr4J4t/NcTQtrfww= +github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 h1:epCh84lMvA70Z7CTTCmYQn2CKbY8j86K7/FAIr141uY= +github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7/go.mod h1:q4W45IWZaF22tdD+VEXcAWRA037jwmWEB5VWYORlTpc= +github.com/tchap/go-patricia v2.2.6+incompatible/go.mod h1:bmLyhP68RS6kStMGxByiQ23RP/odRBOTVjwp2cDyi6I= +github.com/tdakkota/asciicheck v0.0.0-20200416200610-e657995f937b/go.mod h1:yHp0ai0Z9gUljN3o0xMhYJnH/IcvkdTBOX2fmJ93JEM= +github.com/tenntenn/modver v1.0.1/go.mod h1:bePIyQPb7UeioSRkw3Q0XeMhYZSMx9B8ePqg6SAMGH0= +github.com/tenntenn/text/transform v0.0.0-20200319021203-7eef512accb3/go.mod h1:ON8b8w4BN/kE1EOhwT0o+d62W65a6aPw1nouo9LMgyY= +github.com/tent/canonical-json-go v0.0.0-20130607151641-96e4ba3a7613 h1:iGnD/q9160NWqKZZ5vY4p0dMiYMRknzctfSkqA4nBDw= +github.com/tent/canonical-json-go v0.0.0-20130607151641-96e4ba3a7613/go.mod h1:g6AnIpDSYMcphz193otpSIzN+11Rs+AAIIC6rm1enug= +github.com/tetafro/godot v1.4.11/go.mod h1:LR3CJpxDVGlYOWn3ZZg1PgNZdTUvzsZWu8xaEohUpn8= +github.com/thales-e-security/pool v0.0.2 h1:RAPs4q2EbWsTit6tpzuvTFlgFRJ3S8Evf5gtvVDbmPg= +github.com/thales-e-security/pool v0.0.2/go.mod h1:qtpMm2+thHtqhLzTwgDBj/OuNnMpupY8mv0Phz0gjhU= +github.com/therootcompany/xz v1.0.1 h1:CmOtsn1CbtmyYiusbfmhmkpAAETj0wBIH6kCYaX+xzw= +github.com/therootcompany/xz v1.0.1/go.mod h1:3K3UH1yCKgBneZYhuQUvJ9HPD19UEXEI0BWbMn8qNMY= +github.com/theupdateframework/go-tuf v0.3.1 h1:NkjMlCuLcDpHNtsWXY4lTmbbQQ5nOM7JSBbOKEEiI1c= +github.com/theupdateframework/go-tuf v0.3.1/go.mod h1:lhHZ3Vt2pdAh15h0Cc6gWdlI+Okn2ZznD3q/cNjd5jw= +github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk= +github.com/tidwall/pretty v1.2.0 h1:RWIZEg2iJ8/g6fDDYzMpobmaoGh5OLl4AXtGUGPcqCs= +github.com/timakin/bodyclose v0.0.0-20200424151742-cb6215831a94/go.mod h1:Qimiffbc6q9tBWlVV6x0P9sat/ao1xEkREYPPj9hphk= +github.com/titanous/rocacheck v0.0.0-20171023193734-afe73141d399 h1:e/5i7d4oYZ+C1wj2THlRK+oAhjeS/TRQwMfkIuet3w0= +github.com/titanous/rocacheck v0.0.0-20171023193734-afe73141d399/go.mod h1:LdwHTNJT99C5fTAzDz0ud328OgXz+gierycbcIx2fRs= +github.com/tj/assert v0.0.0-20171129193455-018094318fb0/go.mod h1:mZ9/Rh9oLWpLLDRpvE+3b7gP/C2YyLFYxNmcLnPTMe0= +github.com/tj/go-elastic v0.0.0-20171221160941-36157cbbebc2/go.mod h1:WjeM0Oo1eNAjXGDx2yma7uG2XoyRZTq1uv3M/o7imD0= +github.com/tj/go-kinesis v0.0.0-20171128231115-08b17f58cb1b/go.mod h1:/yhzCV0xPfx6jb1bBgRFjl5lytqVqZXEaeqWP8lTEao= +github.com/tj/go-spin v1.1.0/go.mod h1:Mg1mzmePZm4dva8Qz60H2lHwmJ2loum4VIrLgVnKwh4= +github.com/tklauser/go-sysconf v0.3.9/go.mod h1:11DU/5sG7UexIrp/O6g35hrWzu0JxlwQ3LSFUzyeuhs= +github.com/tklauser/numcpus v0.3.0/go.mod h1:yFGUr7TUHQRAhyqBcEg0Ge34zDBAsIvJJcyE6boqnA8= +github.com/tmc/grpc-websocket-proxy v0.0.0-20170815181823-89b8d40f7ca8/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= +github.com/tmc/grpc-websocket-proxy v0.0.0-20190109142713-0ad062ec5ee5/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= +github.com/tmc/grpc-websocket-proxy v0.0.0-20200427203606-3cfed13b9966/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= +github.com/tmc/grpc-websocket-proxy v0.0.0-20201229170055-e5319fda7802 h1:uruHq4dN7GR16kFc5fp3d1RIYzJW5onx8Ybykw2YQFA= +github.com/tmc/grpc-websocket-proxy v0.0.0-20201229170055-e5319fda7802/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= +github.com/tomarrell/wrapcheck/v2 v2.4.0/go.mod h1:68bQ/eJg55BROaRTbMjC7vuhL2OgfoG8bLp9ZyoBfyY= +github.com/tomasen/realip v0.0.0-20180522021738-f0c99a92ddce/go.mod h1:o8v6yHRoik09Xen7gje4m9ERNah1d1PPsVq1VEx9vE4= +github.com/tommy-muehle/go-mnd/v2 v2.4.0/go.mod h1:WsUAkMJMYww6l/ufffCD3m+P7LEvr8TnZn9lwVDlgzw= +github.com/transparency-dev/merkle v0.0.1 h1:T9/9gYB8uZl7VOJIhdwjALeRWlxUxSfDEysjfmx+L9E= +github.com/transparency-dev/merkle v0.0.1/go.mod h1:B8FIw5LTq6DaULoHsVFRzYIUDkl8yuSwCdZnOZGKL/A= +github.com/ugorji/go v1.1.4/go.mod h1:uQMGLiO92mf5W77hV/PUCpI3pbzQx3CRekS0kk+RGrc= +github.com/ugorji/go/codec v0.0.0-20181204163529-d75b2dcb6bc8/go.mod h1:VFNgLljTbGfSG7qAOspJ7OScBnGdDN/yBr0sguwnwf0= +github.com/ulikunitz/xz v0.5.6/go.mod h1:2bypXElzHzzJZwzH67Y6wb67pO62Rzfn7BSiF4ABRW8= +github.com/ulikunitz/xz v0.5.7/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0oWt/14= +github.com/ulikunitz/xz v0.5.8/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0oWt/14= +github.com/ulikunitz/xz v0.5.9/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0oWt/14= +github.com/ulikunitz/xz v0.5.10 h1:t92gobL9l3HE202wg3rlk19F6X+JOxl9BBrCCMYEYd8= +github.com/ulikunitz/xz v0.5.10/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0oWt/14= +github.com/ultraware/funlen v0.0.3/go.mod h1:Dp4UiAus7Wdb9KUZsYWZEWiRzGuM2kXM1lPbfaF6xhA= +github.com/ultraware/whitespace v0.0.4/go.mod h1:aVMh/gQve5Maj9hQ/hg+F75lr/X5A89uZnzAmWSineA= +github.com/urfave/cli v0.0.0-20171014202726-7bc6a0acffa5/go.mod h1:70zkFmudgCuE/ngEzBv17Jvp/497gISqfk5gWijbERA= +github.com/urfave/cli v1.20.0/go.mod h1:70zkFmudgCuE/ngEzBv17Jvp/497gISqfk5gWijbERA= +github.com/urfave/cli v1.22.1/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= +github.com/urfave/cli v1.22.2/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= +github.com/urfave/cli v1.22.4/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= +github.com/urfave/cli v1.22.7 h1:aXiFAgRugfJ27UFDsGJ9DB2FvTC73hlVXFSqq5bo9eU= +github.com/urfave/cli v1.22.7/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= +github.com/uudashr/gocognit v1.0.5/go.mod h1:wgYz0mitoKOTysqxTDMOUXg+Jb5SvtihkfmugIZYpEA= +github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyCJ6HpOuEn7z0Csc= +github.com/valyala/fasthttp v1.30.0/go.mod h1:2rsYD01CKFrjjsvFxx75KlEUNpWNBY9JWD3K/7o2Cus= +github.com/valyala/quicktemplate v1.7.0/go.mod h1:sqKJnoaOF88V07vkO+9FL8fb9uZg/VPSJnLYn+LmLk8= +github.com/valyala/tcplisten v1.0.0/go.mod h1:T0xQ8SeCZGxckz9qRXTfG43PvQ/mcWh7FwZEA7Ioqkc= +github.com/vbatts/go-mtree v0.5.0 h1:dM+5XZdqH0j9CSZeerhoN/tAySdwnmevaZHO1XGW2Vc= +github.com/vbatts/go-mtree v0.5.0/go.mod h1:7JbaNHyBMng+RP8C3Q4E+4Ca8JnGQA2R/MB+jb4tSOk= +github.com/vbatts/tar-split v0.11.2 h1:Via6XqJr0hceW4wff3QRzD5gAk/tatMw/4ZA7cTlIME= +github.com/vbatts/tar-split v0.11.2/go.mod h1:vV3ZuO2yWSVsz+pfFzDG/upWH1JhjOiEaWq6kXyQ3VI= +github.com/vifraa/gopom v0.1.0 h1:v897eVxf6lflkEXzPmKbo4YhX2oS/LGjz7cqjWnSmCU= +github.com/vifraa/gopom v0.1.0/go.mod h1:oPa1dcrGrtlO37WPDBm5SqHAT+wTgF8An1Q71Z6Vv4o= +github.com/viki-org/dnscache v0.0.0-20130720023526-c70c1f23c5d8/go.mod h1:dniwbG03GafCjFohMDmz6Zc6oCuiqgH6tGNyXTkHzXE= +github.com/vishvananda/netlink v0.0.0-20181108222139-023a6dafdcdf/go.mod h1:+SR5DhBJrl6ZM7CoCKvpw5BKroDKQ+PJqOg65H/2ktk= +github.com/vishvananda/netlink v1.1.0/go.mod h1:cTgwzPIzzgDAYoQrMm0EdrjRUBkTqKYppBueQtXaqoE= +github.com/vishvananda/netlink v1.1.1-0.20201029203352-d40f9887b852/go.mod h1:twkDnbuQxJYemMlGd4JFIcuhgX83tXhKS2B/PRMpOho= +github.com/vishvananda/netns v0.0.0-20180720170159-13995c7128cc/go.mod h1:ZjcWmFBXmLKZu9Nxj3WKYEafiSqer2rnvPr0en9UNpI= +github.com/vishvananda/netns v0.0.0-20191106174202-0a2b9b5464df/go.mod h1:JP3t17pCcGlemwknint6hfoeCVQrEMVwxRLRjXpq+BU= +github.com/vishvananda/netns v0.0.0-20200728191858-db3c7e526aae/go.mod h1:DD4vA1DwXk04H54A1oHXtwZmA0grkVMdPxx/VGLCah0= +github.com/vmihailenco/msgpack/v4 v4.3.12 h1:07s4sz9IReOgdikxLTKNbBdqDMLsjPKXwvCazn8G65U= +github.com/vmihailenco/tagparser v0.1.1 h1:quXMXlA39OCbd2wAdTsGDlK9RkOk6Wuw+x37wVyIuWY= +github.com/wagoodman/go-partybus v0.0.0-20200526224238-eb215533f07d/go.mod h1:JPirS5jde/CF5qIjcK4WX+eQmKXdPc6vcZkJ/P0hfPw= +github.com/wagoodman/go-partybus v0.0.0-20210627031916-db1f5573bbc5 h1:phTLPgMRDYTizrBSKsNSOa2zthoC2KsJsaY/8sg3rD8= +github.com/wagoodman/go-partybus v0.0.0-20210627031916-db1f5573bbc5/go.mod h1:JPirS5jde/CF5qIjcK4WX+eQmKXdPc6vcZkJ/P0hfPw= +github.com/wagoodman/go-progress v0.0.0-20200621122631-1a2120f0695a/go.mod h1:jLXFoL31zFaHKAAyZUh+sxiTDFe1L1ZHrcK2T1itVKA= +github.com/wagoodman/go-progress v0.0.0-20200731105512-1020f39e6240 h1:r6BlIP7CVZtMlxUQhT40h1IE1TzEgKVqwmsVGuscvdk= +github.com/wagoodman/go-progress v0.0.0-20200731105512-1020f39e6240/go.mod h1:jLXFoL31zFaHKAAyZUh+sxiTDFe1L1ZHrcK2T1itVKA= +github.com/wagoodman/jotframe v0.0.0-20211129225309-56b0d0a4aebb h1:Yz6VVOcLuWLAHYlJzTw7JKnWxdV/WXpug2X0quEzRnY= +github.com/wagoodman/jotframe v0.0.0-20211129225309-56b0d0a4aebb/go.mod h1:nDi3BAC5nEbVbg+WSJDHLbjHv0ZToq8nMPA97XMxF3E= +github.com/willf/bitset v1.1.11-0.20200630133818-d5bec3311243/go.mod h1:RjeCKbqT1RxIR/KWY6phxZiaY1IyutSBfGjNPySAYV4= +github.com/willf/bitset v1.1.11/go.mod h1:83CECat5yLh5zVOf4P1ErAgKA5UDvKtgyUABdr3+MjI= +github.com/x-cray/logrus-prefixed-formatter v0.5.2 h1:00txxvfBM9muc0jiLIEAkAcIMJzfthRT6usrui8uGmg= +github.com/x-cray/logrus-prefixed-formatter v0.5.2/go.mod h1:2duySbKsL6M18s5GU7VPsoEPHyzalCE06qoARUCeBBE= +github.com/xanzy/go-gitlab v0.31.0/go.mod h1:sPLojNBn68fMUWSxIJtdVVIP8uSBYqesTfDUseX11Ug= +github.com/xanzy/go-gitlab v0.73.1 h1:UMagqUZLJdjss1SovIC+kJCH4k2AZWXl58gJd38Y/hI= +github.com/xanzy/go-gitlab v0.73.1/go.mod h1:d/a0vswScO7Agg1CZNz15Ic6SSvBG9vfw8egL99t4kA= +github.com/xanzy/ssh-agent v0.2.1/go.mod h1:mLlQY/MoOhWBj+gOGMQkOeiEvkx+8pJSI+0Bx9h2kr4= +github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI= +github.com/xdg-go/scram v1.0.2/go.mod h1:1WAq6h33pAW+iRreB34OORO2Nf7qel3VV3fjBj+hCSs= +github.com/xdg-go/scram v1.1.1/go.mod h1:RaEWvsqvNKKvBPvcKeFjrG2cJqOkHTiyTpzz23ni57g= +github.com/xdg-go/stringprep v1.0.2/go.mod h1:8F9zXuvzgwmyT5DUm4GUfZGDdT3W+LCvS6+da4O5kxM= +github.com/xdg-go/stringprep v1.0.3/go.mod h1:W3f5j4i+9rC0kuIEJL0ky1VpHXQU3ocBgklLGvcBnW8= +github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f/go.mod h1:N2zxlSyiKSe5eX1tZViRH5QA0qijqEDrYZiPEAiq3wU= +github.com/xeipuuv/gojsonpointer v0.0.0-20190905194746-02993c407bfb h1:zGWFAtiMcyryUHoUjUJX0/lt1H2+i2Ka2n+D3DImSNo= +github.com/xeipuuv/gojsonpointer v0.0.0-20190905194746-02993c407bfb/go.mod h1:N2zxlSyiKSe5eX1tZViRH5QA0qijqEDrYZiPEAiq3wU= +github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415 h1:EzJWgHovont7NscjpAxXsDA8S8BMYve8Y5+7cuRE7R0= +github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415/go.mod h1:GwrjFmJcFw6At/Gs6z4yjiIwzuJ1/+UwLxMQDVQXShQ= +github.com/xeipuuv/gojsonschema v0.0.0-20180618132009-1d523034197f/go.mod h1:5yf86TLmAcydyeJq5YvxkGPE2fm/u4myDekKRoLuqhs= +github.com/xeipuuv/gojsonschema v1.2.0 h1:LhYJRs+L4fBtjZUfuSZIKGeVu0QRy8e5Xi7D17UxZ74= +github.com/xeipuuv/gojsonschema v1.2.0/go.mod h1:anYRn/JVcOK2ZgGU+IjEV4nwlhoK5sQluxsYJ78Id3Y= +github.com/xi2/xz v0.0.0-20171230120015-48954b6210f8 h1:nIPpBwaJSVYIxUFsDv3M8ofmx9yWTog9BfvIu0q41lo= +github.com/xi2/xz v0.0.0-20171230120015-48954b6210f8/go.mod h1:HUYIGzjTL3rfEspMxjDjgmT5uz5wzYJKVo23qUhYTos= +github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2 h1:eY9dn8+vbi4tKz5Qo6v2eYzo7kUS51QINcR5jNpbZS8= +github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2/go.mod h1:UETIi67q53MR2AWcXfiuqkDkRtnGDLqkBTpCHuJHxtU= +github.com/xo/terminfo v0.0.0-20210125001918-ca9a967f8778 h1:QldyIu/L63oPpyvQmHgvgickp1Yw510KJOqX7H24mg8= +github.com/xo/terminfo v0.0.0-20210125001918-ca9a967f8778/go.mod h1:2MuV+tbUrU1zIOPMxZ5EncGwgmMJsa+9ucAQZXxsObs= +github.com/xordataexchange/crypt v0.0.3-0.20170626215501-b2862e3d0a77/go.mod h1:aYKd//L2LvnjZzWKhF00oedf4jCCReLcmhLdhm1A27Q= +github.com/yeya24/promlinter v0.1.0/go.mod h1:rs5vtZzeBHqqMwXqFScncpCF6u06lezhZepno9AB1Oc= +github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d/go.mod h1:rHwXgn7JulP+udvsHwJoVG1YGAP6VLg4y9I5dyZdqmA= +github.com/ysmood/goob v0.4.0 h1:HsxXhyLBeGzWXnqVKtmT9qM7EuVs/XOgkX7T6r1o1AQ= +github.com/ysmood/gson v0.7.2 h1:1iWUvpi5DPvd2j59W7ifRPR9DiAZ3Ga+fmMl1mJrRbM= +github.com/ysmood/leakless v0.8.0 h1:BzLrVoiwxikpgEQR0Lk8NyBN5Cit2b1z+u0mgL4ZJak= +github.com/yudai/gojsondiff v1.0.0/go.mod h1:AY32+k2cwILAkW1fbgxQ5mUmMiZFgLIV+FBNExI05xg= +github.com/yudai/golcs v0.0.0-20170316035057-ecda9a501e82/go.mod h1:lgjkn3NuSvDfVJdfcVVdX+jpBxNmX4rDAzaS45IcYoM= +github.com/yudai/pp v2.0.1+incompatible/go.mod h1:PuxR/8QJ7cyCkFp/aUDS+JY727OFEZkTdatxwunjIkc= +github.com/yuin/goldmark v1.1.25/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= +github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= +github.com/yuin/goldmark v1.1.32/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= +github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= +github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k= +github.com/yuin/goldmark v1.4.0/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k= +github.com/yuin/goldmark v1.4.1/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k= +github.com/yvasiyarov/go-metrics v0.0.0-20140926110328-57bccd1ccd43/go.mod h1:aX5oPXxHm3bOH+xeAttToC8pqch2ScQN/JoXYupl6xs= +github.com/yvasiyarov/gorelic v0.0.0-20141212073537-a9bba5b9ab50/go.mod h1:NUSPSUX/bi6SeDMUh6brw0nXpxHnc96TguQh0+r/ssA= +github.com/yvasiyarov/newrelic_platform_go v0.0.0-20140908184405-b21fdbd4370f/go.mod h1:GlGEuHIJweS1mbCqG+7vt2nvWLzLLnRHbXz5JKd/Qbg= +github.com/zalando/go-keyring v0.1.0/go.mod h1:RaxNwUITJaHVdQ0VC7pELPZ3tOWn13nr0gZMZEhpVU0= +github.com/zeebo/errs v1.2.2 h1:5NFypMTuSdoySVTqlNs1dEoU21QVamMQJxW/Fii5O7g= +github.com/zeebo/errs v1.2.2/go.mod h1:sgbWHsvVuTPHcqJJGQ1WhI5KbWlHYz+2+2C/LSEtCw4= +go.etcd.io/bbolt v1.3.2/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= +go.etcd.io/bbolt v1.3.3/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= +go.etcd.io/bbolt v1.3.4/go.mod h1:G5EMThwa9y8QZGBClrRx5EY+Yw9kAhnjy3bSjsnlVTQ= +go.etcd.io/bbolt v1.3.5/go.mod h1:G5EMThwa9y8QZGBClrRx5EY+Yw9kAhnjy3bSjsnlVTQ= +go.etcd.io/bbolt v1.3.6 h1:/ecaJf0sk1l4l6V4awd65v2C3ILy7MSj+s/x1ADCIMU= +go.etcd.io/bbolt v1.3.6/go.mod h1:qXsaaIqmgQH0T+OPdb99Bf+PKfBBQVAdyD6TY9G8XM4= +go.etcd.io/etcd v0.0.0-20191023171146-3cf2f69b5738/go.mod h1:dnLIgRNXwCJa5e+c6mIZCrds/GIG4ncV9HhK5PX7jPg= +go.etcd.io/etcd v0.0.0-20200513171258-e048e166ab9c/go.mod h1:xCI7ZzBfRuGgBXyXO6yfWfDmlWd35khcWpUa4L0xI/k= +go.etcd.io/etcd v0.5.0-alpha.5.0.20200910180754-dd1b699fc489/go.mod h1:yVHk9ub3CSBatqGNg7GRmsnfLWtoW60w4eDYfh7vHDg= +go.etcd.io/etcd/api/v3 v3.5.0-alpha.0/go.mod h1:mPcW6aZJukV6Aa81LSKpBjQXTWlXB5r74ymPoSWa3Sw= +go.etcd.io/etcd/api/v3 v3.5.0/go.mod h1:cbVKeC6lCfl7j/8jBhAK6aIYO9XOjdptoxU/nLQcPvs= +go.etcd.io/etcd/api/v3 v3.5.4/go.mod h1:5GB2vv4A4AOn3yk7MftYGHkUfGtDHnEraIjym4dYz5A= +go.etcd.io/etcd/api/v3 v3.6.0-alpha.0 h1:se+XckWlVTTfwjZSsAZJ2zGPzmIMq3j7fKBCmHoB9UA= +go.etcd.io/etcd/api/v3 v3.6.0-alpha.0/go.mod h1:z13pg39zewDLZeXIKeM0xELOeFKcqjLocfwl5M820+w= +go.etcd.io/etcd/client/pkg/v3 v3.5.0/go.mod h1:IJHfcCEKxYu1Os13ZdwCwIUTUVGYTSAM3YSwc9/Ac1g= +go.etcd.io/etcd/client/pkg/v3 v3.5.4/go.mod h1:IJHfcCEKxYu1Os13ZdwCwIUTUVGYTSAM3YSwc9/Ac1g= +go.etcd.io/etcd/client/pkg/v3 v3.6.0-alpha.0 h1:2UyRzFWbZZzgu/xzxoRukgixvafiJtGyxO+3IKUyJ6c= +go.etcd.io/etcd/client/pkg/v3 v3.6.0-alpha.0/go.mod h1:Vl/FkH40bHqmBFwhr8WVKtV47neyts36zl1voccRq8s= +go.etcd.io/etcd/client/v2 v2.305.0-alpha.0/go.mod h1:kdV+xzCJ3luEBSIeQyB/OEKkWKd8Zkux4sbDeANrosU= +go.etcd.io/etcd/client/v2 v2.305.0/go.mod h1:h9puh54ZTgAKtEbut2oe9P4L/oqKCVB6xsXlzd7alYQ= +go.etcd.io/etcd/client/v2 v2.305.4/go.mod h1:Ud+VUwIi9/uQHOMA+4ekToJ12lTxlv0zB/+DHwTGEbU= +go.etcd.io/etcd/client/v2 v2.306.0-alpha.0 h1:9VRJ698EFIMfjOQtcjKMM7CWXOIxp9R4I8JA1mk+WT4= +go.etcd.io/etcd/client/v2 v2.306.0-alpha.0/go.mod h1:eW78BCfOzS1HJgTNzDrb2E6xV1p6kqlpLpKkz7ErzCs= +go.etcd.io/etcd/client/v3 v3.5.0-alpha.0/go.mod h1:wKt7jgDgf/OfKiYmCq5WFGxOFAkVMLxiiXgLDFhECr8= +go.etcd.io/etcd/client/v3 v3.5.4/go.mod h1:ZaRkVgBZC+L+dLCjTcF1hRXpgZXQPOvnA/Ak/gq3kiY= +go.etcd.io/etcd/client/v3 v3.6.0-alpha.0 h1:hHaJ8CvTPJ9iv7xPz3G0gxt3csEqJW8evgty/kYICwo= +go.etcd.io/etcd/client/v3 v3.6.0-alpha.0/go.mod h1:a9JuChoQBDnw7WclHYBYCtTOIC12Wwj+Fw0LX4TI/Gs= +go.etcd.io/etcd/etcdctl/v3 v3.5.0-alpha.0/go.mod h1:YPwSaBciV5G6Gpt435AasAG3ROetZsKNUzibRa/++oo= +go.etcd.io/etcd/etcdctl/v3 v3.5.4/go.mod h1:SMZep1Aj7sUmMSBCHTjkZL/Yw36Vx5Ux61fKbopbb5U= +go.etcd.io/etcd/etcdctl/v3 v3.6.0-alpha.0 h1:3J+c4Av+pF7dBMAnxZVMrfCCMTaBz4CGJ8En3sZMNME= +go.etcd.io/etcd/etcdctl/v3 v3.6.0-alpha.0/go.mod h1:0ugckElRKx3OrV15/WAylLv2Ji67QxXKTh9lytkOh8s= +go.etcd.io/etcd/etcdutl/v3 v3.5.4/go.mod h1:eK9eZfI/BxDQCztpuaJ1E/ufYpMw2Y16dPX1azGWrBU= +go.etcd.io/etcd/etcdutl/v3 v3.6.0-alpha.0 h1:DZwDkrq/z5nHxXtovJMk9fyR6Nc+pwCJt25ptlFta24= +go.etcd.io/etcd/etcdutl/v3 v3.6.0-alpha.0/go.mod h1:0ILo94EKC+jgp/IMfxePlfJD1OVtMVfgTQ/xM8+joOA= +go.etcd.io/etcd/pkg/v3 v3.5.0-alpha.0/go.mod h1:tV31atvwzcybuqejDoY3oaNRTtlD2l/Ot78Pc9w7DMY= +go.etcd.io/etcd/pkg/v3 v3.5.4/go.mod h1:OI+TtO+Aa3nhQSppMbwE4ld3uF1/fqqwbpfndbbrEe0= +go.etcd.io/etcd/pkg/v3 v3.6.0-alpha.0 h1:cV/VsaYde/tcc2G9aHN5DQwx6CtUsWSEW4UqYzXuyyk= +go.etcd.io/etcd/pkg/v3 v3.6.0-alpha.0/go.mod h1:tXqWms0MpOJAS6L0B9nhFqZr0C/WEYzj/OtN90G8xzo= +go.etcd.io/etcd/raft/v3 v3.5.0-alpha.0/go.mod h1:FAwse6Zlm5v4tEWZaTjmNhe17Int4Oxbu7+2r0DiD3w= +go.etcd.io/etcd/raft/v3 v3.5.4/go.mod h1:SCuunjYvZFC0fBX0vxMSPjuZmpcSk+XaAcMrD6Do03w= +go.etcd.io/etcd/raft/v3 v3.6.0-alpha.0 h1:BQ6CnNP4pIpy5rusFlTBxAacDgPXhuiHFwoTsBNsVpI= +go.etcd.io/etcd/raft/v3 v3.6.0-alpha.0/go.mod h1:/kZdrBXlc5fUgYXfIEQ0B5sb7ejXPKbtF4jWzF1exiQ= +go.etcd.io/etcd/server/v3 v3.5.0-alpha.0/go.mod h1:tsKetYpt980ZTpzl/gb+UOJj9RkIyCb1u4wjzMg90BQ= +go.etcd.io/etcd/server/v3 v3.5.4/go.mod h1:S5/YTU15KxymM5l3T6b09sNOHPXqGYIZStpuuGbb65c= +go.etcd.io/etcd/server/v3 v3.6.0-alpha.0 h1:BQUVqBqNFZZyrRbfydrRLzq9hYvCcRj97SsX1YwD7CA= +go.etcd.io/etcd/server/v3 v3.6.0-alpha.0/go.mod h1:3QM2rLq3B3hSXmVEvgVt3vEEbG/AumSs0Is7EgrlKzU= +go.etcd.io/etcd/tests/v3 v3.5.0-alpha.0/go.mod h1:HnrHxjyCuZ8YDt8PYVyQQ5d1ZQfzJVEtQWllr5Vp/30= +go.etcd.io/etcd/tests/v3 v3.5.4/go.mod h1:ymig8LjkI1zqAxxMsl+nntzG21dND2hh0UQXl9BaJP8= +go.etcd.io/etcd/tests/v3 v3.6.0-alpha.0 h1:3qrZ3p/E7CxdV1kKtAU75hHOcUoXcSTwC7ELKWyzMJo= +go.etcd.io/etcd/tests/v3 v3.6.0-alpha.0/go.mod h1:hFQkP/cTsZIXXvUv+BsGHZ3TK+76XZMi5GToYA94iac= +go.etcd.io/etcd/v3 v3.5.0-alpha.0/go.mod h1:JZ79d3LV6NUfPjUxXrpiFAYcjhT+06qqw+i28snx8To= +go.etcd.io/etcd/v3 v3.5.4/go.mod h1:c6jK4IfuWwJU26FD9SeI4cAtvlfu9Iacaxu0vRses1k= +go.etcd.io/etcd/v3 v3.6.0-alpha.0 h1:c4c3xHs9tG097KtpLfBQJSD6c70xgEZbwkoj3gF6As4= +go.etcd.io/etcd/v3 v3.6.0-alpha.0/go.mod h1:9ERPHHuSr8Ho66trD/4f3+vSeqI/hk4loUSFUwj6Zcg= +go.mongodb.org/mongo-driver v1.7.3/go.mod h1:NqaYOwnXWr5Pm7AOpO5QFxKJ503nbMse/R79oO62zWg= +go.mongodb.org/mongo-driver v1.7.5/go.mod h1:VXEWRZ6URJIkUq2SCAyapmhH0ZLRBP+FT4xhp5Zvxng= +go.mongodb.org/mongo-driver v1.8.3/go.mod h1:0sQWfOeY63QTntERDJJ/0SuKK0T1uVSgKCuAROlKEPY= +go.mongodb.org/mongo-driver v1.10.0 h1:UtV6N5k14upNp4LTduX0QCufG124fSu25Wz9tu94GLg= +go.mongodb.org/mongo-driver v1.10.0/go.mod h1:wsihk0Kdgv8Kqu1Anit4sfK+22vSFbUrAVEYRhCXrA8= +go.mozilla.org/mozlog v0.0.0-20170222151521-4bb13139d403/go.mod h1:jHoPAGnDrCy6kaI2tAze5Prf0Nr0w/oNkROt2lw3n3o= +go.mozilla.org/pkcs7 v0.0.0-20200128120323-432b2356ecb1/go.mod h1:SNgMg+EgDFwmvSmLRTNKC5fegJjB7v23qTQ0XLGUNHk= +go.opencensus.io v0.15.0/go.mod h1:UffZAU+4sDEINUGP/B7UfBBkq4fqLu9zXAX7ke6CHW0= +go.opencensus.io v0.20.1/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk= +go.opencensus.io v0.20.2/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk= +go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU= +go.opencensus.io v0.22.0/go.mod h1:+kGneAE2xo2IficOXnaByMWTGM9T73dGwxeWcUqIpI8= +go.opencensus.io v0.22.2/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= +go.opencensus.io v0.22.3/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= +go.opencensus.io v0.22.4/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= +go.opencensus.io v0.22.5/go.mod h1:5pWMHQbX5EPX2/62yrJeAkowc+lfs/XD7Uxpq3pI6kk= +go.opencensus.io v0.23.0 h1:gqCw0LfLxScz8irSi8exQc7fyQ0fKQU/qnC/X8+V/1M= +go.opencensus.io v0.23.0/go.mod h1:XItmlyltB5F7CS4xOC1DcqMoFqwtC6OG2xF7mCv7P7E= +go.opentelemetry.io/contrib v0.20.0/go.mod h1:G/EtFaa6qaN7+LxqfIAT3GiZa7Wv5DTBUzl5H4LY0Kc= +go.opentelemetry.io/contrib v1.6.0 h1:xJawAzMuR3s4Au5p/ABHqYFychHjK2AHB9JvkBuBbTA= +go.opentelemetry.io/contrib v1.6.0/go.mod h1:FlyPNX9s4U6MCsWEc5YAK4KzKNHFDsjrDUZijJiXvy8= +go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.20.0/go.mod h1:oVGt1LRbBOBq1A5BQLlUg9UaU/54aiHw8cgjV3aWZ/E= +go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.28.0 h1:Ky1MObd188aGbgb5OgNnwGuEEwI9MVIcc7rBW6zk5Ak= +go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.28.0/go.mod h1:vEhqr0m4eTc+DWxfsXoXue2GBgV2uUwVznkGIHW/e5w= +go.opentelemetry.io/contrib/propagators v0.19.0 h1:HrixVNZYFjUl/Db+Tr3DhqzLsVW9GeVf/Gye+C5dNUY= +go.opentelemetry.io/otel v0.20.0/go.mod h1:Y3ugLH2oa81t5QO+Lty+zXf8zC9L26ax4Nzoxm/dooo= +go.opentelemetry.io/otel v1.3.0/go.mod h1:PWIKzi6JCp7sM0k9yZ43VX+T345uNbAkDKwHVjb2PTs= +go.opentelemetry.io/otel v1.7.0 h1:Z2lA3Tdch0iDcrhJXDIlC94XE+bxok1F9B+4Lz/lGsM= +go.opentelemetry.io/otel v1.7.0/go.mod h1:5BdUoMIz5WEs0vt0CUEMtSSaTSHBBVwrhnz7+nrD5xk= +go.opentelemetry.io/otel/exporters/otlp v0.20.0/go.mod h1:YIieizyaN77rtLJra0buKiNBOm9XQfkPEKBeuhoMwAM= +go.opentelemetry.io/otel/exporters/otlp/internal/retry v1.7.0 h1:7Yxsak1q4XrJ5y7XBnNwqWx9amMZvoidCctv62XOQ6Y= +go.opentelemetry.io/otel/exporters/otlp/internal/retry v1.7.0/go.mod h1:M1hVZHNxcbkAlcvrOMlpQ4YOO3Awf+4N2dxkZL3xm04= +go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.7.0 h1:cMDtmgJ5FpRvqx9x2Aq+Mm0O6K/zcUkH73SFz20TuBw= +go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.7.0/go.mod h1:ceUgdyfNv4h4gLxHR0WNfDiiVmZFodZhZSbOLhpxqXE= +go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.7.0 h1:MFAyzUPrTwLOwCi+cltN0ZVyy4phU41lwH+lyMyQTS4= +go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.7.0/go.mod h1:E+/KKhwOSw8yoPxSSuUHG6vKppkvhN+S1Jc7Nib3k3o= +go.opentelemetry.io/otel/metric v0.20.0/go.mod h1:598I5tYlH1vzBjn+BTuhzTCSb/9debfNp6R3s7Pr1eU= +go.opentelemetry.io/otel/oteltest v0.20.0/go.mod h1:L7bgKf9ZB7qCwT9Up7i9/pn0PWIa9FqQ2IQ8LoxiGnw= +go.opentelemetry.io/otel/sdk v0.20.0/go.mod h1:g/IcepuwNsoiX5Byy2nNV0ySUF1em498m7hBWC279Yc= +go.opentelemetry.io/otel/sdk v1.7.0 h1:4OmStpcKVOfvDOgCt7UriAPtKolwIhxpnSNI/yK+1B0= +go.opentelemetry.io/otel/sdk v1.7.0/go.mod h1:uTEOTwaqIVuTGiJN7ii13Ibp75wJmYUDe374q6cZwUU= +go.opentelemetry.io/otel/sdk/export/metric v0.20.0/go.mod h1:h7RBNMsDJ5pmI1zExLi+bJK+Dr8NQCh0qGhm1KDnNlE= +go.opentelemetry.io/otel/sdk/metric v0.20.0/go.mod h1:knxiS8Xd4E/N+ZqKmUPf3gTTZ4/0TjTXukfxjzSTpHE= +go.opentelemetry.io/otel/trace v0.20.0/go.mod h1:6GjCW8zgDjwGHGa6GkyeB8+/5vjT16gUEi0Nf1iBdgw= +go.opentelemetry.io/otel/trace v1.3.0/go.mod h1:c/VDhno8888bvQYmbYLqe41/Ldmr/KKunbvWM4/fEjk= +go.opentelemetry.io/otel/trace v1.7.0 h1:O37Iogk1lEkMRXewVtZ1BBTVn5JEp8GrJvP92bJqC6o= +go.opentelemetry.io/otel/trace v1.7.0/go.mod h1:fzLSB9nqR2eXzxPXb2JW9IKE+ScyXA48yyE4TNvoHqU= +go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI= +go.opentelemetry.io/proto/otlp v0.16.0 h1:WHzDWdXUvbc5bG2ObdrGfaNpQz7ft7QN9HHmJlbiB1E= +go.opentelemetry.io/proto/otlp v0.16.0/go.mod h1:H7XAot3MsfNsj7EXtrA2q5xSNQ10UqI405h3+duxN4U= +go.uber.org/atomic v1.3.2/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= +go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= +go.uber.org/atomic v1.5.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ= +go.uber.org/atomic v1.6.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ= +go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= +go.uber.org/atomic v1.9.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= +go.uber.org/atomic v1.10.0 h1:9qC72Qh0+3MqyJbAn8YU5xVq1frD8bn3JtD2oXtafVQ= +go.uber.org/atomic v1.10.0/go.mod h1:LUxbIzbOniOlMKjJjyPfpl4v+PKK2cNJn91OQbhoJI0= +go.uber.org/goleak v1.1.10/go.mod h1:8a7PlsEVH3e/a/GLqe5IIrQx6GzcnRmZEufDUTk4A7A= +go.uber.org/goleak v1.1.11/go.mod h1:cwTWslyiVhfpKIDGSZEM2HlOvcqm+tG4zioyIeLoqMQ= +go.uber.org/goleak v1.1.12 h1:gZAh5/EyT/HQwlpkCy6wTpqfH9H8Lz8zbm3dZh+OyzA= +go.uber.org/goleak v1.1.12/go.mod h1:cwTWslyiVhfpKIDGSZEM2HlOvcqm+tG4zioyIeLoqMQ= +go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0= +go.uber.org/multierr v1.3.0/go.mod h1:VgVr7evmIr6uPjLBxg28wmKNXyqE9akIJ5XnfpiKl+4= +go.uber.org/multierr v1.4.0/go.mod h1:VgVr7evmIr6uPjLBxg28wmKNXyqE9akIJ5XnfpiKl+4= +go.uber.org/multierr v1.5.0/go.mod h1:FeouvMocqHpRaaGuG9EjoKcStLC43Zu/fmqdUMPcKYU= +go.uber.org/multierr v1.6.0/go.mod h1:cdWPpRnG4AhwMwsgIHip0KRBQjJy5kYEpYjJxpXp9iU= +go.uber.org/multierr v1.8.0 h1:dg6GjLku4EH+249NNmoIciG9N/jURbDG+pFlTkhzIC8= +go.uber.org/multierr v1.8.0/go.mod h1:7EAYxJLBy9rStEaz58O2t4Uvip6FSURkq8/ppBp95ak= +go.uber.org/tools v0.0.0-20190618225709-2cfd321de3ee/go.mod h1:vJERXedbb3MVM5f9Ejo0C68/HhF8uaILCdgjnY+goOA= +go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q= +go.uber.org/zap v1.13.0/go.mod h1:zwrFLgMcdUuIBviXEYEH1YKNaOBnKXsx2IPda5bBwHM= +go.uber.org/zap v1.16.0/go.mod h1:MA8QOfq0BHJwdXa996Y4dYkAqRKB8/1K1QMMZVaNZjQ= +go.uber.org/zap v1.17.0/go.mod h1:MXVU+bhUf/A7Xi2HNOnopQOrmycQ5Ih87HtOu4q5SSo= +go.uber.org/zap v1.21.0/go.mod h1:wjWOCqI0f2ZZrJF/UufIOkiC8ii6tm1iqIsLo76RfJw= +go.uber.org/zap v1.22.0 h1:Zcye5DUgBloQ9BaT4qc9BnjOFog5TvBSAGkJ3Nf70c0= +go.uber.org/zap v1.22.0/go.mod h1:H4siCOZOrAolnUPJEkfaSjDqyP+BDS0DdDWzwcgt3+U= +gocloud.dev v0.19.0/go.mod h1:SmKwiR8YwIMMJvQBKLsC3fHNyMwXLw3PMDO+VVteJMI= +golang.org/x/crypto v0.0.0-20171113213409-9f005a07e0d3/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20180501155221-613d6eafa307/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20181009213950-7c1a557ab941/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20181029021203-45a5f77698d3/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20181203042331-505ab145d0a9/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20190219172222-a4c6cb3142f2/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20190228161510-8dd112bcdc25/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20190422162423-af44ce270edf/go.mod h1:WFFai1msRO1wXaEeE5yQxYXgSfI8pQAWXbQop6sCtWE= +golang.org/x/crypto v0.0.0-20190426145343-a29dc8fdc734/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190605123033-f99c8df09eb5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190611184440-5c40567a22f8/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190701094942-4def268fd1a4/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190820162420-60c769a6c586/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190923035154-9ee001bba392/go.mod h1:/lpIB1dKB+9EgE3H3cr1v9wB50oz8l4C4h62xy7jSTY= +golang.org/x/crypto v0.0.0-20191002192127-34f69633bfdc/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20191117063200-497ca9f6d64f/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20200302210943-78000ba7a073/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20200414173820-0848c9571904/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20200604202706-70a84ac30bf9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20200728195943-123391ffb6de/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20200930160638-afb6bcd081ae/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20201002170205-7f63de1d35b0/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20201216223049-8b5274cf687f/go.mod h1:jdWPYTVW3xRLrWPugEBEK3UY2ZEsg3UU495nc5E+M+I= +golang.org/x/crypto v0.0.0-20201221181555-eec23a3978ad/go.mod h1:jdWPYTVW3xRLrWPugEBEK3UY2ZEsg3UU495nc5E+M+I= +golang.org/x/crypto v0.0.0-20210322153248-0c34fe9e7dc2/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4= +golang.org/x/crypto v0.0.0-20210421170649-83a5a9bb288b/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4= +golang.org/x/crypto v0.0.0-20210513164829-c07d793c2f9a/go.mod h1:P+XmwS30IXTQdn5tA2iutPOUgjI07+tq3H3K9MVA1s8= +golang.org/x/crypto v0.0.0-20210817164053-32db794688a5/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= +golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= +golang.org/x/crypto v0.0.0-20211108221036-ceb1ce70b4fa/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= +golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= +golang.org/x/crypto v0.0.0-20220131195533-30dcbda58838/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= +golang.org/x/crypto v0.0.0-20220411220226-7b82a4e95df4/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= +golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= +golang.org/x/crypto v0.0.0-20220722155217-630584e8d5aa h1:zuSxTR4o9y82ebqCUJYNGJbGPo6sKVl54f/TVDObg1c= +golang.org/x/crypto v0.0.0-20220722155217-630584e8d5aa/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= +golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= +golang.org/x/exp v0.0.0-20190306152737-a1d7652674e8/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= +golang.org/x/exp v0.0.0-20190510132918-efd6b22b2522/go.mod h1:ZjyILWgesfNpC6sMxTJOJm9Kp84zZh5NQWvqDGG3Qr8= +golang.org/x/exp v0.0.0-20190829153037-c13cbed26979/go.mod h1:86+5VVa7VpoJ4kLfm080zCjGlMRFzhUhsZKEZO7MGek= +golang.org/x/exp v0.0.0-20191030013958-a1ab85dbe136/go.mod h1:JXzH8nQsPlswgeRAPE3MuO9GYsAcnJvJ4vnMwN/5qkY= +golang.org/x/exp v0.0.0-20191129062945-2f5052295587/go.mod h1:2RIsYlXP63K8oxa1u096TMicItID8zy7Y6sNkU49FU4= +golang.org/x/exp v0.0.0-20191227195350-da58074b4299/go.mod h1:2RIsYlXP63K8oxa1u096TMicItID8zy7Y6sNkU49FU4= +golang.org/x/exp v0.0.0-20200119233911-0405dc783f0a/go.mod h1:2RIsYlXP63K8oxa1u096TMicItID8zy7Y6sNkU49FU4= +golang.org/x/exp v0.0.0-20200207192155-f17229e696bd/go.mod h1:J/WKrq2StrnmMY6+EHIKF9dgMWnmCNThgcyBT1FY9mM= +golang.org/x/exp v0.0.0-20200224162631-6cc2880d07d6/go.mod h1:3jZMyOhIsHpP37uCMkUooju7aAi5cS1Q23tOzKc+0MU= +golang.org/x/exp v0.0.0-20200331195152-e8c3332aa8e5/go.mod h1:4M0jN8W1tt0AVLNr8HDosyJCDCDuyL9N9+3m7wDWgKw= +golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js= +golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= +golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= +golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU= +golang.org/x/lint v0.0.0-20190301231843-5614ed5bae6f/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= +golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= +golang.org/x/lint v0.0.0-20190409202823-959b441ac422/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= +golang.org/x/lint v0.0.0-20190909230951-414d861bb4ac/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= +golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= +golang.org/x/lint v0.0.0-20191125180803-fdd1cda4f05f/go.mod h1:5qLYkcX4OjUUV8bRuDixDT3tpyyb+LUpUlRWLxfhWrs= +golang.org/x/lint v0.0.0-20200130185559-910be7a94367/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY= +golang.org/x/lint v0.0.0-20200302205851-738671d3881b/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY= +golang.org/x/lint v0.0.0-20201208152925-83fdc39ff7b5/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY= +golang.org/x/lint v0.0.0-20210508222113-6edffad5e616/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY= +golang.org/x/mobile v0.0.0-20190312151609-d3739f865fa6/go.mod h1:z+o9i4GpDbdi3rU15maQ/Ox0txvL9dWGYEHz965HBQE= +golang.org/x/mobile v0.0.0-20190719004257-d2bd2a29d028/go.mod h1:E/iHnbuqvinMTCcRqshq8CkpyQDoeVncDDYHnLhea+o= +golang.org/x/mod v0.0.0-20190513183733-4bf6d317e70e/go.mod h1:mXi4GBBbnImb6dmsKGUJ2LatrhH/nqhxcFungHvyanc= +golang.org/x/mod v0.1.0/go.mod h1:0QHyrYULN0/3qlju5TqG8bIK38QM8yzMo5ekMj3DlcY= +golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= +golang.org/x/mod v0.1.1-0.20191107180719-034126e5016b/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= +golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= +golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= +golang.org/x/mod v0.4.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= +golang.org/x/mod v0.4.1/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= +golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= +golang.org/x/mod v0.5.0/go.mod h1:5OXOZSfqPIIbmVBIIKWRFfZjPR0E5r58TLhUjH0a2Ro= +golang.org/x/mod v0.6.0-dev.0.20220106191415-9b9b3d81d5e3/go.mod h1:3p9vT2HGsQu2K1YbXdKPJLVgG5VJdoTa1poYQBtP1AY= +golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4 h1:6zppjxzCulZykYSLyVDYbneBfbaBIQPYMevg0bEwv2s= +golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= +golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20181011144130-49bb7cea24b1/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20181023162649-9b4f9f5ad519/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20181108082009-03003ca0c849/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20181114220301-adae6a3d119a/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20181201002055-351d144fa1fc/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20181220203305-927f97764cc3/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20190125091013-d26f9f9a57f3/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190501004415-9ce7a6920f09/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190503192946-f4e77d36d62c/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190522155817-f3200d17e092/go.mod h1:HSz+uSET+XFnRR8LxR5pz3Of3rY3CfYBVs4xY44aLks= +golang.org/x/net v0.0.0-20190603091049-60506f45cf65/go.mod h1:HSz+uSET+XFnRR8LxR5pz3Of3rY3CfYBVs4xY44aLks= +golang.org/x/net v0.0.0-20190613194153-d28f0bde5980/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20190619014844-b5b0513f8c1b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20190628185345-da137c7871d7/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20190724013045-ca1201d0de80/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20190813141303-74dc4d7220e7/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20190827160401-ba9fcec4b297/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20190923162816-aa69164e4478/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20191002035440-2ec189313ef0/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20191004110552-13f9640d40b9/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20191119073136-fc4aabc6c914/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20191209160850-c0dbc17a3553/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200114155413-6afb5195e5aa/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200222125558-5a598a2470a0/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200301022130-244492dfa37a/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200324143707-d3edc9973b7e/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200421231249-e086a090c8fd/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200501053045-e0ff5e5a1de5/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200505041828-1ed23360d12c/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200506145744-7e3656a0809f/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200513185701-a91f0712d120/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200520182314-0ba52f642ac2/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200625001655-4c5254603344/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= +golang.org/x/net v0.0.0-20200707034311-ab3426394381/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= +golang.org/x/net v0.0.0-20200813134508-3edf25e44fcc/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= +golang.org/x/net v0.0.0-20200822124328-c89045814202/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= +golang.org/x/net v0.0.0-20200930145003-4acb6c075d10/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= +golang.org/x/net v0.0.0-20201006153459-a7d1128ccaa0/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= +golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= +golang.org/x/net v0.0.0-20201031054903-ff519b6c9102/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= +golang.org/x/net v0.0.0-20201110031124-69a78807bb2b/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= +golang.org/x/net v0.0.0-20201202161906-c7110b5ffcbb/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= +golang.org/x/net v0.0.0-20201209123823-ac852fbbde11/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20201224014010-6772e930b67b/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20210316092652-d523dce5a7f4/go.mod h1:RBQZq4jEuRlivfhVLdyRGr576XBO4/greRjx4P4O3yc= +golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM= +golang.org/x/net v0.0.0-20210421230115-4e50805a0758/go.mod h1:72T/g9IO56b78aLF+1Kcs5dz7/ng1VjMUvfKvpfy+jM= +golang.org/x/net v0.0.0-20210423184538-5f58ad60dda6/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= +golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= +golang.org/x/net v0.0.0-20210503060351-7fd8e65b6420/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20210505024714-0287a6fb4125/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20210510120150-4163338589ed/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20210805182204-aaa1db679c0d/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20210813160813-60bc85c4be6d/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20211015210444-4f30a5c0130f/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20211111160137-58aab5ef257a/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20211209124913-491a49abca63/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= +golang.org/x/net v0.0.0-20220225172249-27dd8689420f/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= +golang.org/x/net v0.0.0-20220325170049-de3da57026de/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= +golang.org/x/net v0.0.0-20220412020605-290c469a71a5/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= +golang.org/x/net v0.0.0-20220421235706-1d1ef9303861/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= +golang.org/x/net v0.0.0-20220425223048-2871e0cb64e4/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= +golang.org/x/net v0.0.0-20220607020251-c690dde0001d/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= +golang.org/x/net v0.0.0-20220624214902-1bab6f366d9e/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= +golang.org/x/net v0.0.0-20220805013720-a33c5aa5df48 h1:N9Vc/rorQUDes6B9CNdIxAn5jODGj2wzfrei2x4wNj4= +golang.org/x/net v0.0.0-20220805013720-a33c5aa5df48/go.mod h1:YDH+HFinaLZZlnHAfSS6ZXJJ9M9t4Dl22yv3iI2vPwk= +golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= +golang.org/x/oauth2 v0.0.0-20181106182150-f42d05182288/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= +golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= +golang.org/x/oauth2 v0.0.0-20190402181905-9f3314589c9a/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= +golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= +golang.org/x/oauth2 v0.0.0-20191202225959-858c2ad4c8b6/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= +golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= +golang.org/x/oauth2 v0.0.0-20200902213428-5d25da1a8d43/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20201109201403-9fd604954f58/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20201208152858-08078c50e5b5/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210218202405-ba52d332ba99/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210220000619-9bb904979d93/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210313182246-cd4f82c27b84/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210402161424-2e8d93401602/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210413134643-5e61552d6c78/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210427180440-81ed05c6b58c/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210514164344-f6687ab2804c/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210628180205-a41e5a781914/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210805134026-6f1e6394065a/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20210819190943-2bc19b11175f/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20211005180243-6b3c2da341f1/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20211104180415-d3ed0bb246c8/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20220223155221-ee480838109b/go.mod h1:DAh4E804XQdzx2j+YRIaUnCqCV2RuMz24cGBJ5QYIrc= +golang.org/x/oauth2 v0.0.0-20220309155454-6242fa91716a/go.mod h1:DAh4E804XQdzx2j+YRIaUnCqCV2RuMz24cGBJ5QYIrc= +golang.org/x/oauth2 v0.0.0-20220411215720-9780585627b5/go.mod h1:DAh4E804XQdzx2j+YRIaUnCqCV2RuMz24cGBJ5QYIrc= +golang.org/x/oauth2 v0.0.0-20220608161450-d0670ef3b1eb/go.mod h1:jaDAt6Dkxork7LmZnYtzbRWj0W47D86a3TGe0YHBvmE= +golang.org/x/oauth2 v0.0.0-20220622183110-fd043fe589d2/go.mod h1:jaDAt6Dkxork7LmZnYtzbRWj0W47D86a3TGe0YHBvmE= +golang.org/x/oauth2 v0.0.0-20220722155238-128564f6959c h1:q3gFqPqH7NVofKo3c3yETAP//pPI+G5mvB7qqj1Y5kY= +golang.org/x/oauth2 v0.0.0-20220722155238-128564f6959c/go.mod h1:h4gKUeWbJ4rQPri7E0u6Gs4e9Ri2zaLxzw5DI5XGrYg= +golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20190412183630-56d357773e84/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20200317015054-43a5402ce75a/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20200625203802-6e8e738ad208/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20200930132711-30421366ff76/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20201207232520-09787c993a3a/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20220601150217-0de741cfad7f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4 h1:uVc8UZUe6tr40fFVnUP5Oj+veunVezqYl9z7DYw9xzw= +golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sys v0.0.0-20180823144017-11551d06cbcc/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20181026203630-95b1ffbd15a5/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20181107165924-66b7b1311ac8/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20181116152217-5ac8a444bdc5/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20181122145206-62eef0e2fa9b/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20181205085412-a5c9d58dba9a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190221075227-b4e8571b14e0/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190403152447-81d4e9dc473e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190419153524-e8e3143a4f4a/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190502145724-3ef323f4f1fd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190507160741-ecd444e8653b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190514135907-3a4b5fb9f71f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190522044717-8097e1b27ff5/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190531175056-4c3a928424d2/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190602015325-4c4f7f33c9ed/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190606165138-5da285871e9c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190606203320-7fc4e5ec1444/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190616124812-15dcb6c0061f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190620070143-6f217b454f45/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190624142023-c5567b49c5d0/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190726091711-fc99dfbffb4e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190801041406-cbf593c0f2f3/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190812073006-9eafafc0a87e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190826190057-c7b8b68b1456/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190904154756-749cb33beabd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190916202348-b4ddaad3f8a3/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190922100055-0a153f010e69/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190924154521-2837fb4f24fe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191001151750-bb3f8db39f24/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191005200804-aed5e4c7ecf9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191008105621-543471e840be/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191022100944-742c48ecaeb7/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191115151921-52ab43148777/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191119060738-e882bf8e40c2/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191120155948-bd437916bb0e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191204072324-ce4227a45e2e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191210023423-ac6580df4449/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191220142924-d4481acd189f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191228213918-04cbcbbfeed8/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200106162015-b016eb3dc98e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200113162924-86b910548bc1/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200116001909-b77594299b42/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200120151820-655fe14d7479/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200122134326-e047566fdf82/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200124204421-9fbb57f87de9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200202164722-d101bd2416d5/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200212091648-12a6c2dcc1e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200217220822-9197077df867/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200302150141-5c8b2ff67527/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200331124033-c3d80250170d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200420163511-1957bb5e6d1f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200501052902-10377860bb8e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200511232937-7e40ca221e25/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200515095857-1151b9dac4a9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200519105757-fe76b779f299/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200523222454-059865788121/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200615200032-f1bc736245b1/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200622214017-ed371f2e16b4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200625212154-ddb9806d33ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200728102440-3e129f6d46b1/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200803210538-64077c9b5642/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200814200057-3d37ad5750ed/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200817155316-9781c653f443/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200905004654-be1d3432aa8f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200909081042-eff7692f9009/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200916030750-2334cc1a136f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200922070232-aee5d888a860/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200923182605-d9f96fdee20d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201005172224-997123666555/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201009025420-dfb3f7c4e634/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201112073958-5cba982894dd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201117170446-d9b008d0a637/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201201145000-ef89a241ccb3/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201202213521-69691e467435/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210104204734-6f8348627aad/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210112080510-489259a85091/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210119212857-b64e53b001e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210220050731-9a76102bfb43/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210225134936-a50acf3fe073/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210305230114-8fe3ee5dd75b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210309074719-68d13333faf2/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210315160823-c6e025ad8005/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210320140829-1e4c9ba3b0c4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210324051608-47abb6519492/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210403161142-5e06dd20ab57/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210412220455-f1c623a9e750/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210420072515-93ed5bcd2bfe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210423185535-09eb48e85fd7/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210426230700-d19ff857e887/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210503080704-8803ae5d1324/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210514084401-e8d321eab015/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210603081109-ebe580a85c40/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210603125802-9665404d3644/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210616094352-59db8d763f22/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210806184541-e5e7981a1069/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210809222454-d867a43fc93e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210816074244-15123e1e1f71/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210816183151-1e6c022a8912/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210823070655-63515b42dcdf/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210831042530-f4d43177bf5e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210908233432-aa78b53d3365/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210915083310-ed5796bab164/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210917161153-d61c044b1678/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211007075335-d3039528d8ac/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211013075003-97ac67df715c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211019181941-9d821ace8654/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211110154304-99a53858aa08/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211124211545-fe61309f8881/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211210111614-af8b64212486/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211216021012-1d35b9e2eb4e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220114195835-da31bd327af9/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220128215802-99c3d69c2c27/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220209214540-3681064d5158/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220227234510-4e6760a101f9/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220328115105-d36c6a25d886/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220412211240-33da011f77ad/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220422013727-9388b58f7150/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220502124256-b6088ccd6cba/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220610221304-9f5ed59c137d/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220624220833-87e55d714810/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10 h1:WIoqL4EROvwiPdUtaip4VcDdpZ4kha7wBWZrbVKCIZg= +golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= +golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= +golang.org/x/term v0.0.0-20210615171337-6886f2dfbf5b/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= +golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= +golang.org/x/term v0.0.0-20220526004731-065cf7ba2467 h1:CBpWXWQpIRjzmkkA+M7q9Fqnwd2mZr3AFqexg8YTfoM= +golang.org/x/term v0.0.0-20220526004731-065cf7ba2467/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= +golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= +golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= +golang.org/x/text v0.3.8-0.20211004125949-5bd84dd9b33b h1:NXqSWXSRUSCaFuvitrWtU169I3876zRTalMRbfd6LL0= +golang.org/x/text v0.3.8-0.20211004125949-5bd84dd9b33b/go.mod h1:EFNZuWvGYxIRUEX+K8UmCFwYmZjqcrnq15ZuVldZkZ0= +golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20200416051211-89c76fbcd5d1/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20200630173020-3af7569d3a1e/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20210220033141-f8bda1e9f3ba/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20210723032227-1f47c861a9ac/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20220411224347-583f2d630306/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20220722155302-e5dcc9cfc0b9 h1:ftMN5LMiBFjbzleLqtoBZk7KdJwhuybIU+FckUHgoyQ= +golang.org/x/time v0.0.0-20220722155302-e5dcc9cfc0b9/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/tools v0.0.0-20180221164845-07fd8470d635/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20180525024113-a5b4c53f6e8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20180828015842-6cd1fcedba52/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20181030221726-6c7e314b6563/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20190110163146-51295c7ec13a/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY= +golang.org/x/tools v0.0.0-20190307163923-6a08e3108db3/go.mod h1:25r3+/G6/xytQM8iWZKq3Hn0kr0rgFKPUNVEL/dr3z4= +golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190311215038-5c2858a9cfe5/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190312151545-0bb0c0a6e846/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190312170243-e65039ee4138/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190321232350-e250d351ecad/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190322203728-c1a832b0ad89/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190328211700-ab21143f2384/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190329151228-23e29df326fe/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190416151739-9c9e1878f421/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190420181800-aa740d480789/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190422233926-fe54fb35175b/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/tools v0.0.0-20190425150028-36563e24a262/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= +golang.org/x/tools v0.0.0-20190506145303-2d16b83fe98c/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= +golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= +golang.org/x/tools v0.0.0-20190531172133-b3315ee88b7d/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190606124116-d0a3d012864b/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190614205625-5aca471b1d59/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190621195816-6e04913cbbac/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190624222133-a101b041ded4/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190628153133-6cdbf07be9d0/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190729092621-ff9f1409240a/go.mod h1:jcCCGcm9btYwXyDqrUWc6MKQKKGJCWEQ3AfLSRIbEuI= +golang.org/x/tools v0.0.0-20190816200558-6889da9d5479/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20190907020128-2ca718005c18/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20190910044552-dd2b5c81c578/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20190911174233-4f2ddba30aff/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20190916130336-e45ffcd953cc/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191010075000-0337d82405ff/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191012152004-8de300cfc20a/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191029041327-9cc4af7d6b2c/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191029190741-b9c20aec41a5/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191108193012-7d206e10da11/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191112195655-aa38f8e97acc/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191113191852-77e3bb0ad9e7/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191115202509-3a792d9c32b2/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191118222007-07fc4c7f2b98/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191125144606-a911d9008d1f/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191130070609-6e064ea0cf2d/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191216052735-49a3e744a425/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20191216173652-a0e659d51361/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20191227053925-7b8e75db28f4/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200103221440-774c71fcf114/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200117161641-43d50277825c/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200117220505-0cba7a3a9ee9/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200122220014-bf1340f18c4a/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200130002326-2f3ba24bd6e7/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200204074204-1cc6d1ef6c74/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200207183749-b753a1ba74fa/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200212150539-ea181f53ac56/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200224181240-023911ca70b2/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200227222343-706bc42d1f0d/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/tools v0.0.0-20200304193943-95d2e580d8eb/go.mod h1:o4KQGtdN14AW+yjsvvwRTJJuXz8XRtIHtEnmAXLyFUw= +golang.org/x/tools v0.0.0-20200312045724-11d5b4c81c7d/go.mod h1:o4KQGtdN14AW+yjsvvwRTJJuXz8XRtIHtEnmAXLyFUw= +golang.org/x/tools v0.0.0-20200324003944-a576cf524670/go.mod h1:Sl4aGygMT6LrqrWclx+PTx3U+LnKx/seiNR+3G19Ar8= +golang.org/x/tools v0.0.0-20200329025819-fd4102a86c65/go.mod h1:Sl4aGygMT6LrqrWclx+PTx3U+LnKx/seiNR+3G19Ar8= +golang.org/x/tools v0.0.0-20200331025713-a30bf2db82d4/go.mod h1:Sl4aGygMT6LrqrWclx+PTx3U+LnKx/seiNR+3G19Ar8= +golang.org/x/tools v0.0.0-20200414032229-332987a829c3/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200422022333-3d57cf2e726e/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200426102838-f3a5411a4c3b/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200501065659-ab2804fb9c9d/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200505023115-26f46d2f7ef8/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200512131952-2bc93b1c0c88/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200515010526-7d3b6ebf133d/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200522201501-cb1345f3a375/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200618134242-20370b0cb4b2/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200622203043-20e05c1c8ffa/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200624225443-88f3c62a19ff/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200625211823-6506e20df31f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200626171337-aa94e735be7f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200630154851-b2d8b0336632/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= +golang.org/x/tools v0.0.0-20200706234117-b22de6825cf7/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= +golang.org/x/tools v0.0.0-20200717024301-6ddee64345a6/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= +golang.org/x/tools v0.0.0-20200724022722-7017fd6b1305/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= +golang.org/x/tools v0.0.0-20200729194436-6467de6f59a7/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= +golang.org/x/tools v0.0.0-20200804011535-6c149bb5ef0d/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= +golang.org/x/tools v0.0.0-20200812195022-5ae4c3c160a0/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= +golang.org/x/tools v0.0.0-20200820010801-b793a1359eac/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= +golang.org/x/tools v0.0.0-20200825202427-b303f430e36d/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= +golang.org/x/tools v0.0.0-20200831203904-5a2aa26beb65/go.mod h1:Cj7w3i3Rnn0Xh82ur9kSqwfTHTeVxaDqrfMjpcNT6bE= +golang.org/x/tools v0.0.0-20200904185747-39188db58858/go.mod h1:Cj7w3i3Rnn0Xh82ur9kSqwfTHTeVxaDqrfMjpcNT6bE= +golang.org/x/tools v0.0.0-20201001104356-43ebab892c4c/go.mod h1:z6u4i615ZeAfBE4XtMziQW1fSVJXACjjbWkB/mvPzlU= +golang.org/x/tools v0.0.0-20201002184944-ecd9fd270d5d/go.mod h1:z6u4i615ZeAfBE4XtMziQW1fSVJXACjjbWkB/mvPzlU= +golang.org/x/tools v0.0.0-20201014170642-d1624618ad65/go.mod h1:z6u4i615ZeAfBE4XtMziQW1fSVJXACjjbWkB/mvPzlU= +golang.org/x/tools v0.0.0-20201023174141-c8cfbd0f21e6/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201028025901-8cd080b735b3/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201110124207-079ba7bd75cd/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201114224030-61ea331ec02b/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201118003311-bd56c0adb394/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201124115921-2c860bdd6e78/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201201161351-ac6f37ff4c2a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201208233053-a543418bbed2/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201224043029-2b0845dc783e/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20201230224404-63754364767c/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20210101214203-2dba1e4ea05c/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20210104081019-d8d6ddbec6ee/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20210105154028-b0ab187a4818/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20210108195828-e2f9c7f1fc8e/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.1.0/go.mod h1:xkSsbof2nBLbhDlRMhhhyNLN/zl3eTqcnHD5viDpcZ0= +golang.org/x/tools v0.1.1-0.20210205202024-ef80cdb6ec6d/go.mod h1:9bzcO0MWcOuT0tm1iBGzDVPshzfwoVvREIui8C+MHqU= +golang.org/x/tools v0.1.1-0.20210302220138-2ac05c832e1a/go.mod h1:9bzcO0MWcOuT0tm1iBGzDVPshzfwoVvREIui8C+MHqU= +golang.org/x/tools v0.1.1/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= +golang.org/x/tools v0.1.2/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= +golang.org/x/tools v0.1.3/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= +golang.org/x/tools v0.1.4/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= +golang.org/x/tools v0.1.5/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= +golang.org/x/tools v0.1.6/go.mod h1:LGqMHiF4EqQNHR1JncWGqT5BVaXmza+X+BDGol+dOxo= +golang.org/x/tools v0.1.7/go.mod h1:LGqMHiF4EqQNHR1JncWGqT5BVaXmza+X+BDGol+dOxo= +golang.org/x/tools v0.1.10/go.mod h1:Uh6Zz+xoGYZom868N8YTex3t7RhtHDBrE8Gzo9bV56E= +golang.org/x/tools v0.1.11 h1:loJ25fNOEhSXfHrpoGj91eCUThwdNX6u24rO1xnNteY= +golang.org/x/tools v0.1.11/go.mod h1:SgwaegtQh8clINPpECJMqnxLv9I09HLqnW3RMqW0CA4= +golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +golang.org/x/xerrors v0.0.0-20220411194840-2f41105eb62f/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +golang.org/x/xerrors v0.0.0-20220517211312-f3a8303e98df/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8= +golang.org/x/xerrors v0.0.0-20220609144429-65e65417b02f h1:uF6paiQQebLeSXkrTqHqz0MXhXXS1KgF41eUdBNvxK0= +golang.org/x/xerrors v0.0.0-20220609144429-65e65417b02f/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8= +google.golang.org/api v0.0.0-20160322025152-9bf6e6e569ff/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0= +google.golang.org/api v0.3.1/go.mod h1:6wY9I6uQWHQ8EM57III9mq/AjF+i8G65rmVagqKMtkk= +google.golang.org/api v0.4.0/go.mod h1:8k5glujaEP+g9n7WNsDg8QP6cUVNI86fCNMcbazEtwE= +google.golang.org/api v0.5.0/go.mod h1:8k5glujaEP+g9n7WNsDg8QP6cUVNI86fCNMcbazEtwE= +google.golang.org/api v0.6.0/go.mod h1:btoxGiFvQNVUZQ8W08zLtrVS08CNpINPEfxXxgJL1Q4= +google.golang.org/api v0.7.0/go.mod h1:WtwebWUNSVBH/HAw79HIFXZNqEvBhG+Ra+ax0hx3E3M= +google.golang.org/api v0.8.0/go.mod h1:o4eAsZoiT+ibD93RtjEohWalFOjRDx6CVaqeizhEnKg= +google.golang.org/api v0.9.0/go.mod h1:o4eAsZoiT+ibD93RtjEohWalFOjRDx6CVaqeizhEnKg= +google.golang.org/api v0.10.0/go.mod h1:o4eAsZoiT+ibD93RtjEohWalFOjRDx6CVaqeizhEnKg= +google.golang.org/api v0.13.0/go.mod h1:iLdEw5Ide6rF15KTC1Kkl0iskquN2gFfn9o9XIsbkAI= +google.golang.org/api v0.14.0/go.mod h1:iLdEw5Ide6rF15KTC1Kkl0iskquN2gFfn9o9XIsbkAI= +google.golang.org/api v0.15.0/go.mod h1:iLdEw5Ide6rF15KTC1Kkl0iskquN2gFfn9o9XIsbkAI= +google.golang.org/api v0.17.0/go.mod h1:BwFmGc8tA3vsd7r/7kR8DY7iEEGSU04BFxCo5jP/sfE= +google.golang.org/api v0.18.0/go.mod h1:BwFmGc8tA3vsd7r/7kR8DY7iEEGSU04BFxCo5jP/sfE= +google.golang.org/api v0.19.0/go.mod h1:BwFmGc8tA3vsd7r/7kR8DY7iEEGSU04BFxCo5jP/sfE= +google.golang.org/api v0.20.0/go.mod h1:BwFmGc8tA3vsd7r/7kR8DY7iEEGSU04BFxCo5jP/sfE= +google.golang.org/api v0.22.0/go.mod h1:BwFmGc8tA3vsd7r/7kR8DY7iEEGSU04BFxCo5jP/sfE= +google.golang.org/api v0.24.0/go.mod h1:lIXQywCXRcnZPGlsd8NbLnOjtAoL6em04bJ9+z0MncE= +google.golang.org/api v0.28.0/go.mod h1:lIXQywCXRcnZPGlsd8NbLnOjtAoL6em04bJ9+z0MncE= +google.golang.org/api v0.29.0/go.mod h1:Lcubydp8VUV7KeIHD9z2Bys/sm/vGKnG1UHuDBSrHWM= +google.golang.org/api v0.30.0/go.mod h1:QGmEvQ87FHZNiUVJkT14jQNYJ4ZJjdRF23ZXz5138Fc= +google.golang.org/api v0.35.0/go.mod h1:/XrVsuzM0rZmrsbjJutiuftIzeuTQcEeaYcSk/mQ1dg= +google.golang.org/api v0.36.0/go.mod h1:+z5ficQTmoYpPn8LCUNVpK5I7hwkpjbcgqA7I34qYtE= +google.golang.org/api v0.40.0/go.mod h1:fYKFpnQN0DsDSKRVRcQSDQNtqWPfM9i+zNPxepjRCQ8= +google.golang.org/api v0.41.0/go.mod h1:RkxM5lITDfTzmyKFPt+wGrCJbVfniCr2ool8kTBzRTU= +google.golang.org/api v0.43.0/go.mod h1:nQsDGjRXMo4lvh5hP0TKqF244gqhGcr/YSIykhUk/94= +google.golang.org/api v0.44.0/go.mod h1:EBOGZqzyhtvMDoxwS97ctnh0zUmYY6CxqXsc1AvkYD8= +google.golang.org/api v0.45.0/go.mod h1:ISLIJCedJolbZvDfAk+Ctuq5hf+aJ33WgtUsfyFoLXA= +google.golang.org/api v0.46.0/go.mod h1:ceL4oozhkAiTID8XMmJBsIxID/9wMXJVVFXPg4ylg3I= +google.golang.org/api v0.47.0/go.mod h1:Wbvgpq1HddcWVtzsVLyfLp8lDg6AA241LmgIL59tHXo= +google.golang.org/api v0.48.0/go.mod h1:71Pr1vy+TAZRPkPs/xlCf5SsU8WjuAWv1Pfjbtukyy4= +google.golang.org/api v0.50.0/go.mod h1:4bNT5pAuq5ji4SRZm+5QIkjny9JAyVD/3gaSihNefaw= +google.golang.org/api v0.51.0/go.mod h1:t4HdrdoNgyN5cbEfm7Lum0lcLDLiise1F8qDKX00sOU= +google.golang.org/api v0.54.0/go.mod h1:7C4bFFOvVDGXjfDTAsgGwDgAxRDeQ4X8NvUedIt6z3k= +google.golang.org/api v0.55.0/go.mod h1:38yMfeP1kfjsl8isn0tliTjIb1rJXcQi4UXlbqivdVE= +google.golang.org/api v0.56.0/go.mod h1:38yMfeP1kfjsl8isn0tliTjIb1rJXcQi4UXlbqivdVE= +google.golang.org/api v0.57.0/go.mod h1:dVPlbZyBo2/OjBpmvNdpn2GRm6rPy75jyU7bmhdrMgI= +google.golang.org/api v0.58.0/go.mod h1:cAbP2FsxoGVNwtgNAmmn3y5G1TWAiVYRmg4yku3lv+E= +google.golang.org/api v0.59.0/go.mod h1:sT2boj7M9YJxZzgeZqXogmhfmRWDtPzT31xkieUbuZU= +google.golang.org/api v0.61.0/go.mod h1:xQRti5UdCmoCEqFxcz93fTl338AVqDgyaDRuOZ3hg9I= +google.golang.org/api v0.63.0/go.mod h1:gs4ij2ffTRXwuzzgJl/56BdwJaA194ijkfn++9tDuPo= +google.golang.org/api v0.64.0/go.mod h1:931CdxA8Rm4t6zqTFGSsgwbAEZ2+GMYurbndwSimebM= +google.golang.org/api v0.67.0/go.mod h1:ShHKP8E60yPsKNw/w8w+VYaj9H6buA5UqDp8dhbQZ6g= +google.golang.org/api v0.70.0/go.mod h1:Bs4ZM2HGifEvXwd50TtW70ovgJffJYw2oRCOFU/SkfA= +google.golang.org/api v0.71.0/go.mod h1:4PyU6e6JogV1f9eA4voyrTY2batOLdgZ5qZ5HOCc4j8= +google.golang.org/api v0.74.0/go.mod h1:ZpfMZOVRMywNyvJFeqL9HRWBgAuRfSjJFpe9QtRRyDs= +google.golang.org/api v0.75.0/go.mod h1:pU9QmyHLnzlpar1Mjt4IbapUCy8J+6HD6GeELN69ljA= +google.golang.org/api v0.77.0/go.mod h1:pU9QmyHLnzlpar1Mjt4IbapUCy8J+6HD6GeELN69ljA= +google.golang.org/api v0.78.0/go.mod h1:1Sg78yoMLOhlQTeF+ARBoytAcH1NNyyl390YMy6rKmw= +google.golang.org/api v0.80.0/go.mod h1:xY3nI94gbvBrE0J6NHXhxOmW97HG7Khjkku6AFB3Hyg= +google.golang.org/api v0.84.0/go.mod h1:NTsGnUFJMYROtiquksZHBWtHfeMC7iYthki7Eq3pa8o= +google.golang.org/api v0.93.0 h1:T2xt9gi0gHdxdnRkVQhT8mIvPaXKNsDNWz+L696M66M= +google.golang.org/api v0.93.0/go.mod h1:+Sem1dnrKlrXMR/X0bPnMWyluQe4RsNoYfmNLhOIkzw= +google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= +google.golang.org/appengine v1.2.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= +google.golang.org/appengine v1.3.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= +google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= +google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= +google.golang.org/appengine v1.6.1/go.mod h1:i06prIuMbXzDqacNJfV5OdTW448YApPu5ww/cMBSeb0= +google.golang.org/appengine v1.6.2/go.mod h1:i06prIuMbXzDqacNJfV5OdTW448YApPu5ww/cMBSeb0= +google.golang.org/appengine v1.6.5/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= +google.golang.org/appengine v1.6.6/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= +google.golang.org/appengine v1.6.7 h1:FZR1q0exgwxzPzp/aF+VccGrSfxfPpkBqjIIEq3ru6c= +google.golang.org/appengine v1.6.7/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= +google.golang.org/cloud v0.0.0-20151119220103-975617b05ea8/go.mod h1:0H1ncTHf11KCFhTc/+EFRbzSCOZx+VUbRMk55Yv5MYk= +google.golang.org/genproto v0.0.0-20170818010345-ee236bd376b0/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc= +google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc= +google.golang.org/genproto v0.0.0-20181107211654-5fc9ac540362/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc= +google.golang.org/genproto v0.0.0-20190307195333-5fe7a883aa19/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= +google.golang.org/genproto v0.0.0-20190418145605-e7d98fc518a7/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= +google.golang.org/genproto v0.0.0-20190425155659-357c62f0e4bb/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= +google.golang.org/genproto v0.0.0-20190502173448-54afdca5d873/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= +google.golang.org/genproto v0.0.0-20190508193815-b515fa19cec8/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= +google.golang.org/genproto v0.0.0-20190522204451-c2c4e71fbf69/go.mod h1:z3L6/3dTEVtUr6QSP8miRzeRqwQOioJ9I66odjN4I7s= +google.golang.org/genproto v0.0.0-20190530194941-fb225487d101/go.mod h1:z3L6/3dTEVtUr6QSP8miRzeRqwQOioJ9I66odjN4I7s= +google.golang.org/genproto v0.0.0-20190620144150-6af8c5fc6601/go.mod h1:z3L6/3dTEVtUr6QSP8miRzeRqwQOioJ9I66odjN4I7s= +google.golang.org/genproto v0.0.0-20190801165951-fa694d86fc64/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc= +google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc= +google.golang.org/genproto v0.0.0-20190911173649-1774047e7e51/go.mod h1:IbNlFCBrqXvoKpeg0TB2l7cyZUmoaFKYIwrEpbDKLA8= +google.golang.org/genproto v0.0.0-20190927181202-20e1ac93f88c/go.mod h1:IbNlFCBrqXvoKpeg0TB2l7cyZUmoaFKYIwrEpbDKLA8= +google.golang.org/genproto v0.0.0-20191108220845-16a3f7862a1a/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= +google.golang.org/genproto v0.0.0-20191115194625-c23dd37a84c9/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= +google.golang.org/genproto v0.0.0-20191216164720-4f79533eabd1/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= +google.golang.org/genproto v0.0.0-20191230161307-f3c370f40bfb/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= +google.golang.org/genproto v0.0.0-20200115191322-ca5a22157cba/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= +google.golang.org/genproto v0.0.0-20200117163144-32f20d992d24/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= +google.golang.org/genproto v0.0.0-20200122232147-0452cf42e150/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= +google.golang.org/genproto v0.0.0-20200204135345-fa8e72b47b90/go.mod h1:GmwEX6Z4W5gMy59cAlVYjN9JhxgbQH6Gn+gFDQe2lzA= +google.golang.org/genproto v0.0.0-20200212174721-66ed5ce911ce/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200224152610-e50cd9704f63/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200228133532-8c2c7df3a383/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200305110556-506484158171/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200312145019-da6875a35672/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200331122359-1ee6d9798940/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200423170343-7949de9c1215/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200430143042-b979b6f78d84/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200511104702-f5ebc3bea380/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200513103714-09dca8ec2884/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200515170657-fc4c6c6a6587/go.mod h1:YsZOwe1myG/8QRHRsmBRE1LrgQY60beZKjly0O1fX9U= +google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013/go.mod h1:NbSheEEYHJ7i3ixzK3sjbqSGDJWnxyFXZblF3eUsNvo= +google.golang.org/genproto v0.0.0-20200618031413-b414f8b61790/go.mod h1:jDfRM7FcilCzHH/e9qn6dsT145K34l5v+OpcnNgKAAA= +google.golang.org/genproto v0.0.0-20200626011028-ee7919e894b5/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20200707001353-8e8330bf89df/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20200729003335-053ba62fc06f/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20200804131852-c06518451d9c/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20200806141610-86f49bd18e98/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20200825200019-8632dd797987/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20200904004341-0bd0a958aa1d/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20201019141844-1ed22bb0c154/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20201109203340-2640f1f9cdfb/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20201110150050-8816d57aaa9a/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20201201144952-b05cb90ed32e/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20201210142538-e3217bee35cc/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20201214200347-8c77b98c765d/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20210108203827-ffc7fda8c3d7/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20210222152913-aa3ee6e6a81c/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20210226172003-ab064af71705/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20210303154014-9728d6b83eeb/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20210310155132-4ce2db91004e/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20210319143718-93e7006c17a6/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20210325141258-5636347f2b14/go.mod h1:f2Bd7+2PlaVKmvKQ52aspJZXIDaRQBVdOOBfJ5i8OEs= +google.golang.org/genproto v0.0.0-20210329143202-679c6ae281ee/go.mod h1:9lPAdzaEmUacj36I+k7YKbEc5CXzPIeORRgDAUOu28A= +google.golang.org/genproto v0.0.0-20210331142528-b7513248f0ba/go.mod h1:9lPAdzaEmUacj36I+k7YKbEc5CXzPIeORRgDAUOu28A= +google.golang.org/genproto v0.0.0-20210402141018-6c239bbf2bb1/go.mod h1:9lPAdzaEmUacj36I+k7YKbEc5CXzPIeORRgDAUOu28A= +google.golang.org/genproto v0.0.0-20210406143921-e86de6bf7a46/go.mod h1:P3QM42oQyzQSnHPnZ/vqoCdDmzH28fzWByN9asMeM8A= +google.golang.org/genproto v0.0.0-20210413151531-c14fb6ef47c3/go.mod h1:P3QM42oQyzQSnHPnZ/vqoCdDmzH28fzWByN9asMeM8A= +google.golang.org/genproto v0.0.0-20210420162539-3c870d7478d2/go.mod h1:P3QM42oQyzQSnHPnZ/vqoCdDmzH28fzWByN9asMeM8A= +google.golang.org/genproto v0.0.0-20210427215850-f767ed18ee4d/go.mod h1:P3QM42oQyzQSnHPnZ/vqoCdDmzH28fzWByN9asMeM8A= +google.golang.org/genproto v0.0.0-20210429181445-86c259c2b4ab/go.mod h1:P3QM42oQyzQSnHPnZ/vqoCdDmzH28fzWByN9asMeM8A= +google.golang.org/genproto v0.0.0-20210513213006-bf773b8c8384/go.mod h1:P3QM42oQyzQSnHPnZ/vqoCdDmzH28fzWByN9asMeM8A= +google.golang.org/genproto v0.0.0-20210602131652-f16073e35f0c/go.mod h1:UODoCrxHCcBojKKwX1terBiRUaqAsFqJiF615XL43r0= +google.golang.org/genproto v0.0.0-20210604141403-392c879c8b08/go.mod h1:UODoCrxHCcBojKKwX1terBiRUaqAsFqJiF615XL43r0= +google.golang.org/genproto v0.0.0-20210608205507-b6d2f5bf0d7d/go.mod h1:UODoCrxHCcBojKKwX1terBiRUaqAsFqJiF615XL43r0= +google.golang.org/genproto v0.0.0-20210624195500-8bfb893ecb84/go.mod h1:SzzZ/N+nwJDaO1kznhnlzqS8ocJICar6hYhVyhi++24= +google.golang.org/genproto v0.0.0-20210713002101-d411969a0d9a/go.mod h1:AxrInvYm1dci+enl5hChSFPOmmUF1+uAa/UsgNRWd7k= +google.golang.org/genproto v0.0.0-20210716133855-ce7ef5c701ea/go.mod h1:AxrInvYm1dci+enl5hChSFPOmmUF1+uAa/UsgNRWd7k= +google.golang.org/genproto v0.0.0-20210728212813-7823e685a01f/go.mod h1:ob2IJxKrgPT52GcgX759i1sleT07tiKowYBGbczaW48= +google.golang.org/genproto v0.0.0-20210805201207-89edb61ffb67/go.mod h1:ob2IJxKrgPT52GcgX759i1sleT07tiKowYBGbczaW48= +google.golang.org/genproto v0.0.0-20210813162853-db860fec028c/go.mod h1:cFeNkxwySK631ADgubI+/XFU/xp8FD5KIVV4rj8UC5w= +google.golang.org/genproto v0.0.0-20210821163610-241b8fcbd6c8/go.mod h1:eFjDcFEctNawg4eG61bRv87N7iHBWyVhJu7u1kqDUXY= +google.golang.org/genproto v0.0.0-20210828152312-66f60bf46e71/go.mod h1:eFjDcFEctNawg4eG61bRv87N7iHBWyVhJu7u1kqDUXY= +google.golang.org/genproto v0.0.0-20210831024726-fe130286e0e2/go.mod h1:eFjDcFEctNawg4eG61bRv87N7iHBWyVhJu7u1kqDUXY= +google.golang.org/genproto v0.0.0-20210903162649-d08c68adba83/go.mod h1:eFjDcFEctNawg4eG61bRv87N7iHBWyVhJu7u1kqDUXY= +google.golang.org/genproto v0.0.0-20210909211513-a8c4777a87af/go.mod h1:eFjDcFEctNawg4eG61bRv87N7iHBWyVhJu7u1kqDUXY= +google.golang.org/genproto v0.0.0-20210917145530-b395a37504d4/go.mod h1:eFjDcFEctNawg4eG61bRv87N7iHBWyVhJu7u1kqDUXY= +google.golang.org/genproto v0.0.0-20210921142501-181ce0d877f6/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20210924002016-3dee208752a0/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20211008145708-270636b82663/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20211018162055-cf77aa76bad2/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20211111162719-482062a4217b/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20211118181313-81c1377c94b1/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20211206160659-862468c7d6e0/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20211208223120-3a66f561d7aa/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20211221195035-429b39de9b1c/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20211223182754-3ac035c7e7cb/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20220111164026-67b88f271998/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20220126215142-9970aeb2e350/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20220207164111-0872dc986b00/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= +google.golang.org/genproto v0.0.0-20220218161850-94dd64e39d7c/go.mod h1:kGP+zUP2Ddo0ayMi4YuN7C3WZyJvGLZRh8Z5wnAqvEI= +google.golang.org/genproto v0.0.0-20220222213610-43724f9ea8cf/go.mod h1:kGP+zUP2Ddo0ayMi4YuN7C3WZyJvGLZRh8Z5wnAqvEI= +google.golang.org/genproto v0.0.0-20220304144024-325a89244dc8/go.mod h1:kGP+zUP2Ddo0ayMi4YuN7C3WZyJvGLZRh8Z5wnAqvEI= +google.golang.org/genproto v0.0.0-20220310185008-1973136f34c6/go.mod h1:kGP+zUP2Ddo0ayMi4YuN7C3WZyJvGLZRh8Z5wnAqvEI= +google.golang.org/genproto v0.0.0-20220324131243-acbaeb5b85eb/go.mod h1:hAL49I2IFola2sVEjAn7MEwsja0xp51I0tlGAf9hz4E= +google.golang.org/genproto v0.0.0-20220407144326-9054f6ed7bac/go.mod h1:8w6bsBMX6yCPbAVTeqQHvzxW0EIFigd5lZyahWgyfDo= +google.golang.org/genproto v0.0.0-20220413183235-5e96e2839df9/go.mod h1:8w6bsBMX6yCPbAVTeqQHvzxW0EIFigd5lZyahWgyfDo= +google.golang.org/genproto v0.0.0-20220414192740-2d67ff6cf2b4/go.mod h1:8w6bsBMX6yCPbAVTeqQHvzxW0EIFigd5lZyahWgyfDo= +google.golang.org/genproto v0.0.0-20220421151946-72621c1f0bd3/go.mod h1:8w6bsBMX6yCPbAVTeqQHvzxW0EIFigd5lZyahWgyfDo= +google.golang.org/genproto v0.0.0-20220422154200-b37d22cd5731/go.mod h1:8w6bsBMX6yCPbAVTeqQHvzxW0EIFigd5lZyahWgyfDo= +google.golang.org/genproto v0.0.0-20220426171045-31bebdecfb46/go.mod h1:8w6bsBMX6yCPbAVTeqQHvzxW0EIFigd5lZyahWgyfDo= +google.golang.org/genproto v0.0.0-20220429170224-98d788798c3e/go.mod h1:8w6bsBMX6yCPbAVTeqQHvzxW0EIFigd5lZyahWgyfDo= +google.golang.org/genproto v0.0.0-20220505152158-f39f71e6c8f3/go.mod h1:RAyBrSAP7Fh3Nc84ghnVLDPuV51xc9agzmm4Ph6i0Q4= +google.golang.org/genproto v0.0.0-20220518221133-4f43b3371335/go.mod h1:RAyBrSAP7Fh3Nc84ghnVLDPuV51xc9agzmm4Ph6i0Q4= +google.golang.org/genproto v0.0.0-20220523171625-347a074981d8/go.mod h1:RAyBrSAP7Fh3Nc84ghnVLDPuV51xc9agzmm4Ph6i0Q4= +google.golang.org/genproto v0.0.0-20220608133413-ed9918b62aac/go.mod h1:KEWEmljWE5zPzLBa/oHl6DaEt9LmfH6WtH1OHIvleBA= +google.golang.org/genproto v0.0.0-20220616135557-88e70c0c3a90/go.mod h1:KEWEmljWE5zPzLBa/oHl6DaEt9LmfH6WtH1OHIvleBA= +google.golang.org/genproto v0.0.0-20220624142145-8cd45d7dbd1f/go.mod h1:KEWEmljWE5zPzLBa/oHl6DaEt9LmfH6WtH1OHIvleBA= +google.golang.org/genproto v0.0.0-20220805133916-01dd62135a58 h1:sRT5xdTkj1Kbk30qbYC7VyMj73N5pZYsw6v+Nrzdhno= +google.golang.org/genproto v0.0.0-20220805133916-01dd62135a58/go.mod h1:iHe1svFLAZg9VWz891+QbRMwUv9O/1Ww+/mngYeThbc= +google.golang.org/grpc v0.0.0-20160317175043-d3ddb4469d5a/go.mod h1:yo6s7OP7yaDglbqo1J04qKzAhqBH6lvTonzMVmEdcZw= +google.golang.org/grpc v1.8.0/go.mod h1:yo6s7OP7yaDglbqo1J04qKzAhqBH6lvTonzMVmEdcZw= +google.golang.org/grpc v1.17.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs= +google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= +google.golang.org/grpc v1.20.0/go.mod h1:chYK+tFQF0nDUGJgXMSgLCQk3phJEuONr2DCgLDdAQM= +google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= +google.golang.org/grpc v1.21.0/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= +google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= +google.golang.org/grpc v1.22.1/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg= +google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg= +google.golang.org/grpc v1.23.1/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg= +google.golang.org/grpc v1.24.0/go.mod h1:XDChyiUovWa60DnaeDeZmSW86xtLtjtZbwvSiRnRtcA= +google.golang.org/grpc v1.25.1/go.mod h1:c3i+UQWmh7LiEpx4sFZnkU36qjEYZ0imhYfXVyQciAY= +google.golang.org/grpc v1.26.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= +google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= +google.golang.org/grpc v1.27.1/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= +google.golang.org/grpc v1.28.0/go.mod h1:rpkK4SK4GF4Ach/+MFLZUBavHOvF2JJB5uozKKal+60= +google.golang.org/grpc v1.29.0/go.mod h1:itym6AZVZYACWQqET3MqgPpjcuV5QH3BxFS3IjizoKk= +google.golang.org/grpc v1.29.1/go.mod h1:itym6AZVZYACWQqET3MqgPpjcuV5QH3BxFS3IjizoKk= +google.golang.org/grpc v1.30.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak= +google.golang.org/grpc v1.31.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak= +google.golang.org/grpc v1.31.1/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak= +google.golang.org/grpc v1.32.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak= +google.golang.org/grpc v1.33.1/go.mod h1:fr5YgcSWrqhRRxogOsw7RzIpsmvOZ6IcH4kBYTpR3n0= +google.golang.org/grpc v1.33.2/go.mod h1:JMHMWHQWaTccqQQlmk3MJZS+GWXOdAesneDmEnv2fbc= +google.golang.org/grpc v1.34.0/go.mod h1:WotjhfgOW/POjDeRt8vscBtXq+2VjORFy659qA51WJ8= +google.golang.org/grpc v1.35.0/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU= +google.golang.org/grpc v1.36.0/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU= +google.golang.org/grpc v1.36.1/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU= +google.golang.org/grpc v1.37.0/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQdJfM= +google.golang.org/grpc v1.37.1/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQdJfM= +google.golang.org/grpc v1.38.0/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQdJfM= +google.golang.org/grpc v1.39.0/go.mod h1:PImNr+rS9TWYb2O4/emRugxiyHZ5JyHW5F+RPnDzfrE= +google.golang.org/grpc v1.39.1/go.mod h1:PImNr+rS9TWYb2O4/emRugxiyHZ5JyHW5F+RPnDzfrE= +google.golang.org/grpc v1.40.0/go.mod h1:ogyxbiOoUXAkP+4+xa6PZSE9DZgIHtSpzjDTB9KAK34= +google.golang.org/grpc v1.40.1/go.mod h1:ogyxbiOoUXAkP+4+xa6PZSE9DZgIHtSpzjDTB9KAK34= +google.golang.org/grpc v1.42.0/go.mod h1:k+4IHHFw41K8+bbowsex27ge2rCb65oeWqe4jJ590SU= +google.golang.org/grpc v1.44.0/go.mod h1:k+4IHHFw41K8+bbowsex27ge2rCb65oeWqe4jJ590SU= +google.golang.org/grpc v1.45.0/go.mod h1:lN7owxKUQEqMfSyQikvvk5tf/6zMPsrK+ONuO11+0rQ= +google.golang.org/grpc v1.46.0/go.mod h1:vN9eftEi1UMyUsIF80+uQXhHjbXYbm0uXoFCACuMGWk= +google.golang.org/grpc v1.46.2/go.mod h1:vN9eftEi1UMyUsIF80+uQXhHjbXYbm0uXoFCACuMGWk= +google.golang.org/grpc v1.47.0/go.mod h1:vN9eftEi1UMyUsIF80+uQXhHjbXYbm0uXoFCACuMGWk= +google.golang.org/grpc v1.48.0 h1:rQOsyJ/8+ufEDJd/Gdsz7HG220Mh9HAhFHRGnIjda0w= +google.golang.org/grpc v1.48.0/go.mod h1:vN9eftEi1UMyUsIF80+uQXhHjbXYbm0uXoFCACuMGWk= +google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.1.0/go.mod h1:6Kw0yEErY5E/yWrBtf03jp27GLLJujG4z/JK95pnjjw= +google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.2.0/go.mod h1:DNq5QpG7LJqD2AamLZ7zvKE0DEpVl2BSEVjFycAAjRY= +google.golang.org/grpc/examples v0.0.0-20201130180447-c456688b1860/go.mod h1:Ly7ZA/ARzg8fnPU9TyZIxoz33sEUuWX7txiqs8lPTgE= +google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= +google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= +google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM= +google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= +google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= +google.golang.org/protobuf v1.22.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= +google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= +google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= +google.golang.org/protobuf v1.24.0/go.mod h1:r/3tXBNzIEhYS9I1OUVjXDlt8tc493IdKGjtUeSXeh4= +google.golang.org/protobuf v1.25.0/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlbajtzgsN7c= +google.golang.org/protobuf v1.25.1-0.20200805231151-a709e31e5d12/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlbajtzgsN7c= +google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= +google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= +google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= +google.golang.org/protobuf v1.28.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= +google.golang.org/protobuf v1.28.1 h1:d0NfwRgPtno5B1Wa6L2DAG+KivqkdutMf1UhdNx175w= +google.golang.org/protobuf v1.28.1/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= +gopkg.in/airbrake/gobrake.v2 v2.0.9/go.mod h1:/h5ZAUhDkGaJfjzjKLSjv6zCL6O0LLBxU4K+aSYdM/U= +gopkg.in/alecthomas/kingpin.v2 v2.2.6/go.mod h1:FMv+mEhP44yOT+4EoQTLFTRgOQ1FBLkstjWtayDeSgw= +gopkg.in/alexcesaro/statsd.v2 v2.0.0 h1:FXkZSCZIH17vLCO5sO2UucTHsH9pc+17F6pl3JVCwMc= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20141024133853-64131543e789/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q= +gopkg.in/cheggaaa/pb.v1 v1.0.25/go.mod h1:V/YB90LKu/1FcN3WVnfiiE5oMCibMjukxqG/qStrOgw= +gopkg.in/cheggaaa/pb.v1 v1.0.28 h1:n1tBJnnK2r7g9OW2btFH91V92STTUevLXYFb8gy9EMk= +gopkg.in/cheggaaa/pb.v1 v1.0.28/go.mod h1:V/YB90LKu/1FcN3WVnfiiE5oMCibMjukxqG/qStrOgw= +gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI= +gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys= +gopkg.in/gcfg.v1 v1.2.3/go.mod h1:yesOnuUOFQAhST5vPY4nbZsb/huCgGGXlipJsBn0b3o= +gopkg.in/gemnasium/logrus-airbrake-hook.v2 v2.1.2/go.mod h1:Xk6kEKp8OKb+X14hQBKWaSkCsqBpgog8nAV2xsGOxlo= +gopkg.in/inf.v0 v0.9.1 h1:73M5CoZyi3ZLMOyDlQh031Cx6N9NDJ2Vvfl76EDAgDc= +gopkg.in/inf.v0 v0.9.1/go.mod h1:cWUDdTG/fYaXco+Dcufb5Vnc6Gp2YChqWtbxRZE0mXw= +gopkg.in/ini.v1 v1.51.0/go.mod h1:pNLf8WUiyNEtQjuu5G5vTm06TEv9tsIgeAvK8hOrP4k= +gopkg.in/ini.v1 v1.62.0/go.mod h1:pNLf8WUiyNEtQjuu5G5vTm06TEv9tsIgeAvK8hOrP4k= +gopkg.in/ini.v1 v1.63.2/go.mod h1:pNLf8WUiyNEtQjuu5G5vTm06TEv9tsIgeAvK8hOrP4k= +gopkg.in/ini.v1 v1.67.0 h1:Dgnx+6+nfE+IfzjUEISNeydPJh9AXNNsWbGP9KzCsOA= +gopkg.in/ini.v1 v1.67.0/go.mod h1:pNLf8WUiyNEtQjuu5G5vTm06TEv9tsIgeAvK8hOrP4k= +gopkg.in/linkedin/goavro.v1 v1.0.5/go.mod h1:Aw5GdAbizjOEl0kAMHV9iHmA8reZzW/OKuJAl4Hb9F0= +gopkg.in/natefinch/lumberjack.v2 v2.0.0 h1:1Lc07Kr7qY4U2YPouBjpCLxpiyxIVoxqXgkXLknAOE8= +gopkg.in/natefinch/lumberjack.v2 v2.0.0/go.mod h1:l0ndWWf7gzL7RNwBG7wST/UCcT4T24xpD6X8LsfU/+k= +gopkg.in/resty.v1 v1.12.0/go.mod h1:mDo4pnntr5jdWRML875a/NmxYqAlA73dVijT2AXvQQo= +gopkg.in/square/go-jose.v2 v2.2.2/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= +gopkg.in/square/go-jose.v2 v2.3.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= +gopkg.in/square/go-jose.v2 v2.4.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= +gopkg.in/square/go-jose.v2 v2.5.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= +gopkg.in/square/go-jose.v2 v2.6.0 h1:NGk74WTnPKBNUhNzQX7PYcTLUjoq7mzKk2OKbvwk2iI= +gopkg.in/square/go-jose.v2 v2.6.0/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= +gopkg.in/src-d/go-billy.v4 v4.3.2/go.mod h1:nDjArDMp+XMs1aFAESLRjfGSgfvoYN0hDfzEk0GjC98= +gopkg.in/src-d/go-git-fixtures.v3 v3.5.0/go.mod h1:dLBcvytrw/TYZsNTWCnkNF2DSIlzWYqTe3rJR56Ac7g= +gopkg.in/src-d/go-git.v4 v4.13.1/go.mod h1:nx5NYcxdKxq5fpltdHnPa2Exj4Sx0EclMWZQbYDu2z8= +gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 h1:uRGJdciOHaEIrze2W8Q3AKkepLTh2hOroT7a+7czfdQ= +gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw= +gopkg.in/warnings.v0 v0.1.2/go.mod h1:jksf8JmL6Qr/oQM2OXTHunEvvTAsrWBLb6OOjuVWRNI= +gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7/go.mod h1:JAlM8MvJe8wmxCU4Bli9HhUf9+ttbYbLASfIpnQbh74= +gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.3/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.5/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.6/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.8/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= +gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= +gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20200605160147-a5ece683394c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= +gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gotest.tools v2.2.0+incompatible h1:VsBPFP1AI068pPrMxtb/S8Zkgf9xEmTLJjfM+P5UIEo= +gotest.tools v2.2.0+incompatible/go.mod h1:DsYFclhRJ6vuDpmuTbkuFWG+y2sxOXAzmJt81HFBacw= +gotest.tools/v3 v3.0.2/go.mod h1:3SzNCllyD9/Y+b5r9JIKQ474KzkZyqLqEfYqMsX94Bk= +gotest.tools/v3 v3.0.3/go.mod h1:Z7Lb0S5l+klDB31fvDQX8ss/FlKDxtlFlw3Oa8Ymbl8= +gotest.tools/v3 v3.1.0 h1:rVV8Tcg/8jHUkPUorwjaMTtemIMVXfIPKiOqnhEhakk= +honnef.co/go/tools v0.0.0-20180728063816-88497007e858/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= +honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= +honnef.co/go/tools v0.0.0-20190106161140-3f1c8253044a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= +honnef.co/go/tools v0.0.0-20190418001031-e561f6794a2a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= +honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= +honnef.co/go/tools v0.0.1-2019.2.3/go.mod h1:a3bituU0lyd329TUQxRnasdCoJDkEUEAqEt0JzvZhAg= +honnef.co/go/tools v0.0.1-2020.1.3/go.mod h1:X/FiERA/W4tHapMX5mGpAtMSVEeEUOyHaw9vFzvIQ3k= +honnef.co/go/tools v0.0.1-2020.1.4/go.mod h1:X/FiERA/W4tHapMX5mGpAtMSVEeEUOyHaw9vFzvIQ3k= +honnef.co/go/tools v0.0.1-2020.1.5/go.mod h1:X/FiERA/W4tHapMX5mGpAtMSVEeEUOyHaw9vFzvIQ3k= +honnef.co/go/tools v0.2.1/go.mod h1:lPVVZ2BS5TfnjLyizF7o7hv7j9/L+8cZY2hLyjP9cGY= +k8s.io/api v0.20.1/go.mod h1:KqwcCVogGxQY3nBlRpwt+wpAMF/KjaCc7RpywacvqUo= +k8s.io/api v0.20.4/go.mod h1:++lNL1AJMkDymriNniQsWRkMDzRaX2Y/POTUi8yvqYQ= +k8s.io/api v0.20.6/go.mod h1:X9e8Qag6JV/bL5G6bU8sdVRltWKmdHsFUGS3eVndqE8= +k8s.io/api v0.23.5 h1:zno3LUiMubxD/V1Zw3ijyKO3wxrhbUF1Ck+VjBvfaoA= +k8s.io/api v0.23.5/go.mod h1:Na4XuKng8PXJ2JsploYYrivXrINeTaycCGcYgF91Xm8= +k8s.io/apimachinery v0.20.1/go.mod h1:WlLqWAHZGg07AeltaI0MV5uk1Omp8xaN0JGLY6gkRpU= +k8s.io/apimachinery v0.20.4/go.mod h1:WlLqWAHZGg07AeltaI0MV5uk1Omp8xaN0JGLY6gkRpU= +k8s.io/apimachinery v0.20.6/go.mod h1:ejZXtW1Ra6V1O5H8xPBGz+T3+4gfkTCeExAHKU57MAc= +k8s.io/apimachinery v0.23.5 h1:Va7dwhp8wgkUPWsEXk6XglXWU4IKYLKNlv8VkX7SDM0= +k8s.io/apimachinery v0.23.5/go.mod h1:BEuFMMBaIbcOqVIJqNZJXGFTP4W6AycEpb5+m/97hrM= +k8s.io/apiserver v0.20.1/go.mod h1:ro5QHeQkgMS7ZGpvf4tSMx6bBOgPfE+f52KwvXfScaU= +k8s.io/apiserver v0.20.4/go.mod h1:Mc80thBKOyy7tbvFtB4kJv1kbdD0eIH8k8vianJcbFM= +k8s.io/apiserver v0.20.6/go.mod h1:QIJXNt6i6JB+0YQRNcS0hdRHJlMhflFmsBDeSgT1r8Q= +k8s.io/client-go v0.20.1/go.mod h1:/zcHdt1TeWSd5HoUe6elJmHSQ6uLLgp4bIJHVEuy+/Y= +k8s.io/client-go v0.20.4/go.mod h1:LiMv25ND1gLUdBeYxBIwKpkSC5IsozMMmOOeSJboP+k= +k8s.io/client-go v0.20.6/go.mod h1:nNQMnOvEUEsOzRRFIIkdmYOjAZrC8bgq0ExboWSU1I0= +k8s.io/client-go v0.23.5 h1:zUXHmEuqx0RY4+CsnkOn5l0GU+skkRXKGJrhmE2SLd8= +k8s.io/client-go v0.23.5/go.mod h1:flkeinTO1CirYgzMPRWxUCnV0G4Fbu2vLhYCObnt/r4= +k8s.io/component-base v0.20.1/go.mod h1:guxkoJnNoh8LNrbtiQOlyp2Y2XFCZQmrcg2n/DeYNLk= +k8s.io/component-base v0.20.4/go.mod h1:t4p9EdiagbVCJKrQ1RsA5/V4rFQNDfRlevJajlGwgjI= +k8s.io/component-base v0.20.6/go.mod h1:6f1MPBAeI+mvuts3sIdtpjljHWBQ2cIy38oBIWMYnrM= +k8s.io/cri-api v0.17.3/go.mod h1:X1sbHmuXhwaHs9xxYffLqJogVsnI+f6cPRcgPel7ywM= +k8s.io/cri-api v0.20.1/go.mod h1:2JRbKt+BFLTjtrILYVqQK5jqhI+XNdF6UiGMgczeBCI= +k8s.io/cri-api v0.20.4/go.mod h1:2JRbKt+BFLTjtrILYVqQK5jqhI+XNdF6UiGMgczeBCI= +k8s.io/cri-api v0.20.6/go.mod h1:ew44AjNXwyn1s0U4xCKGodU7J1HzBeZ1MpGrpa5r8Yc= +k8s.io/gengo v0.0.0-20200413195148-3a45101e95ac/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0= +k8s.io/gengo v0.0.0-20210813121822-485abfe95c7c/go.mod h1:FiNAH4ZV3gBg2Kwh89tzAEV2be7d5xI0vBa/VySYy3E= +k8s.io/klog/v2 v2.0.0/go.mod h1:PBfzABfn139FHAV07az/IF9Wp1bkk3vpT2XSJ76fSDE= +k8s.io/klog/v2 v2.2.0/go.mod h1:Od+F08eJP+W3HUb4pSrPpgp9DGU4GzlpG/TmITuYh/Y= +k8s.io/klog/v2 v2.4.0/go.mod h1:Od+F08eJP+W3HUb4pSrPpgp9DGU4GzlpG/TmITuYh/Y= +k8s.io/klog/v2 v2.30.0/go.mod h1:y1WjHnz7Dj687irZUWR/WLkLc5N1YHtjLdmgWjndZn0= +k8s.io/klog/v2 v2.60.1-0.20220317184644-43cc75f9ae89 h1:bUNlsw5yb353zbKMj8srOr6V2Ajhz1VkTKonP1L8r2o= +k8s.io/klog/v2 v2.60.1-0.20220317184644-43cc75f9ae89/go.mod h1:N3kgBtsFxMb4nQ0eBDgbHEt/dtxBuTkSFQ+7K5OUoz4= +k8s.io/kube-openapi v0.0.0-20201113171705-d219536bb9fd/go.mod h1:WOJ3KddDSol4tAGcJo0Tvi+dK12EcqSLqcWsryKMpfM= +k8s.io/kube-openapi v0.0.0-20211115234752-e816edb12b65/go.mod h1:sX9MT8g7NVZM5lVL/j8QyCCJe8YSMW30QvGZWaCIDIk= +k8s.io/kube-openapi v0.0.0-20220124234850-424119656bbf h1:M9XBsiMslw2lb2ZzglC0TOkBPK5NQi0/noUrdnoFwUg= +k8s.io/kube-openapi v0.0.0-20220124234850-424119656bbf/go.mod h1:sX9MT8g7NVZM5lVL/j8QyCCJe8YSMW30QvGZWaCIDIk= +k8s.io/kubernetes v1.13.0/go.mod h1:ocZa8+6APFNC2tX1DZASIbocyYT5jHzqFVsY5aoB7Jk= +k8s.io/utils v0.0.0-20201110183641-67b214c5f920/go.mod h1:jPW/WVKK9YHAvNhRxK0md/EJ228hCsBRufyofKtW8HA= +k8s.io/utils v0.0.0-20210802155522-efc7438f0176/go.mod h1:jPW/WVKK9YHAvNhRxK0md/EJ228hCsBRufyofKtW8HA= +k8s.io/utils v0.0.0-20211116205334-6203023598ed/go.mod h1:jPW/WVKK9YHAvNhRxK0md/EJ228hCsBRufyofKtW8HA= +k8s.io/utils v0.0.0-20220210201930-3a6ce19ff2f9 h1:HNSDgDCrr/6Ly3WEGKZftiE7IY19Vz2GdbOCyI4qqhc= +k8s.io/utils v0.0.0-20220210201930-3a6ce19ff2f9/go.mod h1:jPW/WVKK9YHAvNhRxK0md/EJ228hCsBRufyofKtW8HA= +lukechampine.com/uint128 v1.1.1 h1:pnxCASz787iMf+02ssImqk6OLt+Z5QHMoZyUXR4z6JU= +lukechampine.com/uint128 v1.1.1/go.mod h1:c4eWIwlEGaxC/+H1VguhU4PHXNWDCDMUlWdIWl2j1gk= +modernc.org/cc/v3 v3.36.0 h1:0kmRkTmqNidmu3c7BNDSdVHCxXCkWLmWmCIVX4LUboo= +modernc.org/cc/v3 v3.36.0/go.mod h1:NFUHyPn4ekoC/JHeZFfZurN6ixxawE1BnVonP/oahEI= +modernc.org/ccgo/v3 v3.0.0-20220428102840-41399a37e894/go.mod h1:eI31LL8EwEBKPpNpA4bU1/i+sKOwOrQy8D87zWUcRZc= +modernc.org/ccgo/v3 v3.0.0-20220430103911-bc99d88307be/go.mod h1:bwdAnOoaIt8Ax9YdWGjxWsdkPcZyRPHqrOvJxaKAKGw= +modernc.org/ccgo/v3 v3.16.4/go.mod h1:tGtX0gE9Jn7hdZFeU88slbTh1UtCYKusWOoCJuvkWsQ= +modernc.org/ccgo/v3 v3.16.6 h1:3l18poV+iUemQ98O3X5OMr97LOqlzis+ytivU4NqGhA= +modernc.org/ccgo/v3 v3.16.6/go.mod h1:tGtX0gE9Jn7hdZFeU88slbTh1UtCYKusWOoCJuvkWsQ= +modernc.org/ccorpus v1.11.6 h1:J16RXiiqiCgua6+ZvQot4yUuUy8zxgqbqEEUuGPlISk= +modernc.org/ccorpus v1.11.6/go.mod h1:2gEUTrWqdpH2pXsmTM1ZkjeSrUWDpjMu2T6m29L/ErQ= +modernc.org/httpfs v1.0.6 h1:AAgIpFZRXuYnkjftxTAZwMIiwEqAfk8aVB2/oA6nAeM= +modernc.org/httpfs v1.0.6/go.mod h1:7dosgurJGp0sPaRanU53W4xZYKh14wfzX420oZADeHM= +modernc.org/libc v0.0.0-20220428101251-2d5f3daf273b/go.mod h1:p7Mg4+koNjc8jkqwcoFBJx7tXkpj00G77X7A72jXPXA= +modernc.org/libc v1.16.0/go.mod h1:N4LD6DBE9cf+Dzf9buBlzVJndKr/iJHG97vGLHYnb5A= +modernc.org/libc v1.16.1/go.mod h1:JjJE0eu4yeK7tab2n4S1w8tlWd9MxXLRzheaRnAKymU= +modernc.org/libc v1.16.7 h1:qzQtHhsZNpVPpeCu+aMIQldXeV1P0vRhSqCL0nOIJOA= +modernc.org/libc v1.16.7/go.mod h1:hYIV5VZczAmGZAnG15Vdngn5HSF5cSkbvfz2B7GRuVU= +modernc.org/mathutil v1.2.2/go.mod h1:mZW8CKdRPY1v87qxC/wUdX5O1qDzXMP5TH3wjfpga6E= +modernc.org/mathutil v1.4.1 h1:ij3fYGe8zBF4Vu+g0oT7mB06r8sqGWKuJu1yXeR4by8= +modernc.org/mathutil v1.4.1/go.mod h1:mZW8CKdRPY1v87qxC/wUdX5O1qDzXMP5TH3wjfpga6E= +modernc.org/memory v1.1.1 h1:bDOL0DIDLQv7bWhP3gMvIrnoFw+Eo6F7a2QK9HPDiFU= +modernc.org/memory v1.1.1/go.mod h1:/0wo5ibyrQiaoUoH7f9D8dnglAmILJ5/cxZlRECf+Nw= +modernc.org/opt v0.1.1 h1:/0RX92k9vwVeDXj+Xn23DKp2VJubL7k8qNffND6qn3A= +modernc.org/opt v0.1.1/go.mod h1:WdSiB5evDcignE70guQKxYUl14mgWtbClRi5wmkkTX0= +modernc.org/sqlite v1.17.3 h1:iE+coC5g17LtByDYDWKpR6m2Z9022YrSh3bumwOnIrI= +modernc.org/sqlite v1.17.3/go.mod h1:10hPVYar9C0kfXuTWGz8s0XtB8uAGymUy51ZzStYe3k= +modernc.org/strutil v1.1.1 h1:xv+J1BXY3Opl2ALrBwyfEikFAj8pmqcpnfmuwUwcozs= +modernc.org/strutil v1.1.1/go.mod h1:DE+MQQ/hjKBZS2zNInV5hhcipt5rLPWkmpbGeW5mmdw= +modernc.org/tcl v1.13.1 h1:npxzTwFTZYM8ghWicVIX1cRWzj7Nd8i6AqqX2p+IYao= +modernc.org/tcl v1.13.1/go.mod h1:XOLfOwzhkljL4itZkK6T72ckMgvj0BDsnKNdZVUOecw= +modernc.org/token v1.0.0 h1:a0jaWiNMDhDUtqOj09wvjWWAqd3q7WpBulmL9H2egsk= +modernc.org/token v1.0.0/go.mod h1:UGzOrNV1mAFSEB63lOFHIpNRUVMvYTc6yu1SMY/XTDM= +modernc.org/z v1.5.1 h1:RTNHdsrOpeoSeOF4FbzTo8gBYByaJ5xT7NgZ9ZqRiJM= +modernc.org/z v1.5.1/go.mod h1:eWFB510QWW5Th9YGZT81s+LwvaAs3Q2yr4sP0rmLkv8= +mvdan.cc/gofumpt v0.1.1/go.mod h1:yXG1r1WqZVKWbVRtBWKWX9+CxGYfA51nSomhM0woR48= +mvdan.cc/interfacer v0.0.0-20180901003855-c20040233aed/go.mod h1:Xkxe497xwlCKkIaQYRfC7CSLworTXY9RMqwhhCm+8Nc= +mvdan.cc/lint v0.0.0-20170908181259-adc824a0674b/go.mod h1:2odslEg/xrtNQqCYg2/jCoyKnw3vv5biOc3JnIcYfL4= +mvdan.cc/unparam v0.0.0-20210104141923-aac4ce9116a7/go.mod h1:hBpJkZE8H/sb+VRFvw2+rBpHNsTBcvSpk61hr8mzXZE= +pack.ag/amqp v0.11.2/go.mod h1:4/cbmt4EJXSKlG6LCfWHoqmN0uFdy5i/+YFz+fTfhV4= +rsc.io/binaryregexp v0.2.0/go.mod h1:qTv7/COck+e2FymRvadv62gMdZztPaShugOCi3I+8D8= +rsc.io/quote/v3 v3.1.0/go.mod h1:yEA65RcK8LyAZtP9Kv3t0HmxON59tX3rD+tICJqUlj0= +rsc.io/sampler v1.3.0/go.mod h1:T1hPZKmBbMNahiBKFy5HrXp6adAjACjK9JXDnKaTXpA= +sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.0.14/go.mod h1:LEScyzhFmoF5pso/YSeBstl57mOzx9xlU9n85RGrDQg= +sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.0.15/go.mod h1:LEScyzhFmoF5pso/YSeBstl57mOzx9xlU9n85RGrDQg= +sigs.k8s.io/json v0.0.0-20211020170558-c049b76a60c6/go.mod h1:p4QtZmO4uMYipTQNzagwnNoseA6OxSUutVw05NhYDRs= +sigs.k8s.io/json v0.0.0-20211208200746-9f7c6b3444d2 h1:kDi4JBNAsJWfz1aEXhO8Jg87JJaPNLh5tIzYHgStQ9Y= +sigs.k8s.io/json v0.0.0-20211208200746-9f7c6b3444d2/go.mod h1:B+TnT182UBxE84DiCz4CVE26eOSDAeYCpfDnC2kdKMY= +sigs.k8s.io/release-utils v0.7.3 h1:6pS8x6c5RmdUgR9qcg1LO6hjUzuE4Yo9TGZ3DemrZdM= +sigs.k8s.io/release-utils v0.7.3/go.mod h1:n0mVez/1PZYZaZUTJmxewxH3RJ/Lf7JUDh7TG1CASOE= +sigs.k8s.io/structured-merge-diff/v4 v4.0.2/go.mod h1:bJZC9H9iH24zzfZ/41RGcq60oK1F7G282QMXDPYydCw= +sigs.k8s.io/structured-merge-diff/v4 v4.0.3/go.mod h1:bJZC9H9iH24zzfZ/41RGcq60oK1F7G282QMXDPYydCw= +sigs.k8s.io/structured-merge-diff/v4 v4.2.1 h1:bKCqE9GvQ5tiVHn5rfn1r+yao3aLQEaLzkkmAkf+A6Y= +sigs.k8s.io/structured-merge-diff/v4 v4.2.1/go.mod h1:j/nl6xW8vLS49O8YvXW1ocPhZawJtm+Yrr7PPRQ0Vg4= +sigs.k8s.io/yaml v1.1.0/go.mod h1:UJmg0vDUVViEyp3mgSv9WPwZCDxu4rQW1olrI1uml+o= +sigs.k8s.io/yaml v1.2.0/go.mod h1:yfXDCHCao9+ENCvLSE62v9VSji2MKu5jeNfTrofGhJc= +sigs.k8s.io/yaml v1.3.0 h1:a2VclLzOGrwOHDiV8EfBGhvjHvP46CtW5j6POvhYGGo= +sigs.k8s.io/yaml v1.3.0/go.mod h1:GeOyir5tyXNByN85N/dRIT9es5UQNerPYEKK56eTBm8= +sourcegraph.com/sourcegraph/appdash v0.0.0-20190731080439-ebfcffb1b5c0/go.mod h1:hI742Nqp5OhwiqlzhgfbWU4mW4yO10fP+LoT9WOswdU= diff --git a/ci/tools/openeuler-purl/syft-dev/install.sh b/ci/tools/openeuler-purl/syft-dev/install.sh new file mode 100755 index 0000000000000000000000000000000000000000..f118257ed68f812e3926b5cebb93ffbc4c4c2249 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/install.sh @@ -0,0 +1,699 @@ +#!/bin/sh +# note: we require errors to propagate (don't set -e) +set -u + +PROJECT_NAME="syft" +OWNER=anchore +REPO="${PROJECT_NAME}" +GITHUB_DOWNLOAD_PREFIX=https://github.com/${OWNER}/${REPO}/releases/download +INSTALL_SH_BASE_URL=https://raw.githubusercontent.com/${OWNER}/${PROJECT_NAME} +PROGRAM_ARGS=$@ + +# do not change the name of this parameter (this must always be backwards compatible) +DOWNLOAD_TAG_INSTALL_SCRIPT=${DOWNLOAD_TAG_INSTALL_SCRIPT:-true} + +# +# usage [script-name] +# +usage() ( + this=$1 + cat </dev/null +) + +echo_stderr() ( + echo "$@" 1>&2 +) + +_logp=2 +log_set_priority() { + _logp="$1" +} + +log_priority() ( + if test -z "$1"; then + echo "$_logp" + return + fi + [ "$1" -le "$_logp" ] +) + +init_colors() { + RED='' + BLUE='' + PURPLE='' + BOLD='' + RESET='' + # check if stdout is a terminal + if test -t 1 && is_command tput; then + # see if it supports colors + ncolors=$(tput colors) + if test -n "$ncolors" && test $ncolors -ge 8; then + RED='\033[0;31m' + BLUE='\033[0;34m' + PURPLE='\033[0;35m' + BOLD='\033[1m' + RESET='\033[0m' + fi + fi +} + +init_colors + +log_tag() ( + case $1 in + 0) echo "${RED}${BOLD}[error]${RESET}" ;; + 1) echo "${RED}[warn]${RESET}" ;; + 2) echo "[info]${RESET}" ;; + 3) echo "${BLUE}[debug]${RESET}" ;; + 4) echo "${PURPLE}[trace]${RESET}" ;; + *) echo "[$1]" ;; + esac +) + + +log_trace_priority=4 +log_trace() ( + priority=$log_trace_priority + log_priority "$priority" || return 0 + echo_stderr "$(log_tag $priority)" "${@}" "${RESET}" +) + +log_debug_priority=3 +log_debug() ( + priority=$log_debug_priority + log_priority "$priority" || return 0 + echo_stderr "$(log_tag $priority)" "${@}" "${RESET}" +) + +log_info_priority=2 +log_info() ( + priority=$log_info_priority + log_priority "$priority" || return 0 + echo_stderr "$(log_tag $priority)" "${@}" "${RESET}" +) + +log_warn_priority=1 +log_warn() ( + priority=$log_warn_priority + log_priority "$priority" || return 0 + echo_stderr "$(log_tag $priority)" "${@}" "${RESET}" +) + +log_err_priority=0 +log_err() ( + priority=$log_err_priority + log_priority "$priority" || return 0 + echo_stderr "$(log_tag $priority)" "${@}" "${RESET}" +) + +uname_os_check() ( + os=$1 + case "$os" in + darwin) return 0 ;; + dragonfly) return 0 ;; + freebsd) return 0 ;; + linux) return 0 ;; + android) return 0 ;; + nacl) return 0 ;; + netbsd) return 0 ;; + openbsd) return 0 ;; + plan9) return 0 ;; + solaris) return 0 ;; + windows) return 0 ;; + esac + log_err "uname_os_check '$(uname -s)' got converted to '$os' which is not a GOOS value. Please file bug at https://github.com/client9/shlib" + return 1 +) + +uname_arch_check() ( + arch=$1 + case "$arch" in + 386) return 0 ;; + amd64) return 0 ;; + arm64) return 0 ;; + armv5) return 0 ;; + armv6) return 0 ;; + armv7) return 0 ;; + ppc64) return 0 ;; + ppc64le) return 0 ;; + mips) return 0 ;; + mipsle) return 0 ;; + mips64) return 0 ;; + mips64le) return 0 ;; + s390x) return 0 ;; + amd64p32) return 0 ;; + esac + log_err "uname_arch_check '$(uname -m)' got converted to '$arch' which is not a GOARCH value. Please file bug report at https://github.com/client9/shlib" + return 1 +) + +unpack() ( + archive=$1 + + log_trace "unpack(archive=${archive})" + + case "${archive}" in + *.tar.gz | *.tgz) tar --no-same-owner -xzf "${archive}" ;; + *.tar) tar --no-same-owner -xf "${archive}" ;; + *.zip) unzip -q "${archive}" ;; + *.dmg) extract_from_dmg "${archive}" ;; + *) + log_err "unpack unknown archive format for ${archive}" + return 1 + ;; + esac +) + +extract_from_dmg() ( + dmg_file=$1 + + mount_point="/Volumes/tmp-dmg" + hdiutil attach -quiet -nobrowse -mountpoint "${mount_point}" "${dmg_file}" + cp -fR "${mount_point}/." ./ + hdiutil detach -quiet -force "${mount_point}" +) + +http_download_curl() ( + local_file=$1 + source_url=$2 + header=$3 + + log_trace "http_download_curl(local_file=$local_file, source_url=$source_url, header=$header)" + + if [ -z "$header" ]; then + code=$(curl -w '%{http_code}' -sL -o "$local_file" "$source_url") + else + code=$(curl -w '%{http_code}' -sL -H "$header" -o "$local_file" "$source_url") + fi + + if [ "$code" != "200" ]; then + log_err "received HTTP status=$code for url='$source_url'" + return 1 + fi + return 0 +) + +http_download_wget() ( + local_file=$1 + source_url=$2 + header=$3 + + log_trace "http_download_wget(local_file=$local_file, source_url=$source_url, header=$header)" + + if [ -z "$header" ]; then + wget -q -O "$local_file" "$source_url" + else + wget -q --header "$header" -O "$local_file" "$source_url" + fi +) + +http_download() ( + log_debug "http_download(url=$2)" + if is_command curl; then + http_download_curl "$@" + return + elif is_command wget; then + http_download_wget "$@" + return + fi + log_err "http_download unable to find wget or curl" + return 1 +) + +http_copy() ( + tmp=$(mktemp) + http_download "${tmp}" "$1" "$2" || return 1 + body=$(cat "$tmp") + rm -f "${tmp}" + echo "$body" +) + +hash_sha256() ( + TARGET=${1:-/dev/stdin} + if is_command gsha256sum; then + hash=$(gsha256sum "$TARGET") || return 1 + echo "$hash" | cut -d ' ' -f 1 + elif is_command sha256sum; then + hash=$(sha256sum "$TARGET") || return 1 + echo "$hash" | cut -d ' ' -f 1 + elif is_command shasum; then + hash=$(shasum -a 256 "$TARGET" 2>/dev/null) || return 1 + echo "$hash" | cut -d ' ' -f 1 + elif is_command openssl; then + hash=$(openssl -dst openssl dgst -sha256 "$TARGET") || return 1 + echo "$hash" | cut -d ' ' -f a + else + log_err "hash_sha256 unable to find command to compute sha-256 hash" + return 1 + fi +) + +hash_sha256_verify() ( + TARGET=$1 + checksums=$2 + if [ -z "$checksums" ]; then + log_err "hash_sha256_verify checksum file not specified in arg2" + return 1 + fi + BASENAME=${TARGET##*/} + want=$(grep "${BASENAME}" "${checksums}" 2>/dev/null | tr '\t' ' ' | cut -d ' ' -f 1) + if [ -z "$want" ]; then + log_err "hash_sha256_verify unable to find checksum for '${TARGET}' in '${checksums}'" + return 1 + fi + got=$(hash_sha256 "$TARGET") + if [ "$want" != "$got" ]; then + log_err "hash_sha256_verify checksum for '$TARGET' did not verify ${want} vs $got" + return 1 + fi +) + +# ------------------------------------------------------------------------ +# End of functions from https://github.com/client9/shlib +# ------------------------------------------------------------------------ + +# asset_file_exists [path] +# +# returns 1 if the given file does not exist +# +asset_file_exists() ( + path="$1" + if [ ! -f "${path}" ]; then + return 1 + fi +) + + +# github_release_json [owner] [repo] [version] +# +# outputs release json string +# +github_release_json() ( + owner=$1 + repo=$2 + version=$3 + test -z "$version" && version="latest" + giturl="https://github.com/${owner}/${repo}/releases/${version}" + json=$(http_copy "$giturl" "Accept:application/json") + + log_trace "github_release_json(owner=${owner}, repo=${repo}, version=${version}) returned '${json}'" + + test -z "$json" && return 1 + echo "${json}" +) + +# extract_value [key-value-pair] +# +# outputs value from a colon delimited key-value pair +# +extract_value() ( + key_value="$1" + IFS=':' read -r _ value << EOF +${key_value} +EOF + echo "$value" +) + +# extract_json_value [json] [key] +# +# outputs value of the key from the given json string +# +extract_json_value() ( + json="$1" + key="$2" + key_value=$(echo "${json}" | grep -o "\"$key\":[^,]*[,}]" | tr -d '",}') + + extract_value "$key_value" +) + +# github_release_tag [release-json] +# +# outputs release tag string +# +github_release_tag() ( + json="$1" + tag=$(extract_json_value "${json}" "tag_name") + test -z "$tag" && return 1 + echo "$tag" +) + +# download_github_release_checksums [release-url-prefix] [name] [version] [output-dir] +# +# outputs path to the downloaded checksums file +# +download_github_release_checksums() ( + download_url="$1" + name="$2" + version="$3" + output_dir="$4" + + log_trace "download_github_release_checksums(url=${download_url}, name=${name}, version=${version}, output_dir=${output_dir})" + + checksum_filename=${name}_${version}_checksums.txt + checksum_url=${download_url}/${checksum_filename} + output_path="${output_dir}/${checksum_filename}" + + http_download "${output_path}" "${checksum_url}" "" + asset_file_exists "${output_path}" + + log_trace "download_github_release_checksums() returned '${output_path}'" + + echo "${output_path}" +) + +# search_for_asset [checksums-file-path] [name] [os] [arch] [format] +# +# outputs name of the asset to download +# +search_for_asset() ( + checksum_path="$1" + name="$2" + os="$3" + arch="$4" + format="$5" + + log_trace "search_for_asset(checksum-path=${checksum_path}, name=${name}, os=${os}, arch=${arch}, format=${format})" + + asset_glob="${name}_.*_${os}_${arch}.${format}" + output_path=$(grep -o "${asset_glob}" "${checksum_path}" || true) + + log_trace "search_for_asset() returned '${output_path}'" + + echo "${output_path}" +) + +# uname_os +# +# outputs an adjusted os value +# +uname_os() ( + os=$(uname -s | tr '[:upper:]' '[:lower:]') + case "$os" in + cygwin_nt*) os="windows" ;; + mingw*) os="windows" ;; + msys_nt*) os="windows" ;; + esac + + uname_os_check "$os" + + log_trace "uname_os() returned '${os}'" + + echo "$os" +) + +# uname_arch +# +# outputs an adjusted architecture value +# +uname_arch() ( + arch=$(uname -m) + case $arch in + x86_64) arch="amd64" ;; + x86) arch="386" ;; + i686) arch="386" ;; + i386) arch="386" ;; + aarch64) arch="arm64" ;; + armv5*) arch="armv5" ;; + armv6*) arch="armv6" ;; + armv7*) arch="armv7" ;; + esac + + uname_arch_check "${arch}" + + log_trace "uname_arch() returned '${arch}'" + + echo "${arch}" +) + +# get_release_tag [owner] [repo] [tag] +# +# outputs tag string +# +get_release_tag() ( + owner="$1" + repo="$2" + tag="$3" + + log_trace "get_release_tag(owner=${owner}, repo=${repo}, tag=${tag})" + + json=$(github_release_json "${owner}" "${repo}" "${tag}") + real_tag=$(github_release_tag "${json}") + if test -z "${real_tag}"; then + return 1 + fi + + log_trace "get_release_tag() returned '${real_tag}'" + + echo "${real_tag}" +) + +# tag_to_version [tag] +# +# outputs version string +# +tag_to_version() ( + tag="$1" + value="${tag#v}" + + log_trace "tag_to_version(tag=${tag}) returned '${value}'" + + echo "$value" +) + +# get_binary_name [os] [arch] [default-name] +# +# outputs a the binary string name +# +get_binary_name() ( + os="$1" + arch="$2" + binary="$3" + original_binary="${binary}" + + case "${os}" in + windows) binary="${binary}.exe" ;; + esac + + log_trace "get_binary_name(os=${os}, arch=${arch}, binary=${original_binary}) returned '${binary}'" + + echo "${binary}" +) + + +# get_format_name [os] [arch] [default-format] +# +# outputs an adjusted file format +# +get_format_name() ( + os="$1" + arch="$2" + format="$3" + original_format="${format}" + + case ${os} in + windows) format=zip ;; + esac + + log_trace "get_format_name(os=${os}, arch=${arch}, format=${original_format}) returned '${format}'" + + echo "${format}" +) + +# download_and_install_asset [release-url-prefix] [download-path] [install-path] [name] [os] [arch] [version] [format] [binary] +# +# attempts to download the archive and install it to the given path. +# +download_and_install_asset() ( + download_url="$1" + download_path="$2" + install_path=$3 + name="$4" + os="$5" + arch="$6" + version="$7" + format="$8" + binary="$9" + + asset_filepath=$(download_asset "${download_url}" "${download_path}" "${name}" "${os}" "${arch}" "${version}" "${format}") + + # don't continue if we couldn't download an asset + if [ -z "${asset_filepath}" ]; then + log_err "could not find release asset for os='${os}' arch='${arch}' format='${format}' " + return 1 + fi + + install_asset "${asset_filepath}" "${install_path}" "${binary}" +) + +# download_asset [release-url-prefix] [download-path] [name] [os] [arch] [version] [format] [binary] +# +# outputs the path to the downloaded asset asset_filepath +# +download_asset() ( + download_url="$1" + destination="$2" + name="$3" + os="$4" + arch="$5" + version="$6" + format="$7" + + log_trace "download_asset(url=${download_url}, destination=${destination}, name=${name}, os=${os}, arch=${arch}, version=${version}, format=${format})" + + checksums_filepath=$(download_github_release_checksums "${download_url}" "${name}" "${version}" "${destination}") + + log_trace "checksums content:\n$(cat ${checksums_filepath})" + + asset_filename=$(search_for_asset "${checksums_filepath}" "${name}" "${os}" "${arch}" "${format}") + + # don't continue if we couldn't find a matching asset from the checksums file + if [ -z "${asset_filename}" ]; then + return 1 + fi + + asset_url="${download_url}/${asset_filename}" + asset_filepath="${destination}/${asset_filename}" + http_download "${asset_filepath}" "${asset_url}" "" + + hash_sha256_verify "${asset_filepath}" "${checksums_filepath}" + + log_trace "download_asset_by_checksums_file() returned '${asset_filepath}'" + + echo "${asset_filepath}" +) + +# install_asset [asset-path] [destination-path] [binary] +# +install_asset() ( + asset_filepath="$1" + destination="$2" + binary="$3" + + log_trace "install_asset(asset=${asset_filepath}, destination=${destination}, binary=${binary})" + + # don't continue if we don't have anything to install + if [ -z "${asset_filepath}" ]; then + return + fi + + archive_dir=$(dirname "${asset_filepath}") + + # unarchive the downloaded archive to the temp dir + (cd "${archive_dir}" && unpack "${asset_filepath}") + + # create the destination dir + test ! -d "${destination}" && install -d "${destination}" + + # install the binary to the destination dir + install "${archive_dir}/${binary}" "${destination}/" +) + +main() ( + # parse arguments + + # note: never change default install directory (this must always be backwards compatible) + install_dir=${install_dir:-./bin} + + # note: never change the program flags or arguments (this must always be backwards compatible) + while getopts "b:dh?x" arg; do + case "$arg" in + b) install_dir="$OPTARG" ;; + d) + if [ "$_logp" = "$log_info_priority" ]; then + # -d == debug + log_set_priority $log_debug_priority + else + # -dd (or -ddd...) == trace + log_set_priority $log_trace_priority + fi + ;; + h | \?) usage "$0" ;; + x) set -x ;; + esac + done + shift $((OPTIND - 1)) + set +u + tag=$1 + + if [ -z "${tag}" ]; then + log_debug "checking github for the current release tag" + tag="" + else + log_debug "checking github for release tag='${tag}'" + fi + set -u + + tag=$(get_release_tag "${OWNER}" "${REPO}" "${tag}") + + if [ "$?" != "0" ]; then + log_err "unable to find tag='${tag}'" + log_err "do not specify a version or select a valid version from https://github.com/${OWNER}/${REPO}/releases" + return 1 + fi + + # run the application + + version=$(tag_to_version "${tag}") + os=$(uname_os) + arch=$(uname_arch) + format=$(get_format_name "${os}" "${arch}" "tar.gz") + binary=$(get_binary_name "${os}" "${arch}" "${PROJECT_NAME}") + download_url="${GITHUB_DOWNLOAD_PREFIX}/${tag}" + + # we always use the install.sh script that is associated with the tagged release. Why? the latest install.sh is not + # guaranteed to be able to install every version of the application. We use the DOWNLOAD_TAG_INSTALL_SCRIPT env var + # to indicate if we should continue processing with the existing script or to download the script from the given tag. + if [ "${DOWNLOAD_TAG_INSTALL_SCRIPT}" = "true" ]; then + export DOWNLOAD_TAG_INSTALL_SCRIPT=false + log_info "fetching release script for tag='${tag}'" + http_copy "${INSTALL_SH_BASE_URL}/${tag}/install.sh" "" | sh -s -- ${PROGRAM_ARGS} + exit $? + fi + + log_info "using release tag='${tag}' version='${version}' os='${os}' arch='${arch}'" + + download_dir=$(mktemp -d) + trap 'rm -rf -- "$download_dir"' EXIT + + log_debug "downloading files into ${download_dir}" + + download_and_install_asset "${download_url}" "${download_dir}" "${install_dir}" "${PROJECT_NAME}" "${os}" "${arch}" "${version}" "${format}" "${binary}" + + # don't continue if we couldn't install the asset + if [ "$?" != "0" ]; then + log_err "failed to install ${PROJECT_NAME}" + return 1 + fi + + log_info "installed ${install_dir}/${binary}" +) + +# entrypoint + +set +u +if [ -z "${TEST_INSTALL_SH}" ]; then + set -u + main "$@" +fi +set -u \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/client.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/client.go new file mode 100644 index 0000000000000000000000000000000000000000..b048fcdcaa32e133710f45b286a6a5e816bddfa3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/client.go @@ -0,0 +1,115 @@ +package anchore + +import ( + "context" + "errors" + "fmt" + "path" + "strings" + "unicode" + + "github.com/anchore/client-go/pkg/external" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/version" +) + +type Configuration struct { + BaseURL string + Username string + Password string + UserAgent string +} + +type Client struct { + config Configuration + client *external.APIClient +} + +func NewClient(cfg Configuration) (*Client, error) { + if cfg.UserAgent == "" { + versionInfo := version.FromBuild() + // format: product / product-version comment + cfg.UserAgent = fmt.Sprintf("%s / %s %s", internal.ApplicationName, versionInfo.Version, versionInfo.Platform) + } + + baseURL, err := prepareBaseURLForClient(cfg.BaseURL) + if err != nil { + return nil, fmt.Errorf("unable to create client: %w", err) + } + + return &Client{ + config: cfg, + client: external.NewAPIClient(&external.Configuration{ + BasePath: baseURL, + UserAgent: cfg.UserAgent, + }), + }, nil +} + +func (c *Client) newRequestContext(parentContext context.Context) context.Context { + if parentContext == nil { + parentContext = context.Background() + } + return context.WithValue( + parentContext, + external.ContextBasicAuth, + external.BasicAuth{ + UserName: c.config.Username, + Password: c.config.Password, + }, + ) +} + +var ErrInvalidBaseURLInput = errors.New("invalid base URL input") + +func prepareBaseURLForClient(baseURL string) (string, error) { + if err := checkBaseURLInput(baseURL); err != nil { + return "", err + } + + scheme, urlWithoutScheme := splitSchemeFromURL(baseURL) + + if scheme == "" { + scheme = "http" + } + + urlWithoutScheme = path.Clean(urlWithoutScheme) + + const requiredSuffix = "v1" + if path.Base(urlWithoutScheme) != requiredSuffix { + urlWithoutScheme = path.Join(urlWithoutScheme, requiredSuffix) + } + + preparedBaseURL := scheme + "://" + urlWithoutScheme + return preparedBaseURL, nil +} + +func checkBaseURLInput(url string) error { + if url == "" { + return ErrInvalidBaseURLInput + } + + firstCharacter := rune(url[0]) + if !(unicode.IsLetter(firstCharacter)) { + return ErrInvalidBaseURLInput + } + + return nil +} + +func splitSchemeFromURL(url string) (scheme, urlWithoutScheme string) { + if hasScheme(url) { + urlParts := strings.SplitN(url, "://", 2) + scheme = urlParts[0] + urlWithoutScheme = urlParts[1] + return + } + + return "", url +} + +func hasScheme(url string) bool { + parts := strings.Split(url, "://") + + return len(parts) > 1 +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/client_test.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/client_test.go new file mode 100644 index 0000000000000000000000000000000000000000..fc07ce70827c1f53de62ff063f35f33f5982121d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/client_test.go @@ -0,0 +1,210 @@ +package anchore + +import "testing" + +func TestHasScheme(t *testing.T) { + cases := []struct { + url string + expected bool + }{ + { + url: "http://localhost", + expected: true, + }, + { + url: "https://anchore.com:8443", + expected: true, + }, + { + url: "google.com", + expected: false, + }, + { + url: "", + expected: false, + }, + } + + for _, testCase := range cases { + t.Run(testCase.url, func(t *testing.T) { + result := hasScheme(testCase.url) + + if testCase.expected != result { + t.Errorf("expected %t but got %t", testCase.expected, result) + } + }) + } +} + +func TestPrepareBaseURLForClient(t *testing.T) { + cases := []struct { + inputURL string + expectedURL string + expectedErr error + }{ + { + inputURL: "", + expectedURL: "", + expectedErr: ErrInvalidBaseURLInput, + }, + { + inputURL: "localhost", + expectedURL: "http://localhost/v1", + expectedErr: nil, + }, + { + inputURL: "https://localhost", + expectedURL: "https://localhost/v1", + expectedErr: nil, + }, + { + inputURL: "https://localhost/", + expectedURL: "https://localhost/v1", + expectedErr: nil, + }, + { + inputURL: "https://localhost/v1/", + expectedURL: "https://localhost/v1", + expectedErr: nil, + }, + { + inputURL: "https://localhost/v1//", + expectedURL: "https://localhost/v1", + expectedErr: nil, + }, + { + inputURL: "http://something.com/platform/v1/services/anchore", + expectedURL: "http://something.com/platform/v1/services/anchore/v1", + expectedErr: nil, + }, + { + inputURL: "my-host:8228", + expectedURL: "http://my-host:8228/v1", + expectedErr: nil, + }, + { + inputURL: "v1/v1", + expectedURL: "http://v1/v1", + expectedErr: nil, + }, + { + inputURL: "/v1", + expectedURL: "", + expectedErr: ErrInvalidBaseURLInput, + }, + { + inputURL: "/imports/images", + expectedURL: "", + expectedErr: ErrInvalidBaseURLInput, + }, + } + + for _, testCase := range cases { + t.Run(testCase.inputURL, func(t *testing.T) { + resultURL, err := prepareBaseURLForClient(testCase.inputURL) + if err != testCase.expectedErr { + t.Errorf("expected err to be '%v' but got '%v'", testCase.expectedErr, err) + } + + if resultURL != testCase.expectedURL { + t.Errorf("expected URL to be '%v' but got '%v'", testCase.expectedURL, resultURL) + } + }) + } +} + +func TestCheckBaseURLInput(t *testing.T) { + cases := []struct { + input string + expected error + }{ + { + input: "", + expected: ErrInvalidBaseURLInput, + }, + { + input: "x", + expected: nil, + }, + { + input: "localhost:8000", + expected: nil, + }, + { + input: ":80", + expected: ErrInvalidBaseURLInput, + }, + { + input: "/v1", + expected: ErrInvalidBaseURLInput, + }, + } + + for _, testCase := range cases { + t.Run(testCase.input, func(t *testing.T) { + resultErr := checkBaseURLInput(testCase.input) + + if testCase.expected != resultErr { + t.Errorf("expected err to be '%v' but got '%v'", testCase.expected, resultErr) + } + }) + } +} + +func TestSplitSchemeFromURL(t *testing.T) { + cases := []struct { + input string + expectedScheme string + expectedURLWithoutScheme string + }{ + { + input: "", + expectedScheme: "", + expectedURLWithoutScheme: "", + }, + { + input: "localhost", + expectedScheme: "", + expectedURLWithoutScheme: "localhost", + }, + { + input: "https://anchore.com/path", + expectedScheme: "https", + expectedURLWithoutScheme: "anchore.com/path", + }, + { + input: "tcp://host:1234", + expectedScheme: "tcp", + expectedURLWithoutScheme: "host:1234", + }, + { + input: "/hello", + expectedScheme: "", + expectedURLWithoutScheme: "/hello", + }, + { + input: "://host", + expectedScheme: "", + expectedURLWithoutScheme: "host", + }, + { + input: "http//localhost", + expectedScheme: "", + expectedURLWithoutScheme: "http//localhost", + }, + } + + for _, testCase := range cases { + t.Run(testCase.input, func(t *testing.T) { + resultScheme, resultURLWithoutScheme := splitSchemeFromURL(testCase.input) + + if testCase.expectedScheme != resultScheme { + t.Errorf("expected scheme to be '%s' but got '%s'", testCase.expectedScheme, resultScheme) + } + + if testCase.expectedURLWithoutScheme != resultURLWithoutScheme { + t.Errorf("expected urlWithoutScheme to be '%s' but got '%s'", testCase.expectedURLWithoutScheme, resultURLWithoutScheme) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import.go new file mode 100644 index 0000000000000000000000000000000000000000..4225c96c8a35f1ae3d21eba887036d83f7a44ca9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import.go @@ -0,0 +1,144 @@ +package anchore + +import ( + "context" + "errors" + "fmt" + "time" + + "github.com/anchore/client-go/pkg/external" + "github.com/anchore/stereoscope/pkg/image" + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/syft/sbom" + "github.com/antihax/optional" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/go-progress" +) + +type ImportConfig struct { + ImageMetadata image.Metadata + SBOM sbom.SBOM + Dockerfile []byte + OverwriteExistingUpload bool + Timeout uint +} + +func importProgress(source string) (*progress.Stage, *progress.Manual) { + stage := &progress.Stage{} + prog := &progress.Manual{ + // this is the number of stages to expect; start + individual endpoints + stop + Total: 6, + } + bus.Publish(partybus.Event{ + Type: event.ImportStarted, + Source: source, + Value: progress.StagedProgressable(&struct { + progress.Stager + progress.Progressable + }{ + Stager: progress.Stager(stage), + Progressable: prog, + }), + }) + + return stage, prog +} + +//nolint:funlen +func (c *Client) Import(ctx context.Context, cfg ImportConfig) error { + stage, prog := importProgress(c.config.BaseURL) + + timeout := time.Duration(cfg.Timeout) * time.Second + ctxWithTimeout, cancel := context.WithTimeout(ctx, timeout) + defer cancel() + + authedCtx := c.newRequestContext(ctxWithTimeout) + + stage.Current = "starting session" + startOperation, createResponse, err := c.client.ImportsApi.CreateOperation(authedCtx) + if err != nil { + var detail = "no details given" + var openAPIErr external.GenericOpenAPIError + if errors.As(err, &openAPIErr) { + detail = string(openAPIErr.Body()) + } + return fmt.Errorf("unable to start import session: %w: %s", err, detail) + } + defer createResponse.Body.Close() + + prog.N++ + sessionID := startOperation.Uuid + + packageDigest, err := importPackageSBOM(authedCtx, c.client.ImportsApi, sessionID, cfg.SBOM, stage) + if err != nil { + return fmt.Errorf("failed to import Package SBOM: %w", err) + } + prog.N++ + + manifestDigest, err := importManifest(authedCtx, c.client.ImportsApi, sessionID, cfg.SBOM.Source.ImageMetadata.RawManifest, stage) + if err != nil { + return fmt.Errorf("failed to import Manifest: %w", err) + } + prog.N++ + + configDigest, err := importConfig(authedCtx, c.client.ImportsApi, sessionID, cfg.SBOM.Source.ImageMetadata.RawConfig, stage) + if err != nil { + return fmt.Errorf("failed to import Config: %w", err) + } + prog.N++ + + dockerfileDigest, err := importDockerfile(authedCtx, c.client.ImportsApi, sessionID, cfg.Dockerfile, stage) + if err != nil { + return fmt.Errorf("failed to import Dockerfile: %w", err) + } + prog.N++ + + stage.Current = "finalizing" + imageModel := addImageModel(cfg.ImageMetadata, packageDigest, manifestDigest, dockerfileDigest, configDigest, sessionID) + opts := external.AddImageOpts{ + Force: optional.NewBool(cfg.OverwriteExistingUpload), + } + + _, addResponse, err := c.client.ImagesApi.AddImage(authedCtx, imageModel, &opts) + if err != nil { + var detail = "no details given" + var openAPIErr external.GenericOpenAPIError + if errors.As(err, &openAPIErr) { + detail = string(openAPIErr.Body()) + } + return fmt.Errorf("unable to complete import session=%q: %w: %s", sessionID, err, detail) + } + defer addResponse.Body.Close() + + prog.N++ + + stage.Current = "" + prog.SetCompleted() + + return nil +} + +func addImageModel(imageMetadata image.Metadata, packageDigest, manifestDigest, dockerfileDigest, configDigest, sessionID string) external.ImageAnalysisRequest { + var tags = make([]string, len(imageMetadata.Tags)) + for i, t := range imageMetadata.Tags { + tags[i] = t.String() + } + + return external.ImageAnalysisRequest{ + Source: external.ImageSource{ + Import: &external.ImageImportManifest{ + Contents: external.ImportContentDigests{ + Packages: packageDigest, + Manifest: manifestDigest, + Dockerfile: dockerfileDigest, + ImageConfig: configDigest, + }, + Tags: tags, + Digest: imageMetadata.ManifestDigest, + LocalImageId: imageMetadata.ID, + OperationUuid: sessionID, + }, + }, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_config.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_config.go new file mode 100644 index 0000000000000000000000000000000000000000..feedc0aa3c432d0b130b3e0fbb0f9e4e82363671 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_config.go @@ -0,0 +1,50 @@ +//nolint:dupl +package anchore + +import ( + "context" + "encoding/json" + "errors" + "fmt" + "net/http" + + "github.com/wagoodman/go-progress" + + "github.com/anchore/client-go/pkg/external" + "github.com/anchore/syft/internal/log" +) + +type configImportAPI interface { + ImportImageConfig(ctx context.Context, sessionID string, contents interface{}) (external.ImageImportContentResponse, *http.Response, error) +} + +func importConfig(ctx context.Context, api configImportAPI, sessionID string, config []byte, stage *progress.Stage) (string, error) { + if len(config) > 0 { + log.Debug("importing image config") + stage.Current = "image config" + + // API requires an object, but we do not verify the shape of this object locally + var sender map[string]interface{} + if err := json.Unmarshal(config, &sender); err != nil { + return "", err + } + + response, httpResponse, err := api.ImportImageConfig(ctx, sessionID, sender) + if err != nil { + var openAPIErr external.GenericOpenAPIError + if errors.As(err, &openAPIErr) { + log.Errorf("api response: %+v", string(openAPIErr.Body())) + } + return "", fmt.Errorf("unable to import Config: %w", err) + } + + defer httpResponse.Body.Close() + + if httpResponse.StatusCode != 200 { + return "", fmt.Errorf("unable to import Config: %s", httpResponse.Status) + } + + return response.Digest, nil + } + return "", nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_config_test.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_config_test.go new file mode 100644 index 0000000000000000000000000000000000000000..190808c84bd8d597586d517c2bb9bce611a2d9d8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_config_test.go @@ -0,0 +1,129 @@ +package anchore + +import ( + "context" + "encoding/json" + "fmt" + "net/http" + "strings" + "testing" + + "github.com/wagoodman/go-progress" + + "github.com/anchore/client-go/pkg/external" + "github.com/docker/docker/pkg/ioutils" + "github.com/go-test/deep" +) + +type mockConfigImportAPI struct { + sessionID string + model interface{} + httpResponse *http.Response + err error + ctx context.Context + responseDigest string + wasCalled bool +} + +func (m *mockConfigImportAPI) ImportImageConfig(ctx context.Context, sessionID string, contents interface{}) (external.ImageImportContentResponse, *http.Response, error) { + m.wasCalled = true + m.model = contents + m.sessionID = sessionID + m.ctx = ctx + if m.httpResponse == nil { + m.httpResponse = &http.Response{} + } + m.httpResponse.Body = ioutils.NewReadCloserWrapper(strings.NewReader(""), func() error { return nil }) + return external.ImageImportContentResponse{Digest: m.responseDigest}, m.httpResponse, m.err +} + +func TestConfigImport(t *testing.T) { + + sessionID := "my-session" + + tests := []struct { + name string + manifestJSONStr string + api *mockConfigImportAPI + expectsError bool + expectsCall bool + }{ + + { + name: "Go case: import works", + manifestJSONStr: `{ "key": "the-manifest-contents!" }`, + api: &mockConfigImportAPI{ + httpResponse: &http.Response{StatusCode: 200}, + responseDigest: "digest!", + }, + expectsCall: true, + }, + { + name: "No manifest provided", + manifestJSONStr: "", + api: &mockConfigImportAPI{}, + expectsCall: false, + }, + { + name: "API returns an error", + manifestJSONStr: `{ "key": "the-manifest-contents!" }`, + api: &mockConfigImportAPI{ + err: fmt.Errorf("api error, something went wrong"), + }, + expectsError: true, + expectsCall: true, + }, + { + name: "API HTTP-level error", + manifestJSONStr: `{ "key": "the-manifest-contents!" }`, + api: &mockConfigImportAPI{ + httpResponse: &http.Response{StatusCode: 404}, + }, + expectsError: true, + expectsCall: true, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + digest, err := importConfig(context.TODO(), test.api, sessionID, []byte(test.manifestJSONStr), &progress.Stage{}) + + // validate error handling + if err != nil && !test.expectsError { + t.Fatalf("did not expect an error, but got: %+v", err) + } else if err == nil && test.expectsError { + t.Fatalf("did expect an error, but got none") + } + + if !test.api.wasCalled && test.expectsCall { + t.Fatalf("was not called!") + } else if test.api.wasCalled && !test.expectsCall { + t.Fatalf("should not have been called") + } + + if !test.expectsCall { + return + } + + if digest != test.api.responseDigest { + t.Errorf("unexpected content digest: %q != %q", digest, test.api.responseDigest) + } + + // validating that the mock got the right parameters + if test.api.sessionID != sessionID { + t.Errorf("different session ID: %s != %s", test.api.sessionID, sessionID) + } + + var expected map[string]interface{} + if err := json.Unmarshal([]byte(test.manifestJSONStr), &expected); err != nil { + t.Fatalf("could not unmarshal expected results") + } + + for _, d := range deep.Equal(test.api.model, expected) { + t.Errorf("model difference: %s", d) + } + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_dockerfile.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_dockerfile.go new file mode 100644 index 0000000000000000000000000000000000000000..bc8083768165b967372db7702afbf96c4e93b7eb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_dockerfile.go @@ -0,0 +1,43 @@ +package anchore + +import ( + "context" + "errors" + "fmt" + "net/http" + + "github.com/wagoodman/go-progress" + + "github.com/anchore/syft/internal/log" + + "github.com/anchore/client-go/pkg/external" +) + +type dockerfileImportAPI interface { + ImportImageDockerfile(ctx context.Context, sessionID string, contents string) (external.ImageImportContentResponse, *http.Response, error) +} + +func importDockerfile(ctx context.Context, api dockerfileImportAPI, sessionID string, dockerfile []byte, stage *progress.Stage) (string, error) { + if len(dockerfile) > 0 { + log.Debug("importing dockerfile") + stage.Current = "dockerfile" + + response, httpResponse, err := api.ImportImageDockerfile(ctx, sessionID, string(dockerfile)) + if err != nil { + var openAPIErr external.GenericOpenAPIError + if errors.As(err, &openAPIErr) { + log.Errorf("api response: %+v", string(openAPIErr.Body())) + } + return "", fmt.Errorf("unable to import Dockerfile: %w", err) + } + + defer httpResponse.Body.Close() + + if httpResponse.StatusCode != 200 { + return "", fmt.Errorf("unable to import Dockerfile: %s", httpResponse.Status) + } + + return response.Digest, nil + } + return "", nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_dockerfile_test.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_dockerfile_test.go new file mode 100644 index 0000000000000000000000000000000000000000..27a5c6e2de9ed198227b1e7c65735f91a0462dcf --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_dockerfile_test.go @@ -0,0 +1,124 @@ +package anchore + +import ( + "context" + "fmt" + "net/http" + "strings" + "testing" + + "github.com/wagoodman/go-progress" + + "github.com/docker/docker/pkg/ioutils" + + "github.com/anchore/client-go/pkg/external" + "github.com/go-test/deep" +) + +type mockDockerfileImportAPI struct { + sessionID string + model string + httpResponse *http.Response + err error + ctx context.Context + responseDigest string + wasCalled bool +} + +func (m *mockDockerfileImportAPI) ImportImageDockerfile(ctx context.Context, sessionID string, contents string) (external.ImageImportContentResponse, *http.Response, error) { + m.wasCalled = true + m.model = contents + m.sessionID = sessionID + m.ctx = ctx + if m.httpResponse == nil { + m.httpResponse = &http.Response{} + } + m.httpResponse.Body = ioutils.NewReadCloserWrapper(strings.NewReader(""), func() error { return nil }) + return external.ImageImportContentResponse{Digest: m.responseDigest}, m.httpResponse, m.err +} + +func TestDockerfileImport(t *testing.T) { + + sessionID := "my-session" + + tests := []struct { + name string + dockerfile string + api *mockDockerfileImportAPI + expectsError bool + expectsCall bool + }{ + + { + name: "Go case: import works", + dockerfile: "the-manifest-contents!", + api: &mockDockerfileImportAPI{ + httpResponse: &http.Response{StatusCode: 200}, + responseDigest: "digest!", + }, + expectsCall: true, + }, + { + name: "No manifest provided", + dockerfile: "", + api: &mockDockerfileImportAPI{}, + expectsCall: false, + }, + { + name: "API returns an error", + dockerfile: "the-manifest-contents!", + api: &mockDockerfileImportAPI{ + err: fmt.Errorf("api error, something went wrong"), + }, + expectsError: true, + expectsCall: true, + }, + { + name: "API HTTP-level error", + dockerfile: "the-manifest-contents!", + api: &mockDockerfileImportAPI{ + httpResponse: &http.Response{StatusCode: 404}, + }, + expectsError: true, + expectsCall: true, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + digest, err := importDockerfile(context.TODO(), test.api, sessionID, []byte(test.dockerfile), &progress.Stage{}) + + // validate error handling + if err != nil && !test.expectsError { + t.Fatalf("did not expect an error, but got: %+v", err) + } else if err == nil && test.expectsError { + t.Fatalf("did expect an error, but got none") + } + + if !test.api.wasCalled && test.expectsCall { + t.Fatalf("was not called!") + } else if test.api.wasCalled && !test.expectsCall { + t.Fatalf("should not have been called") + } + + if !test.expectsCall { + return + } + + if digest != test.api.responseDigest { + t.Errorf("unexpected content digest: %q != %q", digest, test.api.responseDigest) + } + + // validating that the mock got the right parameters + if test.api.sessionID != sessionID { + t.Errorf("different session ID: %s != %s", test.api.sessionID, sessionID) + } + + for _, d := range deep.Equal(test.api.model, test.dockerfile) { + t.Errorf("model difference: %s", d) + } + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_manifest.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_manifest.go new file mode 100644 index 0000000000000000000000000000000000000000..f1fb7d905cf4bc6680796c39bd42f9294d4f7fd2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_manifest.go @@ -0,0 +1,50 @@ +//nolint:dupl +package anchore + +import ( + "context" + "encoding/json" + "errors" + "fmt" + "net/http" + + "github.com/wagoodman/go-progress" + + "github.com/anchore/client-go/pkg/external" + "github.com/anchore/syft/internal/log" +) + +type manifestImportAPI interface { + ImportImageManifest(ctx context.Context, sessionID string, contents interface{}) (external.ImageImportContentResponse, *http.Response, error) +} + +func importManifest(ctx context.Context, api manifestImportAPI, sessionID string, manifest []byte, stage *progress.Stage) (string, error) { + if len(manifest) > 0 { + log.Debug("importing image manifest") + stage.Current = "image manifest" + + // API requires an object, but we do not verify the shape of this object locally + var sender map[string]interface{} + if err := json.Unmarshal(manifest, &sender); err != nil { + return "", err + } + + response, httpResponse, err := api.ImportImageManifest(ctx, sessionID, sender) + if err != nil { + var openAPIErr external.GenericOpenAPIError + if errors.As(err, &openAPIErr) { + log.Errorf("api response: %+v", string(openAPIErr.Body())) + } + return "", fmt.Errorf("unable to import Manifest: %w", err) + } + + defer httpResponse.Body.Close() + + if httpResponse.StatusCode != 200 { + return "", fmt.Errorf("unable to import Manifest: %s", httpResponse.Status) + } + + return response.Digest, nil + } + return "", nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_manifest_test.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_manifest_test.go new file mode 100644 index 0000000000000000000000000000000000000000..349970e81e6015d268b232bbae8cc74f117b0b76 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_manifest_test.go @@ -0,0 +1,129 @@ +package anchore + +import ( + "context" + "encoding/json" + "fmt" + "net/http" + "strings" + "testing" + + "github.com/wagoodman/go-progress" + + "github.com/anchore/client-go/pkg/external" + "github.com/docker/docker/pkg/ioutils" + "github.com/go-test/deep" +) + +type mockManifestImportAPI struct { + sessionID string + model interface{} + httpResponse *http.Response + err error + ctx context.Context + responseDigest string + wasCalled bool +} + +func (m *mockManifestImportAPI) ImportImageManifest(ctx context.Context, sessionID string, contents interface{}) (external.ImageImportContentResponse, *http.Response, error) { + m.wasCalled = true + m.model = contents + m.sessionID = sessionID + m.ctx = ctx + if m.httpResponse == nil { + m.httpResponse = &http.Response{} + } + m.httpResponse.Body = ioutils.NewReadCloserWrapper(strings.NewReader(""), func() error { return nil }) + return external.ImageImportContentResponse{Digest: m.responseDigest}, m.httpResponse, m.err +} + +func TestManifestImport(t *testing.T) { + + sessionID := "my-session" + + tests := []struct { + name string + manifest string + api *mockManifestImportAPI + expectsError bool + expectsCall bool + }{ + + { + name: "Go case: import works", + manifest: `{ "key": "the-config-contents!" }`, + api: &mockManifestImportAPI{ + httpResponse: &http.Response{StatusCode: 200}, + responseDigest: "digest!", + }, + expectsCall: true, + }, + { + name: "No manifest provided", + manifest: "", + api: &mockManifestImportAPI{}, + expectsCall: false, + }, + { + name: "API returns an error", + manifest: `{ "key": "the-config-contents!" }`, + api: &mockManifestImportAPI{ + err: fmt.Errorf("api error, something went wrong"), + }, + expectsError: true, + expectsCall: true, + }, + { + name: "API HTTP-level error", + manifest: `{ "key": "the-config-contents!" }`, + api: &mockManifestImportAPI{ + httpResponse: &http.Response{StatusCode: 404}, + }, + expectsError: true, + expectsCall: true, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + digest, err := importManifest(context.TODO(), test.api, sessionID, []byte(test.manifest), &progress.Stage{}) + + // validate error handling + if err != nil && !test.expectsError { + t.Fatalf("did not expect an error, but got: %+v", err) + } else if err == nil && test.expectsError { + t.Fatalf("did expect an error, but got none") + } + + if !test.api.wasCalled && test.expectsCall { + t.Fatalf("was not called!") + } else if test.api.wasCalled && !test.expectsCall { + t.Fatalf("should not have been called") + } + + if !test.expectsCall { + return + } + + if digest != test.api.responseDigest { + t.Errorf("unexpected content digest: %q != %q", digest, test.api.responseDigest) + } + + // validating that the mock got the right parameters + if test.api.sessionID != sessionID { + t.Errorf("different session ID: %s != %s", test.api.sessionID, sessionID) + } + + var expected map[string]interface{} + if err := json.Unmarshal([]byte(test.manifest), &expected); err != nil { + t.Fatalf("could not unmarshal expected results") + } + + for _, d := range deep.Equal(test.api.model, expected) { + t.Errorf("model difference: %s", d) + } + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_package_sbom.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_package_sbom.go new file mode 100644 index 0000000000000000000000000000000000000000..6c9f6c0ac9e18154436128d45acb0e6cc2175d0d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_package_sbom.go @@ -0,0 +1,118 @@ +package anchore + +import ( + "bytes" + "context" + "encoding/json" + "errors" + "fmt" + "net/http" + + "github.com/anchore/client-go/pkg/external" + "github.com/anchore/syft/internal/formats/syftjson" + syftjsonModel "github.com/anchore/syft/internal/formats/syftjson/model" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/sbom" + "github.com/wagoodman/go-progress" +) + +type packageSBOMImportAPI interface { + ImportImagePackages(context.Context, string, external.ImagePackageManifest) (external.ImageImportContentResponse, *http.Response, error) +} + +// importSBOM mirrors all elements found on the syftjson model format object relative to the anchore engine import schema. +type importSBOM struct { + Artifacts []syftjsonModel.Package `json:"artifacts"` // Artifacts is the list of packages discovered and placed into the catalog + ArtifactRelationships []syftjsonModel.Relationship `json:"artifactRelationships"` + Files []syftjsonModel.File `json:"files,omitempty"` // note: must have omitempty + Secrets []syftjsonModel.Secrets `json:"secrets,omitempty"` // note: must have omitempty + Source syftjsonModel.Source `json:"source"` // Source represents the original object that was cataloged + Distro external.ImportDistribution `json:"distro"` // Distro represents the Linux distribution that was detected from the source + Descriptor syftjsonModel.Descriptor `json:"descriptor"` // Descriptor is a block containing self-describing information about syft + Schema syftjsonModel.Schema `json:"schema"` // Schema is a block reserved for defining the version for the shape of this JSON document and where to find the schema document to validate the shape +} + +// toImportSBOMModel transforms the current sbom shape into what is needed for the current anchore import api shape. +func toImportSBOMModel(s sbom.SBOM) importSBOM { + m := syftjson.ToFormatModel(s) + + var idLike string + if len(m.Distro.IDLike) > 0 { + idLike = m.Distro.IDLike[0] + } + + var version = m.Distro.VersionID // note: version is intentionally not used as the default + if version == "" { + version = m.Distro.Version + } + + var name = m.Distro.ID // note: name is intentionally not used as the default + if name == "" { + name = m.Distro.Name + } + + return importSBOM{ + Artifacts: m.Artifacts, + ArtifactRelationships: m.ArtifactRelationships, + Files: m.Files, + Secrets: m.Secrets, + Source: m.Source, + Distro: external.ImportDistribution{ + Name: name, + Version: version, + IdLike: idLike, + }, + Descriptor: m.Descriptor, + Schema: m.Schema, + } +} + +func packageSbomModel(s sbom.SBOM) (*external.ImagePackageManifest, error) { + var buf bytes.Buffer + + doc := toImportSBOMModel(s) + + enc := json.NewEncoder(&buf) + // prevent > and < from being escaped in the payload + enc.SetEscapeHTML(false) + enc.SetIndent("", " ") + + if err := enc.Encode(&doc); err != nil { + return nil, fmt.Errorf("unable to encode import JSON model: %w", err) + } + + // the model is 1:1 the JSON output of today. As the schema changes, this will need to be converted into individual mappings. + var model external.ImagePackageManifest + if err := json.Unmarshal(buf.Bytes(), &model); err != nil { + return nil, fmt.Errorf("unable to convert JSON output to import model: %w", err) + } + + return &model, nil +} + +func importPackageSBOM(ctx context.Context, api packageSBOMImportAPI, sessionID string, s sbom.SBOM, stage *progress.Stage) (string, error) { + log.Debug("importing package SBOM") + stage.Current = "package SBOM" + + model, err := packageSbomModel(s) + if err != nil { + return "", fmt.Errorf("unable to create PackageSBOM model: %w", err) + } + + response, httpResponse, err := api.ImportImagePackages(ctx, sessionID, *model) + if err != nil { + var openAPIErr external.GenericOpenAPIError + if errors.As(err, &openAPIErr) { + log.Errorf("api response: %+v", string(openAPIErr.Body())) + } + return "", fmt.Errorf("unable to import PackageSBOM: %w", err) + } + + defer httpResponse.Body.Close() + + if httpResponse.StatusCode != 200 { + return "", fmt.Errorf("unable to import PackageSBOM: %s", httpResponse.Status) + } + + return response.Digest, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_package_sbom_test.go b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_package_sbom_test.go new file mode 100644 index 0000000000000000000000000000000000000000..3628a07c4820a096285e703aa0495d1a2c9c09eb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/anchore/import_package_sbom_test.go @@ -0,0 +1,397 @@ +package anchore + +import ( + "context" + "encoding/json" + "fmt" + "net/http" + "strings" + "testing" + + "github.com/anchore/client-go/pkg/external" + "github.com/anchore/syft/internal/formats/syftjson" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" + "github.com/docker/docker/pkg/ioutils" + "github.com/go-test/deep" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + "github.com/wagoodman/go-progress" +) + +func must(c pkg.CPE, e error) pkg.CPE { + if e != nil { + panic(e) + } + return c +} + +type mockPackageSBOMImportAPI struct { + sessionID string + model external.ImagePackageManifest + httpResponse *http.Response + err error + ctx context.Context + responseDigest string +} + +func (m *mockPackageSBOMImportAPI) ImportImagePackages(ctx context.Context, sessionID string, model external.ImagePackageManifest) (external.ImageImportContentResponse, *http.Response, error) { + m.model = model + m.sessionID = sessionID + m.ctx = ctx + if m.httpResponse == nil { + m.httpResponse = &http.Response{} + } + m.httpResponse.Body = ioutils.NewReadCloserWrapper(strings.NewReader(""), func() error { return nil }) + return external.ImageImportContentResponse{Digest: m.responseDigest}, m.httpResponse, m.err +} + +func sbomFixture() sbom.SBOM { + return sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: pkg.NewCatalog(pkg.Package{ + Name: "name", + Version: "version", + FoundBy: "foundBy", + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "path", + FileSystemID: "layerID", + }, + }, + ), + Licenses: []string{"license"}, + Language: pkg.Python, + Type: pkg.PythonPkg, + CPEs: []pkg.CPE{ + must(pkg.NewCPE("cpe:2.3:*:some:package:1:*:*:*:*:*:*:*")), + }, + PURL: "purl", + MetadataType: pkg.PythonPackageMetadataType, + Metadata: pkg.PythonPackageMetadata{ + Name: "p-name", + Version: "p-version", + License: "p-license", + Author: "p-author", + AuthorEmail: "p-email", + Platform: "p-platform", + Files: []pkg.PythonFileRecord{ + { + Path: "p-path", + Digest: &pkg.PythonFileDigest{ + Algorithm: "p-alg", + Value: "p-digest", + }, + Size: "p-size", + }, + }, + SitePackagesRootPath: "p-site-packages-root", + TopLevelPackages: []string{"top-level"}, + }, + }), + LinuxDistribution: &linux.Release{ + ID: "centos", + Version: "8.0", + VersionID: "8.0", + IDLike: []string{"rhel"}, + }, + }, + Relationships: []artifact.Relationship{ + { + From: source.NewLocation("/place1"), + To: source.NewLocation("/place2"), + Type: artifact.ContainsRelationship, + }, + }, + Source: source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: source.ImageMetadata{ + UserInput: "user-in", + Layers: nil, + Size: 10, + ManifestDigest: "sha256:digest!", + MediaType: "mediatype!", + Tags: nil, + }, + }, + } + +} + +func TestPackageSbomImport(t *testing.T) { + sbomResult := sbomFixture() + theModel, err := packageSbomModel(sbomResult) + if err != nil { + t.Fatalf("could not get sbom model: %+v", err) + } + + sessionID := "my-session" + + tests := []struct { + name string + api *mockPackageSBOMImportAPI + expectsError bool + }{ + + { + name: "Go case: import works", + api: &mockPackageSBOMImportAPI{ + httpResponse: &http.Response{StatusCode: 200}, + responseDigest: "digest!", + }, + }, + { + name: "API returns an error", + api: &mockPackageSBOMImportAPI{ + err: fmt.Errorf("API error, something went wrong."), + }, + expectsError: true, + }, + { + name: "API HTTP-level error", + api: &mockPackageSBOMImportAPI{ + httpResponse: &http.Response{StatusCode: 404}, + }, + expectsError: true, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + digest, err := importPackageSBOM(context.TODO(), test.api, sessionID, sbomResult, &progress.Stage{}) + + // validate error handling + if err != nil && !test.expectsError { + t.Fatalf("did not expect an error, but got: %+v", err) + } else if err == nil && test.expectsError { + t.Fatalf("did expect an error, but got none") + } + + if digest != test.api.responseDigest { + t.Errorf("unexpected content digest: %q != %q", digest, test.api.responseDigest) + } + + // validating that the mock got the right parameters (api.ImportImagePackages) + if test.api.sessionID != sessionID { + t.Errorf("different session ID: %s != %s", test.api.sessionID, sessionID) + } + + for _, d := range deep.Equal(&test.api.model, theModel) { + t.Errorf("model difference: %s", d) + } + + }) + } +} + +type modelAssertion func(t *testing.T, model *external.ImagePackageManifest) + +func Test_packageSbomModel(t *testing.T) { + fix := sbomFixture() + + tests := []struct { + name string + sbom sbom.SBOM + traits []modelAssertion + }{ + { + name: "distro: has single distro id-like", + sbom: sbom.SBOM{ + Artifacts: sbom.Artifacts{ + LinuxDistribution: &linux.Release{ + Name: "centos-name", + ID: "centos-id", + IDLike: []string{ + "centos-id-like-1", + }, + Version: "version", + VersionID: "version-id", + }, + }, + }, + traits: []modelAssertion{ + hasDistroInfo("centos-id", "version-id", "centos-id-like-1"), + }, + }, + { + name: "distro: has multiple distro id-like", + sbom: sbom.SBOM{ + Artifacts: sbom.Artifacts{ + LinuxDistribution: &linux.Release{ + Name: "centos-name", + ID: "centos-id", + IDLike: []string{ + "centos-id-like-1", + "centos-id-like-2", + }, + Version: "version", + VersionID: "version-id", + }, + }, + }, + traits: []modelAssertion{ + hasDistroInfo("centos-id", "version-id", "centos-id-like-1"), + }, + }, + { + name: "distro: has no distro id-like", + sbom: sbom.SBOM{ + Artifacts: sbom.Artifacts{ + LinuxDistribution: &linux.Release{ + Name: "centos-name", + ID: "centos-id", + IDLike: []string{}, + Version: "version", + VersionID: "version-id", + }, + }, + }, + traits: []modelAssertion{ + hasDistroInfo("centos-id", "version-id", ""), + }, + }, + { + name: "distro: has no version-id", + sbom: sbom.SBOM{ + Artifacts: sbom.Artifacts{ + LinuxDistribution: &linux.Release{ + Name: "centos-name", + ID: "centos-id", + IDLike: []string{}, + Version: "version", + VersionID: "", + }, + }, + }, + traits: []modelAssertion{ + hasDistroInfo("centos-id", "version", ""), + }, + }, + { + name: "distro: has no id", + sbom: sbom.SBOM{ + Artifacts: sbom.Artifacts{ + LinuxDistribution: &linux.Release{ + Name: "centos-name", + ID: "", + IDLike: []string{}, + Version: "version", + VersionID: "version-id", + }, + }, + }, + traits: []modelAssertion{ + hasDistroInfo("centos-name", "version-id", ""), + }, + }, + { + name: "should have expected packages", + sbom: fix, + traits: []modelAssertion{ + func(t *testing.T, model *external.ImagePackageManifest) { + require.Len(t, model.Artifacts, 1) + + modelPkg := model.Artifacts + modelBytes, err := json.Marshal(&modelPkg) + require.NoError(t, err) + + fixPkg := syftjson.ToFormatModel(fix).Artifacts + fixBytes, err := json.Marshal(&fixPkg) + require.NoError(t, err) + + assert.JSONEq(t, string(fixBytes), string(modelBytes)) + }, + }, + }, + { + name: "should have expected relationships", + sbom: fix, + traits: []modelAssertion{ + func(t *testing.T, model *external.ImagePackageManifest) { + modelPkg := model.ArtifactRelationships + modelBytes, err := json.Marshal(&modelPkg) + require.NoError(t, err) + + fixPkg := syftjson.ToFormatModel(fix).ArtifactRelationships + fixBytes, err := json.Marshal(&fixPkg) + require.NoError(t, err) + + assert.JSONEq(t, string(fixBytes), string(modelBytes)) + }, + }, + }, + { + name: "should have expected schema", + sbom: fix, + traits: []modelAssertion{ + func(t *testing.T, model *external.ImagePackageManifest) { + modelPkg := model.Schema + modelBytes, err := json.Marshal(&modelPkg) + require.NoError(t, err) + + fixPkg := syftjson.ToFormatModel(fix).Schema + fixBytes, err := json.Marshal(&fixPkg) + require.NoError(t, err) + + assert.JSONEq(t, string(fixBytes), string(modelBytes)) + }, + }, + }, + { + name: "should have expected descriptor", + sbom: fix, + traits: []modelAssertion{ + func(t *testing.T, model *external.ImagePackageManifest) { + modelPkg := model.Descriptor + modelBytes, err := json.Marshal(&modelPkg) + require.NoError(t, err) + + fixPkg := syftjson.ToFormatModel(fix).Descriptor + fixBytes, err := json.Marshal(&fixPkg) + require.NoError(t, err) + + assert.JSONEq(t, string(fixBytes), string(modelBytes)) + }, + }, + }, + { + name: "should have expected source", + sbom: fix, + traits: []modelAssertion{ + func(t *testing.T, model *external.ImagePackageManifest) { + modelPkg := model.Source + modelBytes, err := json.Marshal(&modelPkg) + require.NoError(t, err) + + fixPkg := syftjson.ToFormatModel(fix).Source + fixBytes, err := json.Marshal(&fixPkg) + require.NoError(t, err) + + assert.JSONEq(t, string(fixBytes), string(modelBytes)) + }, + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + got, err := packageSbomModel(tt.sbom) + require.NoError(t, err) + for _, fn := range tt.traits { + fn(t, got) + } + }) + } +} + +func hasDistroInfo(name, version, idLike string) modelAssertion { + return func(t *testing.T, model *external.ImagePackageManifest) { + assert.Equal(t, name, model.Distro.Name) + assert.Equal(t, version, model.Distro.Version) + assert.Equal(t, idLike, model.Distro.IdLike) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/bus/bus.go b/ci/tools/openeuler-purl/syft-dev/internal/bus/bus.go new file mode 100644 index 0000000000000000000000000000000000000000..0810c2fc6704368524e4723bf4747c10aede52e1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/bus/bus.go @@ -0,0 +1,35 @@ +/* +Package bus provides access to a singleton instance of an event bus (provided by the calling application). The event bus +is intended to allow for the syft library to publish events which library consumers can subscribe to. These events +can provide static information, but also have an object as a payload for which the consumer can poll for updates. +This is akin to a logger, except instead of only allowing strings to be logged, rich objects that can be interacted with. + +Note that the singleton instance is only allowed to publish events and not subscribe to them --this is intentional. +Internal library interactions should continue to use traditional in-execution-path approaches for data sharing +(e.g. function returns and channels) and not depend on bus subscriptions for critical interactions (e.g. one part of the +lib publishes an event and another part of the lib subscribes and reacts to that event). The bus is provided only as a +means for consumers to observe events emitted from the library (such as to provide a rich UI) and not to allow +consumers to augment or otherwise change execution. +*/ +package bus + +import "github.com/wagoodman/go-partybus" + +var publisher partybus.Publisher +var active bool + +// SetPublisher sets the singleton event bus publisher. This is optional; if no bus is provided, the library will +// behave no differently than if a bus had been provided. +func SetPublisher(p partybus.Publisher) { + publisher = p + if p != nil { + active = true + } +} + +// Publish an event onto the bus. If there is no bus set by the calling application, this does nothing. +func Publish(event partybus.Event) { + if active { + publisher.Publish(event) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/anchore.go b/ci/tools/openeuler-purl/syft-dev/internal/config/anchore.go new file mode 100644 index 0000000000000000000000000000000000000000..7e3bc281c9d4dcfee8aa1d8799990e193522d252 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/anchore.go @@ -0,0 +1,21 @@ +package config + +import "github.com/spf13/viper" + +type anchore struct { + // upload options + Host string `yaml:"host" json:"host" mapstructure:"host"` // -H , hostname of the engine/enterprise instance to upload to (setting this value enables upload) + Path string `yaml:"path" json:"path" mapstructure:"path"` // override the engine/enterprise API upload path + // IMPORTANT: do not show the username in any YAML/JSON output (sensitive information) + Username string `yaml:"-" json:"-" mapstructure:"username"` // -u , username to authenticate upload + // IMPORTANT: do not show the password in any YAML/JSON output (sensitive information) + Password string `yaml:"-" json:"-" mapstructure:"password"` // -p , password to authenticate upload + Dockerfile string `yaml:"dockerfile" json:"dockerfile" mapstructure:"dockerfile"` // -d , dockerfile to attach for upload + OverwriteExistingImage bool `yaml:"overwrite-existing-image" json:"overwrite-existing-image" mapstructure:"overwrite-existing-image"` // --overwrite-existing-image , if any of the SBOM components have already been uploaded this flag will ensure they are overwritten with the current upload + ImportTimeout uint `yaml:"import-timeout" json:"import-timeout" mapstructure:"import-timeout"` // --import-timeout + // , customize the number of seconds within which the SBOM import must be completed or canceled +} + +func (cfg anchore) loadDefaultValues(v *viper.Viper) { + v.SetDefault("anchore.path", "") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/application.go b/ci/tools/openeuler-purl/syft-dev/internal/config/application.go new file mode 100644 index 0000000000000000000000000000000000000000..d5898b0d103a9a0b97e690553c3de103ebbac9c2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/application.go @@ -0,0 +1,285 @@ +package config + +import ( + "errors" + "fmt" + "path" + "reflect" + "sort" + "strings" + + "github.com/anchore/syft/syft/pkg/cataloger" + + "github.com/sirupsen/logrus" + + "github.com/adrg/xdg" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/mitchellh/go-homedir" + "github.com/spf13/viper" + "gopkg.in/yaml.v2" +) + +var ( + ErrApplicationConfigNotFound = fmt.Errorf("application config not found") + catalogerEnabledDefault = false +) + +type defaultValueLoader interface { + loadDefaultValues(*viper.Viper) +} + +type parser interface { + parseConfigValues() error +} + +// Application is the main syft application configuration. +type Application struct { + // the location where the application config was read from (either from -c or discovered while loading); default .syft.yaml + ConfigPath string `yaml:"configPath,omitempty" json:"configPath" mapstructure:"config"` + Verbosity uint `yaml:"verbosity,omitempty" json:"verbosity" mapstructure:"verbosity"` + // -q, indicates to not show any status output to stderr (ETUI or logging UI) + Quiet bool `yaml:"quiet" json:"quiet" mapstructure:"quiet"` + Outputs []string `yaml:"output" json:"output" mapstructure:"output"` // -o, the format to use for output + OutputTemplatePath string `yaml:"output-template-path" json:"output-template-path" mapstructure:"output-template-path"` // -t template file to use for output + File string `yaml:"file" json:"file" mapstructure:"file"` // --file, the file to write report output to + CheckForAppUpdate bool `yaml:"check-for-app-update" json:"check-for-app-update" mapstructure:"check-for-app-update"` // whether to check for an application update on start up or not + Anchore anchore `yaml:"anchore" json:"anchore" mapstructure:"anchore"` // options for interacting with Anchore Engine/Enterprise + Dev development `yaml:"dev" json:"dev" mapstructure:"dev"` + Log logging `yaml:"log" json:"log" mapstructure:"log"` // all logging-related options + Catalogers []string `yaml:"catalogers" json:"catalogers" mapstructure:"catalogers"` + Package pkg `yaml:"package" json:"package" mapstructure:"package"` + FileMetadata FileMetadata `yaml:"file-metadata" json:"file-metadata" mapstructure:"file-metadata"` + FileClassification fileClassification `yaml:"file-classification" json:"file-classification" mapstructure:"file-classification"` + FileContents fileContents `yaml:"file-contents" json:"file-contents" mapstructure:"file-contents"` + Secrets secrets `yaml:"secrets" json:"secrets" mapstructure:"secrets"` + Registry registry `yaml:"registry" json:"registry" mapstructure:"registry"` + Exclusions []string `yaml:"exclude" json:"exclude" mapstructure:"exclude"` + Attest attest `yaml:"attest" json:"attest" mapstructure:"attest"` + Platform string `yaml:"platform" json:"platform" mapstructure:"platform"` +} + +func (cfg Application) ToCatalogerConfig() cataloger.Config { + return cataloger.Config{ + Search: cataloger.SearchConfig{ + IncludeIndexedArchives: cfg.Package.SearchIndexedArchives, + IncludeUnindexedArchives: cfg.Package.SearchUnindexedArchives, + Scope: cfg.Package.Cataloger.ScopeOpt, + }, + Catalogers: cfg.Catalogers, + } +} + +func (cfg *Application) LoadAllValues(v *viper.Viper, configPath string) error { + // priority order: viper.Set, flag, env, config, kv, defaults + // flags have already been loaded into viper by command construction + + // check if user specified config; otherwise read all possible paths + if err := loadConfig(v, configPath); err != nil { + if _, ok := err.(viper.ConfigFileNotFoundError); ok { + // Not Found; ignore this error + log.Debug("no config file found; proceeding with defaults") + } + } + + // load default config values into viper + loadDefaultValues(v) + + // load environment variables + v.SetEnvPrefix(internal.ApplicationName) + v.AllowEmptyEnv(true) + v.AutomaticEnv() + + // unmarshal fully populated viper object onto config + err := v.Unmarshal(cfg) + if err != nil { + return err + } + + // Convert all populated config options to their internal application values ex: scope string => scopeOpt source.Scope + return cfg.parseConfigValues() +} + +func (cfg *Application) parseConfigValues() error { + // parse options on this struct + var catalogers []string + for _, c := range cfg.Catalogers { + for _, f := range strings.Split(c, ",") { + catalogers = append(catalogers, strings.TrimSpace(f)) + } + } + sort.Strings(catalogers) + cfg.Catalogers = catalogers + + // parse application config options + for _, optionFn := range []func() error{ + cfg.parseUploadOptions, + cfg.parseLogLevelOption, + cfg.parseFile, + } { + if err := optionFn(); err != nil { + return err + } + } + // parse nested config options + // for each field in the configuration struct, see if the field implements the parser interface + // note: the app config is a pointer, so we need to grab the elements explicitly (to traverse the address) + value := reflect.ValueOf(cfg).Elem() + for i := 0; i < value.NumField(); i++ { + // note: since the interface method of parser is a pointer receiver we need to get the value of the field as a pointer. + if parsable, ok := value.Field(i).Addr().Interface().(parser); ok { + // the field implements parser, call it + if err := parsable.parseConfigValues(); err != nil { + return err + } + } + } + return nil +} + +func (cfg *Application) parseUploadOptions() error { + if cfg.Anchore.Host == "" && cfg.Anchore.Dockerfile != "" { + return fmt.Errorf("cannot provide dockerfile option without enabling upload") + } + return nil +} + +func (cfg *Application) parseLogLevelOption() error { + switch { + case cfg.Quiet: + // TODO: this is bad: quiet option trumps all other logging options (such as to a file on disk) + // we should be able to quiet the console logging and leave file logging alone... + // ... this will be an enhancement for later + cfg.Log.LevelOpt = logrus.PanicLevel + + case cfg.Verbosity > 0: + switch v := cfg.Verbosity; { + case v == 1: + cfg.Log.LevelOpt = logrus.InfoLevel + case v >= 2: + cfg.Log.LevelOpt = logrus.DebugLevel + default: + cfg.Log.LevelOpt = logrus.ErrorLevel + } + case cfg.Log.Level != "": + lvl, err := logrus.ParseLevel(strings.ToLower(cfg.Log.Level)) + if err != nil { + return fmt.Errorf("bad log level configured (%q): %w", cfg.Log.Level, err) + } + + cfg.Log.LevelOpt = lvl + if cfg.Log.LevelOpt >= logrus.InfoLevel { + cfg.Verbosity = 1 + } + default: + cfg.Log.LevelOpt = logrus.WarnLevel + } + + if cfg.Log.Level == "" { + cfg.Log.Level = cfg.Log.LevelOpt.String() + } + + return nil +} + +func (cfg *Application) parseFile() error { + if cfg.File != "" { + expandedPath, err := homedir.Expand(cfg.File) + if err != nil { + return fmt.Errorf("unable to expand file path=%q: %w", cfg.File, err) + } + cfg.File = expandedPath + } + return nil +} + +// init loads the default configuration values into the viper instance (before the config values are read and parsed). +func loadDefaultValues(v *viper.Viper) { + // set the default values for primitive fields in this struct + v.SetDefault("quiet", false) + v.SetDefault("check-for-app-update", true) + v.SetDefault("catalogers", nil) + + // for each field in the configuration struct, see if the field implements the defaultValueLoader interface and invoke it if it does + value := reflect.ValueOf(Application{}) + for i := 0; i < value.NumField(); i++ { + // note: the defaultValueLoader method receiver is NOT a pointer receiver. + if loadable, ok := value.Field(i).Interface().(defaultValueLoader); ok { + // the field implements defaultValueLoader, call it + loadable.loadDefaultValues(v) + } + } +} + +func (cfg Application) String() string { + // yaml is pretty human friendly (at least when compared to json) + appaStr, err := yaml.Marshal(&cfg) + + if err != nil { + return err.Error() + } + + return string(appaStr) +} + +func loadConfig(v *viper.Viper, configPath string) error { + var err error + // use explicitly the given user config + if configPath != "" { + v.SetConfigFile(configPath) + if err := v.ReadInConfig(); err != nil { + return fmt.Errorf("unable to read application config=%q : %w", configPath, err) + } + v.Set("config", v.ConfigFileUsed()) + // don't fall through to other options if the config path was explicitly provided + return nil + } + + // start searching for valid configs in order... + // 1. look for ..yaml (in the current directory) + v.AddConfigPath(".") + v.SetConfigName("." + internal.ApplicationName) + if err = v.ReadInConfig(); err == nil { + v.Set("config", v.ConfigFileUsed()) + return nil + } else if !errors.As(err, &viper.ConfigFileNotFoundError{}) { + return fmt.Errorf("unable to parse config=%q: %w", v.ConfigFileUsed(), err) + } + + // 2. look for ./config.yaml (in the current directory) + v.AddConfigPath("." + internal.ApplicationName) + v.SetConfigName("config") + if err = v.ReadInConfig(); err == nil { + v.Set("config", v.ConfigFileUsed()) + return nil + } else if !errors.As(err, &viper.ConfigFileNotFoundError{}) { + return fmt.Errorf("unable to parse config=%q: %w", v.ConfigFileUsed(), err) + } + + // 3. look for ~/..yaml + home, err := homedir.Dir() + if err == nil { + v.AddConfigPath(home) + v.SetConfigName("." + internal.ApplicationName) + if err = v.ReadInConfig(); err == nil { + v.Set("config", v.ConfigFileUsed()) + return nil + } else if !errors.As(err, &viper.ConfigFileNotFoundError{}) { + return fmt.Errorf("unable to parse config=%q: %w", v.ConfigFileUsed(), err) + } + } + + // 4. look for /config.yaml in xdg locations (starting with xdg home config dir, then moving upwards) + v.AddConfigPath(path.Join(xdg.ConfigHome, internal.ApplicationName)) + for _, dir := range xdg.ConfigDirs { + v.AddConfigPath(path.Join(dir, internal.ApplicationName)) + } + v.SetConfigName("config") + if err = v.ReadInConfig(); err == nil { + v.Set("config", v.ConfigFileUsed()) + return nil + } else if !errors.As(err, &viper.ConfigFileNotFoundError{}) { + return fmt.Errorf("unable to parse config=%q: %w", v.ConfigFileUsed(), err) + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/attest.go b/ci/tools/openeuler-purl/syft-dev/internal/config/attest.go new file mode 100644 index 0000000000000000000000000000000000000000..c59661e55f223d31d7198d4ef1bd358db14598d4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/attest.go @@ -0,0 +1,56 @@ +package config + +import ( + "fmt" + "os" + + "github.com/mitchellh/go-homedir" + "github.com/sigstore/cosign/cmd/cosign/cli/options" + "github.com/spf13/viper" +) + +// IMPORTANT: do not show the password in any YAML/JSON output (sensitive information) +type attest struct { + KeyRef string `yaml:"key" json:"key" mapstructure:"key"` // same as --key, file path to the private key + Cert string `yaml:"cert" json:"cert" mapstructure:"cert"` + NoUpload bool `yaml:"no_upload" json:"noUpload" mapstructure:"no_upload"` + Force bool `yaml:"force" json:"force" mapstructure:"force"` + Recursive bool `yaml:"recursive" json:"recursive" mapstructure:"recursive"` + Replace bool `yaml:"replace" json:"replace" mapstructure:"replace"` + Password string `yaml:"-" json:"-" mapstructure:"password"` // password for the private key + FulcioURL string `yaml:"fulcio_url" json:"fulcioUrl" mapstructure:"fulcio_url"` + FulcioIdentityToken string `yaml:"fulcio_identity_token" json:"fulcio_identity_token" mapstructure:"fulcio_identity_token"` + InsecureSkipFulcioVerify bool `yaml:"insecure_skip_verify" json:"insecure_skip_verify" mapstructure:"insecure_skip_verify"` + RekorURL string `yaml:"rekor_url" json:"rekorUrl" mapstructure:"rekor_url"` + OIDCIssuer string `yaml:"oidc_issuer" json:"oidcIssuer" mapstructure:"oidc_issuer"` + OIDCClientID string `yaml:"oidc_client_id" json:"oidcClientId" mapstructure:"oidc_client_id"` + OIDCRedirectURL string `yaml:"oidc_redirect_url" json:"OIDCRedirectURL" mapstructure:"oidc_redirect_url"` +} + +func (cfg *attest) parseConfigValues() error { + if cfg.KeyRef != "" { + expandedPath, err := homedir.Expand(cfg.KeyRef) + if err != nil { + return fmt.Errorf("unable to expand key path=%q: %w", cfg.KeyRef, err) + } + cfg.KeyRef = expandedPath + } + + if cfg.Password == "" { + // we allow for configuration via syft config/env vars and additionally interop with known cosign config env vars + if pw, ok := os.LookupEnv("COSIGN_PASSWORD"); ok { + cfg.Password = pw + } + } + + return nil +} + +func (cfg attest) loadDefaultValues(v *viper.Viper) { + v.SetDefault("attest.key", "") + v.SetDefault("attest.password", "") + v.SetDefault("attest.fulcio_url", options.DefaultFulcioURL) + v.SetDefault("attest.rekor_url", options.DefaultRekorURL) + v.SetDefault("attest.oidc_issuer", options.DefaultOIDCIssuerURL) + v.SetDefault("attest.oidc_client_id", "sigstore") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/cataloger_options.go b/ci/tools/openeuler-purl/syft-dev/internal/config/cataloger_options.go new file mode 100644 index 0000000000000000000000000000000000000000..1fb2992b44c9f9aa1465994a013302ddcf713504 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/cataloger_options.go @@ -0,0 +1,29 @@ +package config + +import ( + "fmt" + + "github.com/spf13/viper" + + "github.com/anchore/syft/syft/source" +) + +type catalogerOptions struct { + Enabled bool `yaml:"enabled" json:"enabled" mapstructure:"enabled"` + Scope string `yaml:"scope" json:"scope" mapstructure:"scope"` + ScopeOpt source.Scope `yaml:"-" json:"-"` +} + +func (cfg catalogerOptions) loadDefaultValues(v *viper.Viper) { + v.SetDefault("package.cataloger.enabled", true) +} + +func (cfg *catalogerOptions) parseConfigValues() error { + scopeOption := source.ParseScope(cfg.Scope) + if scopeOption == source.UnknownScope { + return fmt.Errorf("bad scope value %q", cfg.Scope) + } + cfg.ScopeOpt = scopeOption + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/config.go b/ci/tools/openeuler-purl/syft-dev/internal/config/config.go new file mode 100644 index 0000000000000000000000000000000000000000..d912156bec00a9f00850ab2ec3a3baf1016c2141 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/config.go @@ -0,0 +1 @@ +package config diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/development.go b/ci/tools/openeuler-purl/syft-dev/internal/config/development.go new file mode 100644 index 0000000000000000000000000000000000000000..4e1e8b01af87c1dfe28df0a6909e89c2d2e35a78 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/development.go @@ -0,0 +1,13 @@ +package config + +import "github.com/spf13/viper" + +type development struct { + ProfileCPU bool `yaml:"profile-cpu" json:"profile-cpu" mapstructure:"profile-cpu"` + ProfileMem bool `yaml:"profile-mem" json:"profile-mem" mapstructure:"profile-mem"` +} + +func (cfg development) loadDefaultValues(v *viper.Viper) { + v.SetDefault("dev.profile-cpu", false) + v.SetDefault("dev.profile-mem", false) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/file_classification.go b/ci/tools/openeuler-purl/syft-dev/internal/config/file_classification.go new file mode 100644 index 0000000000000000000000000000000000000000..f4ba630184e46005ee79259f92ab60efff0f0629 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/file_classification.go @@ -0,0 +1,19 @@ +package config + +import ( + "github.com/anchore/syft/syft/source" + "github.com/spf13/viper" +) + +type fileClassification struct { + Cataloger catalogerOptions `yaml:"cataloger" json:"cataloger" mapstructure:"cataloger"` +} + +func (cfg fileClassification) loadDefaultValues(v *viper.Viper) { + v.SetDefault("file-classification.cataloger.enabled", catalogerEnabledDefault) + v.SetDefault("file-classification.cataloger.scope", source.SquashedScope) +} + +func (cfg *fileClassification) parseConfigValues() error { + return cfg.Cataloger.parseConfigValues() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/file_contents.go b/ci/tools/openeuler-purl/syft-dev/internal/config/file_contents.go new file mode 100644 index 0000000000000000000000000000000000000000..f8c3c47d18b0cf40fe4d48ab2d1b2390a6e79c58 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/file_contents.go @@ -0,0 +1,24 @@ +package config + +import ( + "github.com/anchore/syft/internal/file" + "github.com/anchore/syft/syft/source" + "github.com/spf13/viper" +) + +type fileContents struct { + Cataloger catalogerOptions `yaml:"cataloger" json:"cataloger" mapstructure:"cataloger"` + SkipFilesAboveSize int64 `yaml:"skip-files-above-size" json:"skip-files-above-size" mapstructure:"skip-files-above-size"` + Globs []string `yaml:"globs" json:"globs" mapstructure:"globs"` +} + +func (cfg fileContents) loadDefaultValues(v *viper.Viper) { + v.SetDefault("file-contents.cataloger.enabled", catalogerEnabledDefault) + v.SetDefault("file-contents.cataloger.scope", source.SquashedScope) + v.SetDefault("file-contents.skip-files-above-size", 1*file.MB) + v.SetDefault("file-contents.globs", []string{}) +} + +func (cfg *fileContents) parseConfigValues() error { + return cfg.Cataloger.parseConfigValues() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/file_metadata.go b/ci/tools/openeuler-purl/syft-dev/internal/config/file_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..764b9b3925fea089bedd712470837317c3fb7b8e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/file_metadata.go @@ -0,0 +1,21 @@ +package config + +import ( + "github.com/anchore/syft/syft/source" + "github.com/spf13/viper" +) + +type FileMetadata struct { + Cataloger catalogerOptions `yaml:"cataloger" json:"cataloger" mapstructure:"cataloger"` + Digests []string `yaml:"digests" json:"digests" mapstructure:"digests"` +} + +func (cfg FileMetadata) loadDefaultValues(v *viper.Viper) { + v.SetDefault("file-metadata.cataloger.enabled", catalogerEnabledDefault) + v.SetDefault("file-metadata.cataloger.scope", source.SquashedScope) + v.SetDefault("file-metadata.digests", []string{"sha256"}) +} + +func (cfg *FileMetadata) parseConfigValues() error { + return cfg.Cataloger.parseConfigValues() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/logging.go b/ci/tools/openeuler-purl/syft-dev/internal/config/logging.go new file mode 100644 index 0000000000000000000000000000000000000000..6d6909d42fa4885af46523a4b190796a5c41c99c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/logging.go @@ -0,0 +1,33 @@ +package config + +import ( + "fmt" + + "github.com/mitchellh/go-homedir" + "github.com/sirupsen/logrus" + "github.com/spf13/viper" +) + +// logging contains all logging-related configuration options available to the user via the application config. +type logging struct { + Structured bool `yaml:"structured" json:"structured" mapstructure:"structured"` // show all log entries as JSON formatted strings + LevelOpt logrus.Level `yaml:"-" json:"-"` // the native log level object used by the logger + Level string `yaml:"level" json:"level" mapstructure:"level"` // the log level string hint + FileLocation string `yaml:"file" json:"file-location" mapstructure:"file"` // the file path to write logs to +} + +func (cfg *logging) parseConfigValues() error { + if cfg.FileLocation != "" { + expandedPath, err := homedir.Expand(cfg.FileLocation) + if err != nil { + return fmt.Errorf("unable to expand log file path=%q: %w", cfg.FileLocation, err) + } + cfg.FileLocation = expandedPath + } + return nil +} + +func (cfg logging) loadDefaultValues(v *viper.Viper) { + v.SetDefault("log.structured", false) + v.SetDefault("log.file", "") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/pkg.go b/ci/tools/openeuler-purl/syft-dev/internal/config/pkg.go new file mode 100644 index 0000000000000000000000000000000000000000..88d6225414aacbe6df8270c5307856f9cffca424 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/pkg.go @@ -0,0 +1,23 @@ +package config + +import ( + "github.com/anchore/syft/syft/pkg/cataloger" + "github.com/spf13/viper" +) + +type pkg struct { + Cataloger catalogerOptions `yaml:"cataloger" json:"cataloger" mapstructure:"cataloger"` + SearchUnindexedArchives bool `yaml:"search-unindexed-archives" json:"search-unindexed-archives" mapstructure:"search-unindexed-archives"` + SearchIndexedArchives bool `yaml:"search-indexed-archives" json:"search-indexed-archives" mapstructure:"search-indexed-archives"` +} + +func (cfg pkg) loadDefaultValues(v *viper.Viper) { + cfg.Cataloger.loadDefaultValues(v) + c := cataloger.DefaultSearchConfig() + v.SetDefault("package.search-unindexed-archives", c.IncludeUnindexedArchives) + v.SetDefault("package.search-indexed-archives", c.IncludeIndexedArchives) +} + +func (cfg *pkg) parseConfigValues() error { + return cfg.Cataloger.parseConfigValues() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/registry.go b/ci/tools/openeuler-purl/syft-dev/internal/config/registry.go new file mode 100644 index 0000000000000000000000000000000000000000..6ae85d3e770de0494324c97f227cb4cd287aed22 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/registry.go @@ -0,0 +1,75 @@ +package config + +import ( + "os" + + "github.com/anchore/stereoscope/pkg/image" + + "github.com/spf13/viper" +) + +type RegistryCredentials struct { + Authority string `yaml:"authority" json:"authority" mapstructure:"authority"` + // IMPORTANT: do not show the username in any YAML/JSON output (sensitive information) + Username string `yaml:"-" json:"-" mapstructure:"username"` + // IMPORTANT: do not show the password in any YAML/JSON output (sensitive information) + Password string `yaml:"-" json:"-" mapstructure:"password"` + // IMPORTANT: do not show the token in any YAML/JSON output (sensitive information) + Token string `yaml:"-" json:"-" mapstructure:"token"` +} + +type registry struct { + InsecureSkipTLSVerify bool `yaml:"insecure-skip-tls-verify" json:"insecure-skip-tls-verify" mapstructure:"insecure-skip-tls-verify"` + InsecureUseHTTP bool `yaml:"insecure-use-http" json:"insecure-use-http" mapstructure:"insecure-use-http"` + Auth []RegistryCredentials `yaml:"auth" json:"auth" mapstructure:"auth"` +} + +func (cfg registry) loadDefaultValues(v *viper.Viper) { + v.SetDefault("registry.insecure-skip-tls-verify", false) + v.SetDefault("registry.insecure-use-http", false) + v.SetDefault("registry.auth", []RegistryCredentials{}) +} + +//nolint:unparam +func (cfg *registry) parseConfigValues() error { + // there may be additional credentials provided by env var that should be appended to the set of credentials + authority, username, password, token := + os.Getenv("SYFT_REGISTRY_AUTH_AUTHORITY"), + os.Getenv("SYFT_REGISTRY_AUTH_USERNAME"), + os.Getenv("SYFT_REGISTRY_AUTH_PASSWORD"), + os.Getenv("SYFT_REGISTRY_AUTH_TOKEN") + + if hasNonEmptyCredentials(username, password, token) { + // note: we prepend the credentials such that the environment variables take precedence over on-disk configuration. + cfg.Auth = append([]RegistryCredentials{ + { + Authority: authority, + Username: username, + Password: password, + Token: token, + }, + }, cfg.Auth...) + } + return nil +} + +func hasNonEmptyCredentials(username, password, token string) bool { + return password != "" && username != "" || token != "" +} + +func (cfg *registry) ToOptions() *image.RegistryOptions { + var auth = make([]image.RegistryCredentials, len(cfg.Auth)) + for i, a := range cfg.Auth { + auth[i] = image.RegistryCredentials{ + Authority: a.Authority, + Username: a.Username, + Password: a.Password, + Token: a.Token, + } + } + return &image.RegistryOptions{ + InsecureSkipTLSVerify: cfg.InsecureSkipTLSVerify, + InsecureUseHTTP: cfg.InsecureUseHTTP, + Credentials: auth, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/registry_test.go b/ci/tools/openeuler-purl/syft-dev/internal/config/registry_test.go new file mode 100644 index 0000000000000000000000000000000000000000..6d9ecf280e84663963b7a044fc67b368fdd5d8c7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/registry_test.go @@ -0,0 +1,112 @@ +package config + +import ( + "fmt" + "testing" + + "github.com/anchore/stereoscope/pkg/image" + + "github.com/stretchr/testify/assert" +) + +func TestHasNonEmptyCredentials(t *testing.T) { + tests := []struct { + username, password, token string + expected bool + }{ + + { + "", "", "", + false, + }, + { + "user", "", "", + false, + }, + { + "", "pass", "", + false, + }, + { + "", "pass", "tok", + true, + }, + { + "user", "", "tok", + true, + }, + { + "", "", "tok", + true, + }, + { + "user", "pass", "tok", + true, + }, + + { + "user", "pass", "", + true, + }, + } + + for _, test := range tests { + t.Run(fmt.Sprintf("%+v", test), func(t *testing.T) { + assert.Equal(t, test.expected, hasNonEmptyCredentials(test.username, test.password, test.token)) + }) + } +} + +func Test_registry_ToOptions(t *testing.T) { + tests := []struct { + name string + input registry + expected image.RegistryOptions + }{ + { + name: "no registry options", + input: registry{}, + expected: image.RegistryOptions{ + Credentials: []image.RegistryCredentials{}, + }, + }, + { + name: "set InsecureSkipTLSVerify", + input: registry{ + InsecureSkipTLSVerify: true, + }, + expected: image.RegistryOptions{ + InsecureSkipTLSVerify: true, + Credentials: []image.RegistryCredentials{}, + }, + }, + { + name: "set InsecureUseHTTP", + input: registry{ + InsecureUseHTTP: true, + }, + expected: image.RegistryOptions{ + InsecureUseHTTP: true, + Credentials: []image.RegistryCredentials{}, + }, + }, + { + name: "set all bool options", + input: registry{ + InsecureSkipTLSVerify: true, + InsecureUseHTTP: true, + }, + expected: image.RegistryOptions{ + InsecureSkipTLSVerify: true, + InsecureUseHTTP: true, + Credentials: []image.RegistryCredentials{}, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, &test.expected, test.input.ToOptions()) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/config/secrets.go b/ci/tools/openeuler-purl/syft-dev/internal/config/secrets.go new file mode 100644 index 0000000000000000000000000000000000000000..2c07dd4987ef3d7f4022bb1f91394e57e2c66daa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/config/secrets.go @@ -0,0 +1,28 @@ +package config + +import ( + "github.com/anchore/syft/internal/file" + "github.com/anchore/syft/syft/source" + "github.com/spf13/viper" +) + +type secrets struct { + Cataloger catalogerOptions `yaml:"cataloger" json:"cataloger" mapstructure:"cataloger"` + AdditionalPatterns map[string]string `yaml:"additional-patterns" json:"additional-patterns" mapstructure:"additional-patterns"` + ExcludePatternNames []string `yaml:"exclude-pattern-names" json:"exclude-pattern-names" mapstructure:"exclude-pattern-names"` + RevealValues bool `yaml:"reveal-values" json:"reveal-values" mapstructure:"reveal-values"` + SkipFilesAboveSize int64 `yaml:"skip-files-above-size" json:"skip-files-above-size" mapstructure:"skip-files-above-size"` +} + +func (cfg secrets) loadDefaultValues(v *viper.Viper) { + v.SetDefault("secrets.cataloger.enabled", catalogerEnabledDefault) + v.SetDefault("secrets.cataloger.scope", source.AllLayersScope) + v.SetDefault("secrets.reveal-values", false) + v.SetDefault("secrets.skip-files-above-size", 1*file.MB) + v.SetDefault("secrets.additional-patterns", map[string]string{}) + v.SetDefault("secrets.exclude-pattern-names", []string{}) +} + +func (cfg *secrets) parseConfigValues() error { + return cfg.Cataloger.parseConfigValues() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/constants.go b/ci/tools/openeuler-purl/syft-dev/internal/constants.go new file mode 100644 index 0000000000000000000000000000000000000000..6fcf68a47938f698ab6d46bef9ca364373d81b9a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/constants.go @@ -0,0 +1,10 @@ +package internal + +const ( + // ApplicationName is the non-capitalized name of the application (do not change this) + ApplicationName = "syft" + + // JSONSchemaVersion is the current schema version output by the JSON encoder + // This is roughly following the "SchemaVer" guidelines for versioning the JSON schema. Please see schema/json/README.md for details on how to increment. + JSONSchemaVersion = "3.3.2" +) diff --git a/ci/tools/openeuler-purl/syft-dev/internal/docs.go b/ci/tools/openeuler-purl/syft-dev/internal/docs.go new file mode 100644 index 0000000000000000000000000000000000000000..d06d47f6a1733e97adab6db84950a06cd01268b7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/docs.go @@ -0,0 +1,4 @@ +/* +Package internal contains miscellaneous functions and objects useful within syft but should not be used externally. +*/ +package internal diff --git a/ci/tools/openeuler-purl/syft-dev/internal/err_helper.go b/ci/tools/openeuler-purl/syft-dev/internal/err_helper.go new file mode 100644 index 0000000000000000000000000000000000000000..132b60f89c227f732fe3af09f1e64b248917a45a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/err_helper.go @@ -0,0 +1,39 @@ +package internal + +import ( + "fmt" + "io" + "os" + + "github.com/anchore/syft/internal/log" +) + +// CloseAndLogError closes the given io.Closer and reports any errors found as a warning in the log +func CloseAndLogError(closer io.Closer, location string) { + if err := closer.Close(); err != nil { + log.Warnf("unable to close file for location=%q: %+v", location, err) + } +} + +type ErrPath struct { + Context string + Path string + Err error +} + +func (e ErrPath) Error() string { + return fmt.Sprintf("%s unable to observe contents of %+v: %v", e.Context, e.Path, e.Err) +} + +func IsErrPath(err error) bool { + _, ok := err.(ErrPath) + return ok +} + +func IsErrPathPermission(err error) bool { + pathErr, ok := err.(ErrPath) + if ok { + return os.IsPermission(pathErr.Err) + } + return ok +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/copy.go b/ci/tools/openeuler-purl/syft-dev/internal/file/copy.go new file mode 100644 index 0000000000000000000000000000000000000000..d569dcc4cf5b606e7e9ed50f1e0ff836ba9c0b82 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/copy.go @@ -0,0 +1,19 @@ +package file + +import ( + "errors" + "fmt" + "io" +) + +const perFileReadLimit = 2 * GB + +// safeCopy limits the copy from the reader. This is useful when extracting files from archives to +// protect against decompression bomb attacks. +func safeCopy(writer io.Writer, reader io.Reader) error { + numBytes, err := io.Copy(writer, io.LimitReader(reader, perFileReadLimit)) + if numBytes >= perFileReadLimit || errors.Is(err, io.EOF) { + return fmt.Errorf("zip read limit hit (potential decompression bomb attack)") + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/glob_match.go b/ci/tools/openeuler-purl/syft-dev/internal/file/glob_match.go new file mode 100644 index 0000000000000000000000000000000000000000..6befe32e4102c2b0c1c8923aadc1e79097ae5225 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/glob_match.go @@ -0,0 +1,46 @@ +package file + +// GlobMatch evaluates the given glob pattern against the given "name" string, indicating if there is a match or not. +// Source: https://research.swtch.com/glob.go +func GlobMatch(pattern, name string) bool { + px := 0 + nx := 0 + nextPx := 0 + nextNx := 0 + for px < len(pattern) || nx < len(name) { + if px < len(pattern) { + c := pattern[px] + switch c { + default: // ordinary character + if nx < len(name) && name[nx] == c { + px++ + nx++ + continue + } + case '?': // single-character wildcard + if nx < len(name) { + px++ + nx++ + continue + } + case '*': // zero-or-more-character wildcard + // Try to match at nx. + // If that doesn't work out, + // restart at nx+1 next. + nextPx = px + nextNx = nx + 1 + px++ + continue + } + } + // Mismatch. Maybe restart. + if 0 < nextNx && nextNx <= len(name) { + px = nextPx + nx = nextNx + continue + } + return false + } + // Matched all of pattern to all of name. Success. + return true +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/glob_match_test.go b/ci/tools/openeuler-purl/syft-dev/internal/file/glob_match_test.go new file mode 100644 index 0000000000000000000000000000000000000000..aab2803dc9a29711c2aa5e6e25e38aec8d976259 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/glob_match_test.go @@ -0,0 +1,39 @@ +package file + +import ( + "strings" + "testing" +) + +func TestGlobMatch(t *testing.T) { + var tests = []struct { + pattern string + data string + ok bool + }{ + {"", "", true}, + {"x", "", false}, + {"", "x", false}, + {"abc", "abc", true}, + {"*", "abc", true}, + {"*c", "abc", true}, + {"*b", "abc", false}, + {"a*", "abc", true}, + {"b*", "abc", false}, + {"a*", "a", true}, + {"*a", "a", true}, + {"a*b*c*d*e*", "axbxcxdxe", true}, + {"a*b*c*d*e*", "axbxcxdxexxx", true}, + {"a*b?c*x", "abxbbxdbxebxczzx", true}, + {"a*b?c*x", "abxbbxdbxebxczzy", false}, + {"a*a*a*a*b", strings.Repeat("a", 100), false}, + {"*x", "xxx", true}, + {"/home/place/**", "/home/place/a/thing", true}, + } + + for _, test := range tests { + if GlobMatch(test.pattern, test.data) != test.ok { + t.Errorf("failed glob='%s' data='%s'", test.pattern, test.data) + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/opener.go b/ci/tools/openeuler-purl/syft-dev/internal/file/opener.go new file mode 100644 index 0000000000000000000000000000000000000000..969930f11ffdeede7b02483c64e60d85bd8485c2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/opener.go @@ -0,0 +1,16 @@ +package file + +import ( + "io" + "os" +) + +// Opener is an object that stores a path to later be opened as a file. +type Opener struct { + path string +} + +// Open the stored path as a io.ReadCloser. +func (o Opener) Open() (io.ReadCloser, error) { + return os.Open(o.path) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/tar_file_traversal.go b/ci/tools/openeuler-purl/syft-dev/internal/file/tar_file_traversal.go new file mode 100644 index 0000000000000000000000000000000000000000..dbe2a60f6b4d139cc60708e4d2182dc9a82954b3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/tar_file_traversal.go @@ -0,0 +1,64 @@ +package file + +import ( + "fmt" + "os" + "path/filepath" + + "github.com/bmatcuk/doublestar/v4" + "github.com/mholt/archiver/v3" +) + +// ExtractGlobsFromTarToUniqueTempFile extracts paths matching the given globs within the given archive to a temporary directory, returning file openers for each file extracted. +func ExtractGlobsFromTarToUniqueTempFile(archivePath, dir string, globs ...string) (map[string]Opener, error) { + results := make(map[string]Opener) + + // don't allow for full traversal, only select traversal from given paths + if len(globs) == 0 { + return results, nil + } + + visitor := func(file archiver.File) error { + defer file.Close() + + // ignore directories + if file.FileInfo.IsDir() { + return nil + } + + // ignore any filename that doesn't match the given globs... + if !matchesAnyGlob(file.Name(), globs...) { + return nil + } + + // we have a file we want to extract.... + tempfilePrefix := filepath.Base(filepath.Clean(file.Name())) + "-" + tempFile, err := os.CreateTemp(dir, tempfilePrefix) + if err != nil { + return fmt.Errorf("unable to create temp file: %w", err) + } + // we shouldn't try and keep the tempfile open as the returned result may have several files, which takes up + // resources (leading to "too many open files"). Instead we'll return a file opener to the caller which + // provides a ReadCloser. It is up to the caller to handle closing the file explicitly. + defer tempFile.Close() + + if err := safeCopy(tempFile, file.ReadCloser); err != nil { + return fmt.Errorf("unable to copy source=%q for tar=%q: %w", file.Name(), archivePath, err) + } + + results[file.Name()] = Opener{path: tempFile.Name()} + + return nil + } + + return results, archiver.Walk(archivePath, visitor) +} + +func matchesAnyGlob(name string, globs ...string) bool { + for _, glob := range globs { + if matches, err := doublestar.PathMatch(glob, name); err == nil && matches { + return true + } + } + return false +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/generate-zip-fixture-from-source-dir.sh b/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/generate-zip-fixture-from-source-dir.sh new file mode 100755 index 0000000000000000000000000000000000000000..f73ea4ba0f64108b2e2419cba22c777a5a7077b6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/generate-zip-fixture-from-source-dir.sh @@ -0,0 +1,12 @@ +#!/usr/bin/env bash +set -eux + +# $1 —— absolute path to destination file, should end with .zip, ideally +# $2 —— absolute path to directory from which to add entries to the archive +# $3 —— if files should be zip64 or not + +if [[$3]]; then + pushd "$2" && find . -print | zip -fz "$1" -@ && popd +else + pushd "$2" && find . -print | zip "$1" -@ && popd +fi diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/zip-source/b-file.txt b/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/zip-source/b-file.txt new file mode 100644 index 0000000000000000000000000000000000000000..a8f5b7786e8e841f5c18048b4b1f64a907f6e972 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/zip-source/b-file.txt @@ -0,0 +1 @@ +B file... \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/zip-source/some-dir/a-file.txt b/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/zip-source/some-dir/a-file.txt new file mode 100644 index 0000000000000000000000000000000000000000..3658752202e70baf807897c9c563d273f6243f18 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/test-fixtures/zip-source/some-dir/a-file.txt @@ -0,0 +1 @@ +A file! nice! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_helpers_test.go b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_helpers_test.go new file mode 100644 index 0000000000000000000000000000000000000000..7a76be3b01a6d57cec7f0b5beed3cf913c499742 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_helpers_test.go @@ -0,0 +1,119 @@ +package file + +import ( + "io/ioutil" + "os" + "os/exec" + "path" + "path/filepath" + "syscall" + "testing" + + "github.com/stretchr/testify/assert" +) + +var expectedZipArchiveEntries = []string{ + "some-dir" + string(os.PathSeparator), + filepath.Join("some-dir", "a-file.txt"), + "b-file.txt", + "nested.zip", +} + +// createZipArchive creates a new ZIP archive file at destinationArchivePath based on the directory found at +// sourceDirPath. It forces a zip64 archive if zip64 is "0". +func createZipArchive(t testing.TB, sourceDirPath, destinationArchivePath string, zip64 bool) { + t.Helper() + + cwd, err := os.Getwd() + if err != nil { + t.Fatalf("unable to get cwd: %+v", err) + } + zip64Arg := "0" + if zip64 { + zip64Arg = "1" + } + + cmd := exec.Command("./generate-zip-fixture-from-source-dir.sh", destinationArchivePath, path.Base(sourceDirPath), zip64Arg) + cmd.Dir = filepath.Join(cwd, "test-fixtures") + + if err := cmd.Start(); err != nil { + t.Fatalf("unable to start generate zip fixture script: %+v", err) + } + + if err := cmd.Wait(); err != nil { + if exiterr, ok := err.(*exec.ExitError); ok { + // The program has exited with an exit code != 0 + + // This works on both Unix and Windows. Although package + // syscall is generally platform dependent, WaitStatus is + // defined for both Unix and Windows and in both cases has + // an ExitStatus() method with the same signature. + if status, ok := exiterr.Sys().(syscall.WaitStatus); ok { + if status.ExitStatus() != 0 { + t.Fatalf("failed to generate fixture: rc=%d", status.ExitStatus()) + } + } + } else { + t.Fatalf("unable to get generate fixture script result: %+v", err) + } + } + +} + +func assertNoError(t testing.TB, fn func() error) func() { + return func() { + assert.NoError(t, fn()) + } +} + +// setupZipFileTest encapsulates common test setup work for zip file tests. It returns a cleanup function, +// which should be called (typically deferred) by the caller, the path of the created zip archive, and an error, +// which should trigger a fatal test failure in the consuming test. The returned cleanup function will never be nil +// (even if there's an error), and it should always be called. +func setupZipFileTest(t testing.TB, sourceDirPath string, zip64 bool) string { + t.Helper() + + archivePrefix, err := ioutil.TempFile("", "syft-ziputil-archive-TEST-") + if err != nil { + t.Fatalf("unable to create tempfile: %+v", err) + } + + t.Cleanup( + assertNoError(t, + func() error { + return os.Remove(archivePrefix.Name()) + }, + ), + ) + + destinationArchiveFilePath := archivePrefix.Name() + ".zip" + t.Logf("archive path: %s", destinationArchiveFilePath) + createZipArchive(t, sourceDirPath, destinationArchiveFilePath, zip64) + + t.Cleanup( + assertNoError(t, + func() error { + return os.Remove(destinationArchiveFilePath) + }, + ), + ) + + cwd, err := os.Getwd() + if err != nil { + t.Fatalf("unable to get cwd: %+v", err) + } + + t.Logf("running from: %s", cwd) + + return destinationArchiveFilePath +} + +// TODO: Consider moving any non-git asset generation to a task (e.g. make) that's run ahead of running go tests. +func ensureNestedZipExists(t *testing.T, sourceDirPath string) error { + t.Helper() + + nestedArchiveFilePath := path.Join(sourceDirPath, "nested.zip") + createZipArchive(t, sourceDirPath, nestedArchiveFilePath, false) + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_manifest.go b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_manifest.go new file mode 100644 index 0000000000000000000000000000000000000000..700c1472bcfeeb63287369a6ea889dbe47a7260e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_manifest.go @@ -0,0 +1,70 @@ +package file + +import ( + "fmt" + "os" + "sort" + "strings" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" +) + +// ZipFileManifest is a collection of paths and their file metadata. +type ZipFileManifest map[string]os.FileInfo + +// NewZipFileManifest creates and returns a new ZipFileManifest populated with path and metadata from the given zip archive path. +func NewZipFileManifest(archivePath string) (ZipFileManifest, error) { + zipReader, err := OpenZip(archivePath) + manifest := make(ZipFileManifest) + if err != nil { + return manifest, fmt.Errorf("unable to open zip archive (%s): %w", archivePath, err) + } + defer func() { + err = zipReader.Close() + if err != nil { + log.Warnf("unable to close zip archive (%s): %+v", archivePath, err) + } + }() + + for _, file := range zipReader.Reader.File { + manifest.Add(file.Name, file.FileInfo()) + } + return manifest, nil +} + +// Add a new path and it's file metadata to the collection. +func (z ZipFileManifest) Add(entry string, info os.FileInfo) { + z[entry] = info +} + +// GlobMatch returns the path keys that match the given value(s). +func (z ZipFileManifest) GlobMatch(patterns ...string) []string { + uniqueMatches := internal.NewStringSet() + + for _, pattern := range patterns { + for entry := range z { + // We want to match globs as if entries begin with a leading slash (akin to an absolute path) + // so that glob logic is consistent inside and outside of ZIP archives + normalizedEntry := normalizeZipEntryName(entry) + + if GlobMatch(pattern, normalizedEntry) { + uniqueMatches.Add(entry) + } + } + } + + results := uniqueMatches.ToSlice() + sort.Strings(results) + + return results +} + +// normalizeZipEntryName takes the given path entry and ensures it is prefixed with "/". +func normalizeZipEntryName(entry string) string { + if !strings.HasPrefix(entry, "/") { + return "/" + entry + } + + return entry +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_manifest_test.go b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_manifest_test.go new file mode 100644 index 0000000000000000000000000000000000000000..b9b475e27d5144729cac1cf1746e8f022f235ac8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_manifest_test.go @@ -0,0 +1,138 @@ +//go:build !windows +// +build !windows + +package file + +import ( + "encoding/json" + "os" + "path" + "testing" +) + +func TestNewZipFileManifest(t *testing.T) { + cwd, err := os.Getwd() + if err != nil { + t.Fatal(err) + } + + sourceDirPath := path.Join(cwd, "test-fixtures", "zip-source") + err = ensureNestedZipExists(t, sourceDirPath) + if err != nil { + t.Fatal(err) + } + + archiveFilePath := setupZipFileTest(t, sourceDirPath, false) + + actual, err := NewZipFileManifest(archiveFilePath) + if err != nil { + t.Fatalf("unable to extract from unzip archive: %+v", err) + } + + if len(expectedZipArchiveEntries) != len(actual) { + t.Fatalf("mismatched manifest: %d != %d", len(actual), len(expectedZipArchiveEntries)) + } + + for _, e := range expectedZipArchiveEntries { + _, ok := actual[e] + if !ok { + t.Errorf("missing path: %s", e) + } + } + + if t.Failed() { + b, err := json.MarshalIndent(actual, "", " ") + if err != nil { + t.Fatalf("can't show results: %+v", err) + } + + t.Errorf("full result: %s", string(b)) + } +} + +func TestNewZip64FileManifest(t *testing.T) { + cwd, err := os.Getwd() + if err != nil { + t.Fatal(err) + } + + sourceDirPath := path.Join(cwd, "test-fixtures", "zip-source") + archiveFilePath := setupZipFileTest(t, sourceDirPath, true) + + actual, err := NewZipFileManifest(archiveFilePath) + if err != nil { + t.Fatalf("unable to extract from unzip archive: %+v", err) + } + + if len(expectedZipArchiveEntries) != len(actual) { + t.Fatalf("mismatched manifest: %d != %d", len(actual), len(expectedZipArchiveEntries)) + } + + for _, e := range expectedZipArchiveEntries { + _, ok := actual[e] + if !ok { + t.Errorf("missing path: %s", e) + } + } + + if t.Failed() { + b, err := json.MarshalIndent(actual, "", " ") + if err != nil { + t.Fatalf("can't show results: %+v", err) + } + + t.Errorf("full result: %s", string(b)) + } +} + +func TestZipFileManifest_GlobMatch(t *testing.T) { + cwd, err := os.Getwd() + if err != nil { + t.Fatal(err) + } + + sourceDirPath := path.Join(cwd, "test-fixtures", "zip-source") + err = ensureNestedZipExists(t, sourceDirPath) + if err != nil { + t.Fatal(err) + } + + archiveFilePath := setupZipFileTest(t, sourceDirPath, false) + + z, err := NewZipFileManifest(archiveFilePath) + if err != nil { + t.Fatalf("unable to extract from unzip archive: %+v", err) + } + + cases := []struct { + glob string + expected string + }{ + { + "/b*", + "b-file.txt", + }, + { + "*/a-file.txt", + "some-dir/a-file.txt", + }, + { + "**/*.zip", + "nested.zip", + }, + } + + for _, tc := range cases { + t.Run(tc.glob, func(t *testing.T) { + glob := tc.glob + + results := z.GlobMatch(glob) + + if len(results) == 1 && results[0] == tc.expected { + return + } + + t.Errorf("unexpected results for glob '%s': %+v", glob, results) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_traversal.go b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_traversal.go new file mode 100644 index 0000000000000000000000000000000000000000..9b8025419027334c530fc7563b48b229fac50da7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_traversal.go @@ -0,0 +1,224 @@ +package file + +import ( + "archive/zip" + "bytes" + "fmt" + "os" + "path/filepath" + "strings" + + "github.com/anchore/syft/internal/log" +) + +const ( + // represents the order of bytes + _ = iota + KB = 1 << (10 * iota) + MB + GB +) + +type errZipSlipDetected struct { + Prefix string + JoinArgs []string +} + +func (e *errZipSlipDetected) Error() string { + return fmt.Sprintf("paths are not allowed to resolve outside of the root prefix (%q). Destination: %q", e.Prefix, e.JoinArgs) +} + +type zipTraversalRequest map[string]struct{} + +func newZipTraverseRequest(paths ...string) zipTraversalRequest { + results := make(zipTraversalRequest) + for _, p := range paths { + results[p] = struct{}{} + } + return results +} + +// TraverseFilesInZip enumerates all paths stored within a zip archive using the visitor pattern. +func TraverseFilesInZip(archivePath string, visitor func(*zip.File) error, paths ...string) error { + request := newZipTraverseRequest(paths...) + + zipReader, err := OpenZip(archivePath) + if err != nil { + return fmt.Errorf("unable to open zip archive (%s): %w", archivePath, err) + } + defer func() { + err = zipReader.Close() + if err != nil { + log.Errorf("unable to close zip archive (%s): %+v", archivePath, err) + } + }() + + for _, file := range zipReader.Reader.File { + // if no paths are given then assume that all files should be traversed + if len(paths) > 0 { + if _, ok := request[file.Name]; !ok { + // this file path is not of interest + continue + } + } + + if err = visitor(file); err != nil { + return err + } + } + return nil +} + +// ExtractFromZipToUniqueTempFile extracts select paths for the given archive to a temporary directory, returning file openers for each file extracted. +func ExtractFromZipToUniqueTempFile(archivePath, dir string, paths ...string) (map[string]Opener, error) { + results := make(map[string]Opener) + + // don't allow for full traversal, only select traversal from given paths + if len(paths) == 0 { + return results, nil + } + + visitor := func(file *zip.File) error { + tempfilePrefix := filepath.Base(filepath.Clean(file.Name)) + "-" + + tempFile, err := os.CreateTemp(dir, tempfilePrefix) + if err != nil { + return fmt.Errorf("unable to create temp file: %w", err) + } + // we shouldn't try and keep the tempfile open as the returned result may have several files, which takes up + // resources (leading to "too many open files"). Instead we'll return a file opener to the caller which + // provides a ReadCloser. It is up to the caller to handle closing the file explicitly. + defer tempFile.Close() + + zippedFile, err := file.Open() + if err != nil { + return fmt.Errorf("unable to read file=%q from zip=%q: %w", file.Name, archivePath, err) + } + defer func() { + err := zippedFile.Close() + if err != nil { + log.Errorf("unable to close source file=%q from zip=%q: %+v", file.Name, archivePath, err) + } + }() + + if file.FileInfo().IsDir() { + return fmt.Errorf("unable to extract directories, only files: %s", file.Name) + } + + if err := safeCopy(tempFile, zippedFile); err != nil { + return fmt.Errorf("unable to copy source=%q for zip=%q: %w", file.Name, archivePath, err) + } + + results[file.Name] = Opener{path: tempFile.Name()} + + return nil + } + + return results, TraverseFilesInZip(archivePath, visitor, paths...) +} + +// ContentsFromZip extracts select paths for the given archive and returns a set of string contents for each path. +func ContentsFromZip(archivePath string, paths ...string) (map[string]string, error) { + results := make(map[string]string) + + // don't allow for full traversal, only select traversal from given paths + if len(paths) == 0 { + return results, nil + } + + visitor := func(file *zip.File) error { + zippedFile, err := file.Open() + if err != nil { + return fmt.Errorf("unable to read file=%q from zip=%q: %w", file.Name, archivePath, err) + } + + if file.FileInfo().IsDir() { + return fmt.Errorf("unable to extract directories, only files: %s", file.Name) + } + + var buffer bytes.Buffer + if err := safeCopy(&buffer, zippedFile); err != nil { + return fmt.Errorf("unable to copy source=%q for zip=%q: %w", file.Name, archivePath, err) + } + + results[file.Name] = buffer.String() + + err = zippedFile.Close() + if err != nil { + return fmt.Errorf("unable to close source file=%q from zip=%q: %w", file.Name, archivePath, err) + } + return nil + } + + return results, TraverseFilesInZip(archivePath, visitor, paths...) +} + +// UnzipToDir extracts a zip archive to a target directory. +func UnzipToDir(archivePath, targetDir string) error { + visitor := func(file *zip.File) error { + joinedPath, err := safeJoin(targetDir, file.Name) + if err != nil { + return err + } + + if err = extractSingleFile(file, joinedPath, archivePath); err != nil { + return err + } + return nil + } + + return TraverseFilesInZip(archivePath, visitor) +} + +// safeJoin ensures that any destinations do not resolve to a path above the prefix path. +func safeJoin(prefix string, dest ...string) (string, error) { + joinResult := filepath.Join(append([]string{prefix}, dest...)...) + cleanJoinResult := filepath.Clean(joinResult) + if !strings.HasPrefix(cleanJoinResult, filepath.Clean(prefix)) { + return "", &errZipSlipDetected{ + Prefix: prefix, + JoinArgs: dest, + } + } + // why not return the clean path? the called may not be expected it from what should only be a join operation. + return joinResult, nil +} + +func extractSingleFile(file *zip.File, expandedFilePath, archivePath string) error { + zippedFile, err := file.Open() + if err != nil { + return fmt.Errorf("unable to read file=%q from zip=%q: %w", file.Name, archivePath, err) + } + + if file.FileInfo().IsDir() { + err = os.MkdirAll(expandedFilePath, file.Mode()) + if err != nil { + return fmt.Errorf("unable to create dir=%q from zip=%q: %w", expandedFilePath, archivePath, err) + } + } else { + // Open an output file for writing + outputFile, err := os.OpenFile( + expandedFilePath, + os.O_WRONLY|os.O_CREATE|os.O_TRUNC, + file.Mode(), + ) + if err != nil { + return fmt.Errorf("unable to create dest file=%q from zip=%q: %w", expandedFilePath, archivePath, err) + } + + if err := safeCopy(outputFile, zippedFile); err != nil { + return fmt.Errorf("unable to copy source=%q to dest=%q for zip=%q: %w", file.Name, outputFile.Name(), archivePath, err) + } + + err = outputFile.Close() + if err != nil { + return fmt.Errorf("unable to close dest file=%q from zip=%q: %w", outputFile.Name(), archivePath, err) + } + } + + err = zippedFile.Close() + if err != nil { + return fmt.Errorf("unable to close source file=%q from zip=%q: %w", file.Name, archivePath, err) + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_traversal_test.go b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_traversal_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d2bff824438a43fe3b7e029eecbc2b1b2bddd0bb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_file_traversal_test.go @@ -0,0 +1,333 @@ +//go:build !windows +// +build !windows + +package file + +import ( + "crypto/sha256" + "encoding/json" + "errors" + "fmt" + "io" + "io/ioutil" + "os" + "path" + "path/filepath" + "strings" + "testing" + + "github.com/go-test/deep" + "github.com/stretchr/testify/assert" +) + +func equal(r1, r2 io.Reader) (bool, error) { + w1 := sha256.New() + w2 := sha256.New() + n1, err1 := io.Copy(w1, r1) + if err1 != nil { + return false, err1 + } + n2, err2 := io.Copy(w2, r2) + if err2 != nil { + return false, err2 + } + + var b1, b2 [sha256.Size]byte + copy(b1[:], w1.Sum(nil)) + copy(b2[:], w2.Sum(nil)) + + return n1 != n2 || b1 == b2, nil +} + +func TestUnzipToDir(t *testing.T) { + cwd, err := os.Getwd() + if err != nil { + t.Fatal(err) + } + + goldenRootDir := filepath.Join(cwd, "test-fixtures") + sourceDirPath := path.Join(goldenRootDir, "zip-source") + archiveFilePath := setupZipFileTest(t, sourceDirPath, false) + + unzipDestinationDir, err := ioutil.TempDir("", "syft-ziputil-contents-TEST-") + t.Cleanup(assertNoError(t, func() error { + return os.RemoveAll(unzipDestinationDir) + })) + if err != nil { + t.Fatalf("unable to create tempdir: %+v", err) + } + + t.Logf("content path: %s", unzipDestinationDir) + + expectedPaths := len(expectedZipArchiveEntries) + observedPaths := 0 + + err = UnzipToDir(archiveFilePath, unzipDestinationDir) + if err != nil { + t.Fatalf("unable to unzip archive: %+v", err) + } + + // compare the source dir tree and the unzipped tree + err = filepath.Walk(unzipDestinationDir, + func(path string, info os.FileInfo, err error) error { + // We don't unzip the root archive dir, since there's no archive entry for it + if path != unzipDestinationDir { + t.Logf("unzipped path: %s", path) + observedPaths++ + } + + if err != nil { + t.Fatalf("this should not happen") + return err + } + + goldenPath := filepath.Join(sourceDirPath, strings.TrimPrefix(path, unzipDestinationDir)) + + if info.IsDir() { + i, err := os.Stat(goldenPath) + if err != nil { + t.Fatalf("unable to stat golden path: %+v", err) + } + if !i.IsDir() { + t.Fatalf("mismatched file types: %s", goldenPath) + } + return nil + } + + // this is a file, not a dir... + + testFile, err := os.Open(path) + if err != nil { + t.Fatalf("unable to open test file=%s :%+v", path, err) + } + + goldenFile, err := os.Open(goldenPath) + if err != nil { + t.Fatalf("unable to open golden file=%s :%+v", goldenPath, err) + } + + same, err := equal(testFile, goldenFile) + if err != nil { + t.Fatalf("could not compare files (%s, %s): %+v", goldenPath, path, err) + } + + if !same { + t.Errorf("paths are not the same (%s, %s)", goldenPath, path) + } + + return nil + }) + + if err != nil { + t.Errorf("failed to walk dir: %+v", err) + } + + if observedPaths != expectedPaths { + t.Errorf("missed test paths: %d != %d", observedPaths, expectedPaths) + } +} + +func TestContentsFromZip(t *testing.T) { + tests := []struct { + name string + archivePrep func(tb testing.TB) string + }{ + { + name: "standard, non-nested zip", + archivePrep: prepZipSourceFixture, + }, + { + name: "zip with prepended bytes", + archivePrep: prependZipSourceFixtureWithString(t, "junk at the beginning of the file..."), + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + archivePath := test.archivePrep(t) + expected := zipSourceFixtureExpectedContents() + + var paths []string + for p := range expected { + paths = append(paths, p) + } + + actual, err := ContentsFromZip(archivePath, paths...) + if err != nil { + t.Fatalf("unable to extract from unzip archive: %+v", err) + } + + assertZipSourceFixtureContents(t, actual, expected) + }) + } +} + +func prependZipSourceFixtureWithString(tb testing.TB, value string) func(tb testing.TB) string { + if len(value) == 0 { + tb.Fatalf("no bytes given to prefix") + } + return func(t testing.TB) string { + archivePath := prepZipSourceFixture(t) + + // create a temp file + tmpFile, err := ioutil.TempFile("", "syft-ziputil-prependZipSourceFixtureWithString-") + if err != nil { + t.Fatalf("unable to create tempfile: %+v", err) + } + defer tmpFile.Close() + + // write value to the temp file + if _, err := tmpFile.WriteString(value); err != nil { + t.Fatalf("unable to write to tempfile: %+v", err) + } + + // open the original archive + sourceFile, err := os.Open(archivePath) + if err != nil { + t.Fatalf("unable to read source file: %+v", err) + } + + // copy all contents from the archive to the temp file + if _, err := io.Copy(tmpFile, sourceFile); err != nil { + t.Fatalf("unable to copy source to dest: %+v", err) + } + + sourceFile.Close() + + // remove the original archive and replace it with the temp file + if err := os.Remove(archivePath); err != nil { + t.Fatalf("unable to remove original source archive (%q): %+v", archivePath, err) + } + + if err := os.Rename(tmpFile.Name(), archivePath); err != nil { + t.Fatalf("unable to move new archive to old path (%q): %+v", tmpFile.Name(), err) + } + + return archivePath + } +} + +func prepZipSourceFixture(t testing.TB) string { + t.Helper() + archivePrefix, err := ioutil.TempFile("", "syft-ziputil-prepZipSourceFixture-") + if err != nil { + t.Fatalf("unable to create tempfile: %+v", err) + } + + t.Cleanup(func() { + assert.NoError(t, os.Remove(archivePrefix.Name())) + }) + + // the zip utility will add ".zip" to the end of the given name + archivePath := archivePrefix.Name() + ".zip" + + t.Cleanup(func() { + assert.NoError(t, os.Remove(archivePath)) + }) + + t.Logf("archive path: %s", archivePath) + + createZipArchive(t, "zip-source", archivePrefix.Name(), false) + + return archivePath +} + +func zipSourceFixtureExpectedContents() map[string]string { + return map[string]string{ + filepath.Join("some-dir", "a-file.txt"): "A file! nice!", + filepath.Join("b-file.txt"): "B file...", + } +} + +func assertZipSourceFixtureContents(t testing.TB, actual map[string]string, expected map[string]string) { + t.Helper() + diffs := deep.Equal(actual, expected) + if len(diffs) > 0 { + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + + b, err := json.MarshalIndent(actual, "", " ") + if err != nil { + t.Fatalf("can't show results: %+v", err) + } + + t.Errorf("full result: %s", string(b)) + } +} + +// looks like there isn't a helper for this yet? https://github.com/stretchr/testify/issues/497 +func assertErrorAs(expectedErr interface{}) assert.ErrorAssertionFunc { + return func(t assert.TestingT, actualErr error, i ...interface{}) bool { + return errors.As(actualErr, &expectedErr) + } +} + +func TestSafeJoin(t *testing.T) { + tests := []struct { + prefix string + args []string + expected string + errAssertion assert.ErrorAssertionFunc + }{ + // go cases... + { + prefix: "/a/place", + args: []string{ + "somewhere/else", + }, + expected: "/a/place/somewhere/else", + errAssertion: assert.NoError, + }, + { + prefix: "/a/place", + args: []string{ + "somewhere/../else", + }, + expected: "/a/place/else", + errAssertion: assert.NoError, + }, + { + prefix: "/a/../place", + args: []string{ + "somewhere/else", + }, + expected: "/place/somewhere/else", + errAssertion: assert.NoError, + }, + // zip slip examples.... + { + prefix: "/a/place", + args: []string{ + "../../../etc/passwd", + }, + expected: "", + errAssertion: assertErrorAs(&errZipSlipDetected{}), + }, + { + prefix: "/a/place", + args: []string{ + "../", + "../", + }, + expected: "", + errAssertion: assertErrorAs(&errZipSlipDetected{}), + }, + { + prefix: "/a/place", + args: []string{ + "../", + }, + expected: "", + errAssertion: assertErrorAs(&errZipSlipDetected{}), + }, + } + + for _, test := range tests { + t.Run(fmt.Sprintf("%+v:%+v", test.prefix, test.args), func(t *testing.T) { + actual, err := safeJoin(test.prefix, test.args...) + test.errAssertion(t, err) + assert.Equal(t, test.expected, actual) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/zip_read_closer.go b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_read_closer.go new file mode 100644 index 0000000000000000000000000000000000000000..cba80b8517da3c39a2e04cf2d592cb4fb08f62f1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_read_closer.go @@ -0,0 +1,223 @@ +package file + +import ( + "archive/zip" + "encoding/binary" + "errors" + "fmt" + "io" + "os" +) + +// directoryEndLen, readByf, directoryEnd, and findSignatureInBlock were copied from the golang stdlib, specifically: +// - https://github.com/golang/go/blob/go1.16.4/src/archive/zip/struct.go +// - https://github.com/golang/go/blob/go1.16.4/src/archive/zip/reader.go +// findArchiveStartOffset is derived from the same stdlib utils, specifically the readDirectoryEnd function. + +const ( + directoryEndLen = 22 + directory64LocLen = 20 + directory64EndLen = 56 + directory64LocSignature = 0x07064b50 + directory64EndSignature = 0x06064b50 +) + +// ZipReadCloser is a drop-in replacement for zip.ReadCloser (from zip.OpenReader) that additionally considers zips +// that have bytes prefixed to the front of the archive (common with self-extracting jars). +type ZipReadCloser struct { + *zip.Reader + io.Closer +} + +// OpenZip provides a ZipReadCloser for the given filepath. +func OpenZip(filepath string) (*ZipReadCloser, error) { + f, err := os.Open(filepath) + if err != nil { + return nil, err + } + fi, err := f.Stat() + if err != nil { + f.Close() + return nil, err + } + + // some archives may have bytes prepended to the front of the archive, such as with self executing JARs. We first + // need to find the start of the archive and keep track of this offset. + offset, err := findArchiveStartOffset(f, fi.Size()) + if err != nil { + return nil, fmt.Errorf("cannot find beginning of zip archive=%q : %w", filepath, err) + } + + if _, err := f.Seek(0, io.SeekStart); err != nil { + return nil, fmt.Errorf("unable to seek to beginning of archive: %w", err) + } + + size := fi.Size() - int64(offset) + + r, err := zip.NewReader(io.NewSectionReader(f, int64(offset), size), size) + if err != nil { + return nil, fmt.Errorf("unable to open ZipReadCloser @ %q: %w", filepath, err) + } + + return &ZipReadCloser{ + Reader: r, + Closer: f, + }, nil +} + +type readBuf []byte + +func (b *readBuf) uint16() uint16 { + v := binary.LittleEndian.Uint16(*b) + *b = (*b)[2:] + return v +} + +func (b *readBuf) uint32() uint32 { + v := binary.LittleEndian.Uint32(*b) + *b = (*b)[4:] + return v +} + +func (b *readBuf) uint64() uint64 { + v := binary.LittleEndian.Uint64(*b) + *b = (*b)[8:] + return v +} + +type directoryEnd struct { + diskNbr uint32 // unused + dirDiskNbr uint32 // unused + dirRecordsThisDisk uint64 // unused + directoryRecords uint64 + directorySize uint64 + directoryOffset uint64 // relative to file +} + +// note: this is derived from readDirectoryEnd within the archive/zip package +// +//nolint:gocognit +func findArchiveStartOffset(r io.ReaderAt, size int64) (startOfArchive uint64, err error) { + // look for directoryEndSignature in the last 1k, then in the last 65k + var buf []byte + var directoryEndOffset int64 + for i, bLen := range []int64{1024, 65 * 1024} { + if bLen > size { + bLen = size + } + buf = make([]byte, int(bLen)) + if _, err := r.ReadAt(buf, size-bLen); err != nil && err != io.EOF { + return 0, err + } + if p := findSignatureInBlock(buf); p >= 0 { + buf = buf[p:] + directoryEndOffset = size - bLen + int64(p) + break + } + if i == 1 || bLen == size { + return 0, zip.ErrFormat + } + } + + if buf == nil { + // we were unable to find the directoryEndSignature block + return 0, zip.ErrFormat + } + + // read header into struct + b := readBuf(buf[4:]) // skip signature + d := &directoryEnd{ + diskNbr: uint32(b.uint16()), + dirDiskNbr: uint32(b.uint16()), + dirRecordsThisDisk: uint64(b.uint16()), + directoryRecords: uint64(b.uint16()), + directorySize: uint64(b.uint32()), + directoryOffset: uint64(b.uint32()), + } + // Calculate where the zip data actually begins + + // These values mean that the file can be a zip64 file + if d.directoryRecords == 0xffff || d.directorySize == 0xffff || d.directoryOffset == 0xffffffff { + p, err := findDirectory64End(r, directoryEndOffset) + if err == nil && p >= 0 { + directoryEndOffset = p + err = readDirectory64End(r, p, d) + } + if err != nil { + return 0, err + } + startOfArchive = 0 // Prefixed data not supported + } + + startOfArchive = uint64(directoryEndOffset) - d.directorySize - d.directoryOffset + + // Make sure directoryOffset points to somewhere in our file. + if o := int64(d.directoryOffset); o < 0 || o >= size { + return 0, zip.ErrFormat + } + return startOfArchive, nil +} + +// findDirectory64End tries to read the zip64 locator just before the +// directory end and returns the offset of the zip64 directory end if +// found. +func findDirectory64End(r io.ReaderAt, directoryEndOffset int64) (int64, error) { + locOffset := directoryEndOffset - directory64LocLen + if locOffset < 0 { + return -1, nil // no need to look for a header outside the file + } + buf := make([]byte, directory64LocLen) + if _, err := r.ReadAt(buf, locOffset); err != nil { + return -1, err + } + b := readBuf(buf) + if sig := b.uint32(); sig != directory64LocSignature { + return -1, nil + } + if b.uint32() != 0 { // number of the disk with the start of the zip64 end of central directory + return -1, nil // the file is not a valid zip64-file + } + p := b.uint64() // relative offset of the zip64 end of central directory record + if b.uint32() != 1 { // total number of disks + return -1, nil // the file is not a valid zip64-file + } + return int64(p), nil +} + +// readDirectory64End reads the zip64 directory end and updates the +// directory end with the zip64 directory end values. +func readDirectory64End(r io.ReaderAt, offset int64, d *directoryEnd) (err error) { + buf := make([]byte, directory64EndLen) + if _, err := r.ReadAt(buf, offset); err != nil { + return err + } + + b := readBuf(buf) + if sig := b.uint32(); sig != directory64EndSignature { + return errors.New("could not read directory64End") + } + + b = b[12:] // skip dir size, version and version needed (uint64 + 2x uint16) + d.diskNbr = b.uint32() // number of this disk + d.dirDiskNbr = b.uint32() // number of the disk with the start of the central directory + d.dirRecordsThisDisk = b.uint64() // total number of entries in the central directory on this disk + d.directoryRecords = b.uint64() // total number of entries in the central directory + d.directorySize = b.uint64() // size of the central directory + d.directoryOffset = b.uint64() // offset of start of central directory with respect to the starting disk number + + return nil +} + +func findSignatureInBlock(b []byte) int { + for i := len(b) - directoryEndLen; i >= 0; i-- { + // defined from directoryEndSignature + if b[i] == 'P' && b[i+1] == 'K' && b[i+2] == 0x05 && b[i+3] == 0x06 { + // n is length of comment + n := int(b[i+directoryEndLen-2]) | int(b[i+directoryEndLen-1])<<8 + if n+directoryEndLen+i <= len(b) { + return i + } + } + } + return -1 +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/file/zip_read_closer_test.go b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_read_closer_test.go new file mode 100644 index 0000000000000000000000000000000000000000..349bfcc9bf0dd63d3e2e97ba6886555c4117feb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/file/zip_read_closer_test.go @@ -0,0 +1,50 @@ +//go:build !windows +// +build !windows + +package file + +import ( + "os" + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestFindArchiveStartOffset(t *testing.T) { + tests := []struct { + name string + archivePrep func(tb testing.TB) string + expected uint64 + }{ + { + name: "standard, non-nested zip", + archivePrep: prepZipSourceFixture, + expected: 0, + }, + { + name: "zip with prepended bytes", + archivePrep: prependZipSourceFixtureWithString(t, "junk at the beginning of the file..."), + expected: 36, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + archivePath := test.archivePrep(t) + f, err := os.Open(archivePath) + if err != nil { + t.Fatalf("could not open archive %q: %+v", archivePath, err) + } + fi, err := os.Stat(f.Name()) + if err != nil { + t.Fatalf("unable to stat archive: %+v", err) + } + + actual, err := findArchiveStartOffset(f, fi.Size()) + if err != nil { + t.Fatalf("unable to find offset: %+v", err) + } + assert.Equal(t, test.expected, actual) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/author.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/author.go new file mode 100644 index 0000000000000000000000000000000000000000..31ebdde8e2718b13e59e86e1ce0434b26ba842ce --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/author.go @@ -0,0 +1,47 @@ +package cyclonedxhelpers + +import ( + "fmt" + "strings" + + "github.com/anchore/syft/syft/pkg" +) + +func encodeAuthor(p pkg.Package) string { + if hasMetadata(p) { + switch metadata := p.Metadata.(type) { + case pkg.NpmPackageJSONMetadata: + return metadata.Author + case pkg.PythonPackageMetadata: + author := metadata.Author + if metadata.AuthorEmail != "" { + if author == "" { + return metadata.AuthorEmail + } + author += fmt.Sprintf(" <%s>", metadata.AuthorEmail) + } + return author + case pkg.GemMetadata: + if len(metadata.Authors) > 0 { + return strings.Join(metadata.Authors, ",") + } + return "" + } + } + return "" +} + +func decodeAuthor(author string, metadata interface{}) { + switch meta := metadata.(type) { + case *pkg.NpmPackageJSONMetadata: + meta.Author = author + case *pkg.PythonPackageMetadata: + parts := strings.SplitN(author, " <", 2) + meta.Author = parts[0] + if len(parts) > 1 { + meta.AuthorEmail = strings.TrimSuffix(parts[1], ">") + } + case *pkg.GemMetadata: + meta.Authors = strings.Split(author, ",") + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/author_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/author_test.go new file mode 100644 index 0000000000000000000000000000000000000000..11cd95d667acbd47030ec721be778ab6f238b00a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/author_test.go @@ -0,0 +1,87 @@ +package cyclonedxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_encodeAuthor(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "no metadata", + input: pkg.Package{}, + expected: "", + }, + { + name: "from gem", + input: pkg.Package{ + Metadata: pkg.GemMetadata{ + Authors: []string{ + "auth1", + "auth2", + }, + }, + }, + expected: "auth1,auth2", + }, + { + name: "from npm", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Author: "auth", + }, + }, + expected: "auth", + }, + { + name: "from python - just name", + input: pkg.Package{ + Metadata: pkg.PythonPackageMetadata{ + Author: "auth", + }, + }, + expected: "auth", + }, + { + name: "from python - just email", + input: pkg.Package{ + Metadata: pkg.PythonPackageMetadata{ + AuthorEmail: "auth@auth.gov", + }, + }, + expected: "auth@auth.gov", + }, + { + name: "from python - both name and email", + input: pkg.Package{ + Metadata: pkg.PythonPackageMetadata{ + Author: "auth", + AuthorEmail: "auth@auth.gov", + }, + }, + expected: "auth ", + }, + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "empty", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Author: "", + }, + }, + expected: "", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, encodeAuthor(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/component.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/component.go new file mode 100644 index 0000000000000000000000000000000000000000..955b3b227c5a283f56e04b417a1cae97a580478d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/component.go @@ -0,0 +1,128 @@ +package cyclonedxhelpers + +import ( + "reflect" + + "github.com/CycloneDX/cyclonedx-go" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/internal/formats/common" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +func encodeComponent(p pkg.Package) cyclonedx.Component { + props := encodeProperties(p, "syft:package") + props = append(props, encodeCPEs(p)...) + locations := p.Locations.ToSlice() + if len(locations) > 0 { + props = append(props, encodeProperties(locations, "syft:location")...) + } + if hasMetadata(p) { + props = append(props, encodeProperties(p.Metadata, "syft:metadata")...) + } + + var properties *[]cyclonedx.Property + if len(props) > 0 { + properties = &props + } + + return cyclonedx.Component{ + Type: cyclonedx.ComponentTypeLibrary, + Name: p.Name, + Group: encodeGroup(p), + Version: p.Version, + PackageURL: p.PURL, + Licenses: encodeLicenses(p), + CPE: encodeSingleCPE(p), + Author: encodeAuthor(p), + Publisher: encodePublisher(p), + Description: encodeDescription(p), + ExternalReferences: encodeExternalReferences(p), + Properties: properties, + BOMRef: deriveBomRef(p), + } +} + +func deriveBomRef(p pkg.Package) string { + // try and parse the PURL if possible and append syft id to it, to make + // the purl unique in the BOM. + // TODO: In the future we may want to dedupe by PURL and combine components with + // the same PURL while preserving their unique metadata. + if parsedPURL, err := packageurl.FromString(p.PURL); err == nil { + parsedPURL.Qualifiers = append(parsedPURL.Qualifiers, packageurl.Qualifier{Key: "package-id", Value: string(p.ID())}) + return parsedPURL.ToString() + } + // fallback is to use strictly the ID if there is no valid pURL + return string(p.ID()) +} + +func hasMetadata(p pkg.Package) bool { + return p.Metadata != nil +} + +func decodeComponent(c *cyclonedx.Component) *pkg.Package { + values := map[string]string{} + if c.Properties != nil { + for _, p := range *c.Properties { + values[p.Name] = p.Value + } + } + + p := &pkg.Package{ + Name: c.Name, + Version: c.Version, + Locations: decodeLocations(values), + Licenses: decodeLicenses(c), + CPEs: decodeCPEs(c), + PURL: c.PackageURL, + } + + common.DecodeInto(p, values, "syft:package", CycloneDXFields) + + p.MetadataType = pkg.CleanMetadataType(p.MetadataType) + + p.Metadata = decodePackageMetadata(values, c, p.MetadataType) + + if p.Type == "" { + p.Type = pkg.TypeFromPURL(p.PURL) + } + + if p.Language == "" { + p.Language = pkg.LanguageFromPURL(p.PURL) + } + + return p +} + +func decodeLocations(vals map[string]string) source.LocationSet { + v := common.Decode(reflect.TypeOf([]source.Location{}), vals, "syft:location", CycloneDXFields) + out, ok := v.([]source.Location) + if !ok { + out = nil + } + return source.NewLocationSet(out...) +} + +func decodePackageMetadata(vals map[string]string, c *cyclonedx.Component, typ pkg.MetadataType) interface{} { + if typ != "" && c.Properties != nil { + metaTyp, ok := pkg.MetadataTypeByName[typ] + if !ok { + return nil + } + metaPtrTyp := reflect.PtrTo(metaTyp) + metaPtr := common.Decode(metaPtrTyp, vals, "syft:metadata", CycloneDXFields) + + // Map all explicit metadata properties + decodeAuthor(c.Author, metaPtr) + decodeGroup(c.Group, metaPtr) + decodePublisher(c.Publisher, metaPtr) + decodeDescription(c.Description, metaPtr) + decodeExternalReferences(c, metaPtr) + + // return the actual interface{} -> struct ... not interface{} -> *struct + return common.PtrToStruct(metaPtr) + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/component_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/component_test.go new file mode 100644 index 0000000000000000000000000000000000000000..00c685b4d70c5574a2c2d5899baeb733eb2e589c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/component_test.go @@ -0,0 +1,243 @@ +package cyclonedxhelpers + +import ( + "fmt" + "testing" + + "github.com/CycloneDX/cyclonedx-go" + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +func Test_encodeComponentProperties(t *testing.T) { + epoch := 2 + tests := []struct { + name string + input pkg.Package + expected *[]cyclonedx.Property + }{ + { + name: "no metadata", + input: pkg.Package{}, + expected: nil, + }, + { + name: "from apk", + input: pkg.Package{ + FoundBy: "cataloger", + Locations: source.NewLocationSet( + source.Location{Coordinates: source.Coordinates{RealPath: "test"}}, + ), + Metadata: pkg.ApkMetadata{ + Package: "libc-utils", + OriginPackage: "libc-dev", + Maintainer: "Natanael Copa ", + Version: "0.7.2-r0", + License: "BSD", + Architecture: "x86_64", + URL: "http://alpinelinux.org", + Description: "Meta package to pull in correct libc", + Size: 0, + InstalledSize: 4096, + PullDependencies: "musl-utils", + PullChecksum: "Q1p78yvTLG094tHE1+dToJGbmYzQE=", + GitCommitOfAport: "97b1c2842faa3bfa30f5811ffbf16d5ff9f1a479", + Files: []pkg.ApkFileRecord{}, + }, + }, + expected: &[]cyclonedx.Property{ + {Name: "syft:package:foundBy", Value: "cataloger"}, + {Name: "syft:location:0:path", Value: "test"}, + {Name: "syft:metadata:gitCommitOfApkPort", Value: "97b1c2842faa3bfa30f5811ffbf16d5ff9f1a479"}, + {Name: "syft:metadata:installedSize", Value: "4096"}, + {Name: "syft:metadata:originPackage", Value: "libc-dev"}, + {Name: "syft:metadata:pullChecksum", Value: "Q1p78yvTLG094tHE1+dToJGbmYzQE="}, + {Name: "syft:metadata:pullDependencies", Value: "musl-utils"}, + {Name: "syft:metadata:size", Value: "0"}, + }, + }, + { + name: "from dpkg", + input: pkg.Package{ + MetadataType: pkg.DpkgMetadataType, + Metadata: pkg.DpkgMetadata{ + Package: "tzdata", + Version: "2020a-0+deb10u1", + Source: "tzdata-dev", + SourceVersion: "1.0", + Architecture: "all", + InstalledSize: 3036, + Maintainer: "GNU Libc Maintainers ", + Files: []pkg.DpkgFileRecord{}, + }, + }, + expected: &[]cyclonedx.Property{ + {Name: "syft:package:metadataType", Value: "DpkgMetadata"}, + {Name: "syft:metadata:installedSize", Value: "3036"}, + {Name: "syft:metadata:source", Value: "tzdata-dev"}, + {Name: "syft:metadata:sourceVersion", Value: "1.0"}, + }, + }, + { + name: "from go bin", + input: pkg.Package{ + Name: "golang.org/x/net", + Version: "v0.0.0-20211006190231-62292e806868", + Language: pkg.Go, + Type: pkg.GoModulePkg, + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{ + GoCompiledVersion: "1.17", + Architecture: "amd64", + H1Digest: "h1:KlOXYy8wQWTUJYFgkUI40Lzr06ofg5IRXUK5C7qZt1k=", + }, + }, + expected: &[]cyclonedx.Property{ + {Name: "syft:package:language", Value: pkg.Go.String()}, + {Name: "syft:package:metadataType", Value: "GolangBinMetadata"}, + {Name: "syft:package:type", Value: "go-module"}, + {Name: "syft:metadata:architecture", Value: "amd64"}, + {Name: "syft:metadata:goCompiledVersion", Value: "1.17"}, + {Name: "syft:metadata:h1Digest", Value: "h1:KlOXYy8wQWTUJYFgkUI40Lzr06ofg5IRXUK5C7qZt1k="}, + }, + }, + { + name: "from rpm", + input: pkg.Package{ + Name: "dive", + Version: "0.9.2-1", + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: pkg.RpmMetadata{ + Name: "dive", + Epoch: &epoch, + Arch: "x86_64", + Release: "1", + Version: "0.9.2", + SourceRpm: "dive-0.9.2-1.src.rpm", + Size: 12406784, + License: "MIT", + Vendor: "", + Files: []pkg.RpmdbFileRecord{}, + }, + }, + expected: &[]cyclonedx.Property{ + {Name: "syft:package:metadataType", Value: "RpmMetadata"}, + {Name: "syft:package:type", Value: "rpm"}, + {Name: "syft:metadata:epoch", Value: "2"}, + {Name: "syft:metadata:release", Value: "1"}, + {Name: "syft:metadata:size", Value: "12406784"}, + {Name: "syft:metadata:sourceRpm", Value: "dive-0.9.2-1.src.rpm"}, + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + c := encodeComponent(test.input) + assert.Equal(t, test.expected, c.Properties) + }) + } +} + +func Test_deriveBomRef(t *testing.T) { + pkgWithPurl := pkg.Package{ + Name: "django", + Version: "1.11.1", + PURL: "pkg:pypi/django@1.11.1", + } + pkgWithPurl.SetID() + + pkgWithOutPurl := pkg.Package{ + Name: "django", + Version: "1.11.1", + PURL: "", + } + pkgWithOutPurl.SetID() + + pkgWithBadPurl := pkg.Package{ + Name: "django", + Version: "1.11.1", + PURL: "pkg:pyjango@1.11.1", + } + pkgWithBadPurl.SetID() + + tests := []struct { + name string + pkg pkg.Package + want string + }{ + { + name: "use pURL-id hybrid", + pkg: pkgWithPurl, + want: fmt.Sprintf("pkg:pypi/django@1.11.1?package-id=%s", pkgWithPurl.ID()), + }, + { + name: "fallback to ID when pURL is invalid", + pkg: pkgWithBadPurl, + want: string(pkgWithBadPurl.ID()), + }, + { + name: "fallback to ID when pURL is missing", + pkg: pkgWithOutPurl, + want: string(pkgWithOutPurl.ID()), + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + tt.pkg.ID() + assert.Equal(t, tt.want, deriveBomRef(tt.pkg)) + }) + } +} + +func Test_decodeComponent(t *testing.T) { + tests := []struct { + name string + component cyclonedx.Component + wantLanguage pkg.Language + wantMetadataType pkg.MetadataType + }{ + { + name: "derive language from pURL if missing", + component: cyclonedx.Component{ + Name: "ch.qos.logback/logback-classic", + Version: "1.2.3", + PackageURL: "pkg:maven/ch.qos.logback/logback-classic@1.2.3", + Type: "library", + BOMRef: "pkg:maven/ch.qos.logback/logback-classic@1.2.3", + }, + wantLanguage: pkg.Java, + }, + { + name: "handle existing RpmdbMetadata type", + component: cyclonedx.Component{ + Name: "acl", + Version: "2.2.53-1.el8", + PackageURL: "pkg:rpm/centos/acl@2.2.53-1.el8?arch=x86_64&upstream=acl-2.2.53-1.el8.src.rpm&distro=centos-8", + Type: "library", + BOMRef: "pkg:rpm/centos/acl@2.2.53-1.el8?arch=x86_64&upstream=acl-2.2.53-1.el8.src.rpm&distro=centos-8", + Properties: &[]cyclonedx.Property{ + { + Name: "syft:package:metadataType", + Value: "RpmdbMetadata", + }, + }, + }, + wantMetadataType: pkg.RpmMetadataType, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + p := decodeComponent(&tt.component) + if tt.wantLanguage != "" { + assert.Equal(t, tt.wantLanguage, p.Language) + } + if tt.wantMetadataType != "" { + assert.Equal(t, tt.wantMetadataType, p.MetadataType) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/cpe.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/cpe.go new file mode 100644 index 0000000000000000000000000000000000000000..ecee0dc39183ff0f935878574f9f804406e912c0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/cpe.go @@ -0,0 +1,57 @@ +package cyclonedxhelpers + +import ( + "github.com/CycloneDX/cyclonedx-go" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" +) + +func encodeSingleCPE(p pkg.Package) string { + // Since the CPEs in a package are sorted by specificity + // we can extract the first CPE as the one to output in cyclonedx + if len(p.CPEs) > 0 { + return pkg.CPEString(p.CPEs[0]) + } + return "" +} + +func encodeCPEs(p pkg.Package) (out []cyclonedx.Property) { + for i, c := range p.CPEs { + // first CPE is "most specific" and already encoded as the component CPE + if i == 0 { + continue + } + out = append(out, cyclonedx.Property{ + Name: "syft:cpe23", + Value: pkg.CPEString(c), + }) + } + return +} + +func decodeCPEs(c *cyclonedx.Component) (out []pkg.CPE) { + if c.CPE != "" { + cp, err := pkg.NewCPE(c.CPE) + if err != nil { + log.Warnf("invalid CPE: %s", c.CPE) + } else { + out = append(out, cp) + } + } + + if c.Properties != nil { + for _, p := range *c.Properties { + if p.Name == "syft:cpe23" { + cp, err := pkg.NewCPE(p.Value) + if err != nil { + log.Warnf("invalid CPE: %s", p.Value) + } else { + out = append(out, cp) + } + } + } + } + + return +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/cpe_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/cpe_test.go new file mode 100644 index 0000000000000000000000000000000000000000..1eff79ac6b0579ead84625d8c1ce2eab63d70379 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/cpe_test.go @@ -0,0 +1,58 @@ +package cyclonedxhelpers + +import ( + "testing" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/pkg" +) + +func Test_encodeCPE(t *testing.T) { + testCPE := pkg.MustCPE("cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*") + testCPE2 := pkg.MustCPE("cpe:2.3:a:name:name2:3.2:*:*:*:*:*:*:*") + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "no metadata", + input: pkg.Package{ + CPEs: []pkg.CPE{}, + }, + expected: "", + }, + { + name: "single CPE", + input: pkg.Package{ + CPEs: []pkg.CPE{ + testCPE, + }, + }, + expected: "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + }, + { + name: "multiple CPEs", + input: pkg.Package{ + CPEs: []pkg.CPE{ + testCPE2, + testCPE, + }, + }, + expected: "cpe:2.3:a:name:name2:3.2:*:*:*:*:*:*:*", + }, + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "empty", + input: pkg.Package{}, + expected: "", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, encodeSingleCPE(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/decoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/decoder.go new file mode 100644 index 0000000000000000000000000000000000000000..f255d1b228cbe7a1c08492453e6bb5f0e7fd9914 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/decoder.go @@ -0,0 +1,251 @@ +package cyclonedxhelpers + +import ( + "fmt" + "io" + + "github.com/CycloneDX/cyclonedx-go" + + "github.com/anchore/syft/internal/formats/common" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" +) + +func GetValidator(format cyclonedx.BOMFileFormat) sbom.Validator { + return func(reader io.Reader) error { + bom := &cyclonedx.BOM{} + err := cyclonedx.NewBOMDecoder(reader, format).Decode(bom) + if err != nil { + return err + } + // random JSON does not necessarily cause an error (e.g. SPDX) + if (cyclonedx.BOM{} == *bom || bom.Components == nil) { + return fmt.Errorf("not a valid CycloneDX document") + } + return nil + } +} + +func GetDecoder(format cyclonedx.BOMFileFormat) sbom.Decoder { + return func(reader io.Reader) (*sbom.SBOM, error) { + bom := &cyclonedx.BOM{ + Components: &[]cyclonedx.Component{}, + } + err := cyclonedx.NewBOMDecoder(reader, format).Decode(bom) + if err != nil { + return nil, err + } + s, err := toSyftModel(bom) + if err != nil { + return nil, err + } + return s, nil + } +} + +func toSyftModel(bom *cyclonedx.BOM) (*sbom.SBOM, error) { + if bom == nil { + return nil, fmt.Errorf("no content defined in CycloneDX BOM") + } + + s := &sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: pkg.NewCatalog(), + LinuxDistribution: linuxReleaseFromComponents(*bom.Components), + }, + Source: extractComponents(bom.Metadata), + Descriptor: extractDescriptor(bom.Metadata), + } + + idMap := make(map[string]interface{}) + + if err := collectBomPackages(bom, s, idMap); err != nil { + return nil, err + } + + collectRelationships(bom, s, idMap) + + return s, nil +} + +func collectBomPackages(bom *cyclonedx.BOM, s *sbom.SBOM, idMap map[string]interface{}) error { + if bom.Components == nil { + return fmt.Errorf("no components are defined in the CycloneDX BOM") + } + for i := range *bom.Components { + collectPackages(&(*bom.Components)[i], s, idMap) + } + return nil +} + +func collectPackages(component *cyclonedx.Component, s *sbom.SBOM, idMap map[string]interface{}) { + switch component.Type { + case cyclonedx.ComponentTypeOS: + case cyclonedx.ComponentTypeContainer: + case cyclonedx.ComponentTypeApplication, cyclonedx.ComponentTypeFramework, cyclonedx.ComponentTypeLibrary: + p := decodeComponent(component) + idMap[component.BOMRef] = p + // TODO there must be a better way than needing to call this manually: + p.SetID() + s.Artifacts.PackageCatalog.Add(*p) + } + + if component.Components != nil { + for i := range *component.Components { + collectPackages(&(*component.Components)[i], s, idMap) + } + } +} + +func linuxReleaseFromComponents(components []cyclonedx.Component) *linux.Release { + for i := range components { + component := &components[i] + if component.Type == cyclonedx.ComponentTypeOS { + return linuxReleaseFromOSComponent(component) + } + } + return nil +} + +func linuxReleaseFromOSComponent(component *cyclonedx.Component) *linux.Release { + if component == nil { + return nil + } + + var name string + var version string + if component.SWID != nil { + name = component.SWID.Name + version = component.SWID.Version + } + if name == "" { + name = component.Name + } + if name == "" { + name = getPropertyValue(component, "id") + } + if version == "" { + version = component.Version + } + if version == "" { + version = getPropertyValue(component, "versionID") + } + + rel := &linux.Release{ + CPEName: component.CPE, + PrettyName: name, + Name: name, + ID: name, + IDLike: []string{name}, + Version: version, + VersionID: version, + } + if component.ExternalReferences != nil { + for _, ref := range *component.ExternalReferences { + switch ref.Type { + case cyclonedx.ERTypeIssueTracker: + rel.BugReportURL = ref.URL + case cyclonedx.ERTypeWebsite: + rel.HomeURL = ref.URL + case cyclonedx.ERTypeOther: + switch ref.Comment { + case "support": + rel.SupportURL = ref.URL + case "privacyPolicy": + rel.PrivacyPolicyURL = ref.URL + } + } + } + } + + if component.Properties != nil { + values := map[string]string{} + for _, p := range *component.Properties { + values[p.Name] = p.Value + } + common.DecodeInto(&rel, values, "syft:distro", CycloneDXFields) + } + + return rel +} + +func getPropertyValue(component *cyclonedx.Component, name string) string { + if component.Properties != nil { + for _, p := range *component.Properties { + if p.Name == name { + return p.Value + } + } + } + return "" +} + +func collectRelationships(bom *cyclonedx.BOM, s *sbom.SBOM, idMap map[string]interface{}) { + if bom.Dependencies == nil { + return + } + for _, d := range *bom.Dependencies { + from, fromOk := idMap[d.Ref].(artifact.Identifiable) + if fromOk { + if d.Dependencies == nil { + continue + } + for _, t := range *d.Dependencies { + to, toOk := idMap[t.Ref].(artifact.Identifiable) + if toOk { + s.Relationships = append(s.Relationships, artifact.Relationship{ + From: from, + To: to, + Type: artifact.DependencyOfRelationship, // FIXME this information is lost + }) + } + } + } + } +} + +func extractComponents(meta *cyclonedx.Metadata) source.Metadata { + if meta == nil || meta.Component == nil { + return source.Metadata{} + } + c := meta.Component + + image := source.ImageMetadata{ + UserInput: c.Name, + ID: c.BOMRef, + ManifestDigest: c.Version, + } + + switch c.Type { + case cyclonedx.ComponentTypeContainer: + return source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: image, + } + case cyclonedx.ComponentTypeFile: + return source.Metadata{ + Scheme: source.FileScheme, // or source.DirectoryScheme + Path: c.Name, + ImageMetadata: image, + } + } + return source.Metadata{} +} + +// if there is more than one tool in meta.Tools' list the last item will be used +// as descriptor. If there is a way to know which tool to use here please fix it. +func extractDescriptor(meta *cyclonedx.Metadata) (desc sbom.Descriptor) { + if meta == nil || meta.Tools == nil { + return + } + + for _, t := range *meta.Tools { + desc.Name = t.Name + desc.Version = t.Version + } + + return +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/decoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/decoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..5f029bd3e412b65aa909542ddb8886a14111d6f7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/decoder_test.go @@ -0,0 +1,297 @@ +package cyclonedxhelpers + +import ( + "bytes" + "encoding/json" + "fmt" + "testing" + + "github.com/CycloneDX/cyclonedx-go" + "github.com/stretchr/testify/assert" +) + +func Test_decode(t *testing.T) { + type expected struct { + os string + pkg string + ver string + relation string + purl string + cpe string + } + tests := []struct { + name string + input cyclonedx.BOM + expected []expected + }{ + { + name: "basic mapping from cyclonedx", + input: cyclonedx.BOM{ + Metadata: nil, + Components: &[]cyclonedx.Component{ + { + BOMRef: "p1", + Type: cyclonedx.ComponentTypeLibrary, + Name: "package-1", + Version: "1.0.1", + Description: "", + Hashes: nil, + Licenses: &cyclonedx.Licenses{ + { + License: &cyclonedx.License{ + ID: "MIT", + }, + }, + }, + CPE: "cpe:2.3:*:some:package:1:*:*:*:*:*:*:*", + PackageURL: "pkg:some/package-1@1.0.1?arch=arm64&upstream=upstream1&distro=alpine-1", + ExternalReferences: &[]cyclonedx.ExternalReference{ + { + URL: "", + Comment: "", + Hashes: nil, + Type: "", + }, + }, + Properties: &[]cyclonedx.Property{ + { + Name: "foundBy", + Value: "the-cataloger-1", + }, + { + Name: "language", + Value: "python", + }, + { + Name: "type", + Value: "python", + }, + { + Name: "metadataType", + Value: "PythonPackageMetadata", + }, + { + Name: "path", + Value: "/some/path/pkg1", + }, + }, + Components: nil, + Evidence: nil, + }, + { + BOMRef: "p2", + Type: cyclonedx.ComponentTypeLibrary, + Name: "package-2", + Version: "2.0.2", + Hashes: nil, + Licenses: &cyclonedx.Licenses{ + { + License: &cyclonedx.License{ + ID: "MIT", + }, + }, + }, + CPE: "cpe:2.3:*:another:package:2:*:*:*:*:*:*:*", + PackageURL: "pkg:alpine/alpine-baselayout@3.2.0-r16?arch=x86_64&upstream=alpine-baselayout&distro=alpine-3.14.2", + Properties: &[]cyclonedx.Property{ + + { + Name: "foundBy", + Value: "apkdb-cataloger", + }, + { + Name: "type", + Value: "apk", + }, + { + Name: "metadataType", + Value: "ApkMetadata", + }, + { + Name: "path", + Value: "/lib/apk/db/installed", + }, + { + Name: "layerID", + Value: "sha256:9fb3aa2f8b8023a4bebbf92aa567caf88e38e969ada9f0ac12643b2847391635", + }, + { + Name: "originPackage", + Value: "zlib", + }, + { + Name: "size", + Value: "51213", + }, + { + Name: "installedSize", + Value: "110592", + }, + { + Name: "pullDependencies", + Value: "so:libc.musl-x86_64.so.1", + }, + { + Name: "pullChecksum", + Value: "Q1uss4DfpvL16Nw2YUTwmzGBABz3Y=", + }, + { + Name: "gitCommitOfApkPort", + Value: "d2bfb22c8e8f67ad7d8d02704f35ec4d2a19f9b9", + }, + }, + }, + { + Type: cyclonedx.ComponentTypeOS, + Name: "debian", + Version: "1.2.3", + Hashes: nil, + Licenses: &cyclonedx.Licenses{ + { + License: &cyclonedx.License{ + ID: "MIT", + }, + }, + }, + Properties: &[]cyclonedx.Property{ + { + Name: "prettyName", + Value: "debian", + }, + { + Name: "id", + Value: "debian", + }, + { + Name: "versionID", + Value: "1.2.3", + }, + }, + Components: nil, + Evidence: nil, + }, + }, + Dependencies: &[]cyclonedx.Dependency{ + { + Ref: "p1", + Dependencies: &[]cyclonedx.Dependency{ + { + Ref: "p2", + }, + }, + }, + }, + }, + expected: []expected{ + { + os: "debian", + ver: "1.2.3", + }, + { + pkg: "package-1", + ver: "1.0.1", + cpe: "cpe:2.3:*:some:package:1:*:*:*:*:*:*:*", + purl: "pkg:some/package-1@1.0.1?arch=arm64&upstream=upstream1&distro=alpine-1", + relation: "package-2", + }, + { + pkg: "package-2", + ver: "2.0.2", + purl: "pkg:alpine/alpine-baselayout@3.2.0-r16?arch=x86_64&upstream=alpine-baselayout&distro=alpine-3.14.2", + }, + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + sbom, err := toSyftModel(&test.input) + assert.NoError(t, err) + + test: + for _, e := range test.expected { + if e.os != "" { + assert.Equal(t, e.os, sbom.Artifacts.LinuxDistribution.ID) + assert.Equal(t, e.ver, sbom.Artifacts.LinuxDistribution.VersionID) + } + if e.pkg != "" { + for p := range sbom.Artifacts.PackageCatalog.Enumerate() { + if e.pkg != p.Name { + continue + } + + assert.Equal(t, e.ver, p.Version) + + if e.cpe != "" { + foundCPE := false + for _, c := range p.CPEs { + cstr := c.BindToFmtString() + if e.cpe == cstr { + foundCPE = true + break + } + } + if !foundCPE { + assert.Fail(t, fmt.Sprintf("CPE not found in package: %s", e.cpe)) + } + } + + if e.purl != "" { + assert.Equal(t, e.purl, p.PURL) + } + + if e.relation != "" { + foundRelation := false + for _, r := range sbom.Relationships { + p := sbom.Artifacts.PackageCatalog.Package(r.To.ID()) + if e.relation == p.Name { + foundRelation = true + break + } + } + if !foundRelation { + assert.Fail(t, fmt.Sprintf("relation not found: %s", e.relation)) + } + } + continue test + } + assert.Fail(t, fmt.Sprintf("package should be present: %s", e.pkg)) + } + } + }) + } +} + +func Test_missingDataDecode(t *testing.T) { + bom := &cyclonedx.BOM{ + Metadata: nil, + Components: &[]cyclonedx.Component{}, + } + + _, err := toSyftModel(bom) + assert.NoError(t, err) + + bom.Metadata = &cyclonedx.Metadata{} + + _, err = toSyftModel(bom) + assert.NoError(t, err) + + pkg := decodeComponent(&cyclonedx.Component{ + Licenses: &cyclonedx.Licenses{ + { + License: nil, + }, + }, + }) + + assert.Len(t, pkg.Licenses, 0) +} + +func Test_missingComponentsDecode(t *testing.T) { + bom := &cyclonedx.BOM{} + bomBytes, _ := json.Marshal(&bom) + decode := GetDecoder(cyclonedx.BOMFileFormatJSON) + + _, err := decode(bytes.NewReader(bomBytes)) + + assert.NoError(t, err) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/description.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/description.go new file mode 100644 index 0000000000000000000000000000000000000000..36add799af1d2034a39f7ee3a907d1825d6fa4b4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/description.go @@ -0,0 +1,24 @@ +package cyclonedxhelpers + +import "github.com/anchore/syft/syft/pkg" + +func encodeDescription(p pkg.Package) string { + if hasMetadata(p) { + switch metadata := p.Metadata.(type) { + case pkg.ApkMetadata: + return metadata.Description + case pkg.NpmPackageJSONMetadata: + return metadata.Description + } + } + return "" +} + +func decodeDescription(description string, metadata interface{}) { + switch meta := metadata.(type) { + case *pkg.ApkMetadata: + meta.Description = description + case *pkg.NpmPackageJSONMetadata: + meta.Description = description + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/description_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/description_test.go new file mode 100644 index 0000000000000000000000000000000000000000..21f72270204430352074393aa215a98ab77a1a84 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/description_test.go @@ -0,0 +1,56 @@ +package cyclonedxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_encodeDescription(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "no metadata", + input: pkg.Package{}, + expected: "", + }, + { + name: "from apk", + input: pkg.Package{ + Metadata: pkg.ApkMetadata{ + Description: "a description!", + }, + }, + expected: "a description!", + }, + { + name: "from npm", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Description: "a description!", + }, + }, + expected: "a description!", + }, + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "empty", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Homepage: "", + }, + }, + expected: "", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, encodeDescription(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/external_references.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/external_references.go new file mode 100644 index 0000000000000000000000000000000000000000..c7f952717df702c72a0d218dc98db78a8a3940bb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/external_references.go @@ -0,0 +1,159 @@ +package cyclonedxhelpers + +import ( + "fmt" + "strings" + + syftFile "github.com/anchore/syft/syft/file" + + "github.com/CycloneDX/cyclonedx-go" + "github.com/anchore/syft/syft/pkg" +) + +//nolint:funlen, gocognit +func encodeExternalReferences(p pkg.Package) *[]cyclonedx.ExternalReference { + var refs []cyclonedx.ExternalReference + if hasMetadata(p) { + switch metadata := p.Metadata.(type) { + case pkg.ApkMetadata: + if metadata.URL != "" { + refs = append(refs, cyclonedx.ExternalReference{ + URL: metadata.URL, + Type: cyclonedx.ERTypeDistribution, + }) + } + case pkg.CargoPackageMetadata: + if metadata.Source != "" { + refs = append(refs, cyclonedx.ExternalReference{ + URL: metadata.Source, + Type: cyclonedx.ERTypeDistribution, + }) + } + case pkg.NpmPackageJSONMetadata: + if metadata.URL != "" { + refs = append(refs, cyclonedx.ExternalReference{ + URL: metadata.URL, + Type: cyclonedx.ERTypeDistribution, + }) + } + if metadata.Homepage != "" { + refs = append(refs, cyclonedx.ExternalReference{ + URL: metadata.Homepage, + Type: cyclonedx.ERTypeWebsite, + }) + } + case pkg.GemMetadata: + if metadata.Homepage != "" { + refs = append(refs, cyclonedx.ExternalReference{ + URL: metadata.Homepage, + Type: cyclonedx.ERTypeWebsite, + }) + } + case pkg.JavaMetadata: + if len(metadata.ArchiveDigests) > 0 { + for _, digest := range metadata.ArchiveDigests { + refs = append(refs, cyclonedx.ExternalReference{ + URL: "", + Type: cyclonedx.ERTypeBuildMeta, + Hashes: &[]cyclonedx.Hash{{ + Algorithm: toCycloneDXAlgorithm(digest.Algorithm), + Value: digest.Value, + }}, + }) + } + } + case pkg.PythonPackageMetadata: + if metadata.DirectURLOrigin != nil && metadata.DirectURLOrigin.URL != "" { + ref := cyclonedx.ExternalReference{ + URL: metadata.DirectURLOrigin.URL, + Type: cyclonedx.ERTypeVCS, + } + if metadata.DirectURLOrigin.CommitID != "" { + ref.Comment = fmt.Sprintf("commit: %s", metadata.DirectURLOrigin.CommitID) + } + refs = append(refs, ref) + } + } + } + if len(refs) > 0 { + return &refs + } + return nil +} + +// supported algorithm in cycloneDX as of 1.4 +// "MD5", "SHA-1", "SHA-256", "SHA-384", "SHA-512", +// "SHA3-256", "SHA3-384", "SHA3-512", "BLAKE2b-256", "BLAKE2b-384", "BLAKE2b-512", "BLAKE3" +// syft supported digests: cmd/syft/cli/eventloop/tasks.go +// MD5, SHA1, SHA256 +func toCycloneDXAlgorithm(algorithm string) cyclonedx.HashAlgorithm { + validMap := map[string]cyclonedx.HashAlgorithm{ + "sha1": cyclonedx.HashAlgorithm("SHA-1"), + "md5": cyclonedx.HashAlgorithm("MD5"), + "sha256": cyclonedx.HashAlgorithm("SHA-256"), + } + + return validMap[algorithm] +} + +func decodeExternalReferences(c *cyclonedx.Component, metadata interface{}) { + if c.ExternalReferences == nil { + return + } + switch meta := metadata.(type) { + case *pkg.ApkMetadata: + meta.URL = refURL(c, cyclonedx.ERTypeDistribution) + case *pkg.CargoPackageMetadata: + meta.Source = refURL(c, cyclonedx.ERTypeDistribution) + case *pkg.NpmPackageJSONMetadata: + meta.URL = refURL(c, cyclonedx.ERTypeDistribution) + meta.Homepage = refURL(c, cyclonedx.ERTypeWebsite) + case *pkg.GemMetadata: + meta.Homepage = refURL(c, cyclonedx.ERTypeWebsite) + case *pkg.JavaMetadata: + var digests []syftFile.Digest + if ref := findExternalRef(c, cyclonedx.ERTypeBuildMeta); ref != nil { + if ref.Hashes != nil { + for _, hash := range *ref.Hashes { + digests = append(digests, syftFile.Digest{ + Algorithm: syftFile.CleanDigestAlgorithmName(string(hash.Algorithm)), + Value: hash.Value, + }) + } + } + } + + meta.ArchiveDigests = digests + case *pkg.PythonPackageMetadata: + if meta.DirectURLOrigin == nil { + meta.DirectURLOrigin = &pkg.PythonDirectURLOriginInfo{} + } + meta.DirectURLOrigin.URL = refURL(c, cyclonedx.ERTypeVCS) + meta.DirectURLOrigin.CommitID = strings.TrimPrefix(refComment(c, cyclonedx.ERTypeVCS), "commit: ") + } +} + +func findExternalRef(c *cyclonedx.Component, typ cyclonedx.ExternalReferenceType) *cyclonedx.ExternalReference { + if c.ExternalReferences != nil { + for _, r := range *c.ExternalReferences { + if r.Type == typ { + return &r + } + } + } + return nil +} + +func refURL(c *cyclonedx.Component, typ cyclonedx.ExternalReferenceType) string { + if r := findExternalRef(c, typ); r != nil { + return r.URL + } + return "" +} + +func refComment(c *cyclonedx.Component, typ cyclonedx.ExternalReferenceType) string { + if r := findExternalRef(c, typ); r != nil { + return r.Comment + } + return "" +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/external_references_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/external_references_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e5a91daa6675ac7b7a67c9ec80ddd6de36a4e843 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/external_references_test.go @@ -0,0 +1,133 @@ +package cyclonedxhelpers + +import ( + "testing" + + "github.com/CycloneDX/cyclonedx-go" + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_encodeExternalReferences(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected *[]cyclonedx.ExternalReference + }{ + { + name: "no metadata", + input: pkg.Package{}, + expected: nil, + }, + { + name: "from apk", + input: pkg.Package{ + Metadata: pkg.ApkMetadata{ + URL: "http://a-place.gov", + }, + }, + expected: &[]cyclonedx.ExternalReference{ + {URL: "http://a-place.gov", Type: cyclonedx.ERTypeDistribution}, + }, + }, + { + name: "from npm", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + URL: "http://a-place.gov", + }, + }, + expected: &[]cyclonedx.ExternalReference{ + {URL: "http://a-place.gov", Type: cyclonedx.ERTypeDistribution}, + }, + }, + { + name: "from cargo lock", + input: pkg.Package{ + Name: "ansi_term", + Version: "0.12.1", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "ansi_term", + Version: "0.12.1", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "d52a9bb7ec0cf484c551830a7ce27bd20d67eac647e1befb56b0be4ee39a55d2", + Dependencies: []string{ + "winapi", + }, + }, + }, + expected: &[]cyclonedx.ExternalReference{ + {URL: "registry+https://github.com/rust-lang/crates.io-index", Type: cyclonedx.ERTypeDistribution}, + }, + }, + { + name: "from npm with homepage", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + URL: "http://a-place.gov", + Homepage: "http://homepage", + }, + }, + expected: &[]cyclonedx.ExternalReference{ + {URL: "http://a-place.gov", Type: cyclonedx.ERTypeDistribution}, + {URL: "http://homepage", Type: cyclonedx.ERTypeWebsite}, + }, + }, + { + name: "from gem", + input: pkg.Package{ + Metadata: pkg.GemMetadata{ + Homepage: "http://a-place.gov", + }, + }, + expected: &[]cyclonedx.ExternalReference{ + {URL: "http://a-place.gov", Type: cyclonedx.ERTypeWebsite}, + }, + }, + { + name: "from python direct url", + input: pkg.Package{ + Metadata: pkg.PythonPackageMetadata{ + DirectURLOrigin: &pkg.PythonDirectURLOriginInfo{ + URL: "http://a-place.gov", + }, + }, + }, + expected: &[]cyclonedx.ExternalReference{ + {URL: "http://a-place.gov", Type: cyclonedx.ERTypeVCS}, + }, + }, + { + name: "from python direct url with commit", + input: pkg.Package{ + Metadata: pkg.PythonPackageMetadata{ + DirectURLOrigin: &pkg.PythonDirectURLOriginInfo{ + URL: "http://a-place.gov", + CommitID: "test", + }, + }, + }, + expected: &[]cyclonedx.ExternalReference{ + {URL: "http://a-place.gov", Type: cyclonedx.ERTypeVCS, Comment: "commit: test"}, + }, + }, + { + name: "empty", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + URL: "", + }, + }, + expected: nil, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, encodeExternalReferences(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/format.go new file mode 100644 index 0000000000000000000000000000000000000000..a22b191b2d11375824b648e70d08afbf133f3fde --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/format.go @@ -0,0 +1,180 @@ +package cyclonedxhelpers + +import ( + "time" + + "github.com/CycloneDX/cyclonedx-go" + "github.com/google/uuid" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" +) + +func ToFormatModel(s sbom.SBOM) *cyclonedx.BOM { + cdxBOM := cyclonedx.NewBOM() + + // NOTE(jonasagx): cycloneDX requires URN uuids (URN returns the RFC 2141 URN form of uuid): + // https://github.com/CycloneDX/specification/blob/master/schema/bom-1.3-strict.schema.json#L36 + // "pattern": "^urn:uuid:[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$" + cdxBOM.SerialNumber = uuid.New().URN() + cdxBOM.Metadata = toBomDescriptor(internal.ApplicationName, s.Descriptor.Version, s.Source) + + packages := s.Artifacts.PackageCatalog.Sorted() + components := make([]cyclonedx.Component, len(packages)) + for i, p := range packages { + components[i] = encodeComponent(p) + } + components = append(components, toOSComponent(s.Artifacts.LinuxDistribution)...) + cdxBOM.Components = &components + + dependencies := toDependencies(s.Relationships) + if len(dependencies) > 0 { + cdxBOM.Dependencies = &dependencies + } + + return cdxBOM +} + +func toOSComponent(distro *linux.Release) []cyclonedx.Component { + if distro == nil { + return []cyclonedx.Component{} + } + eRefs := &[]cyclonedx.ExternalReference{} + if distro.BugReportURL != "" { + *eRefs = append(*eRefs, cyclonedx.ExternalReference{ + URL: distro.BugReportURL, + Type: cyclonedx.ERTypeIssueTracker, + }) + } + if distro.HomeURL != "" { + *eRefs = append(*eRefs, cyclonedx.ExternalReference{ + URL: distro.HomeURL, + Type: cyclonedx.ERTypeWebsite, + }) + } + if distro.SupportURL != "" { + *eRefs = append(*eRefs, cyclonedx.ExternalReference{ + URL: distro.SupportURL, + Type: cyclonedx.ERTypeOther, + Comment: "support", + }) + } + if distro.PrivacyPolicyURL != "" { + *eRefs = append(*eRefs, cyclonedx.ExternalReference{ + URL: distro.PrivacyPolicyURL, + Type: cyclonedx.ERTypeOther, + Comment: "privacyPolicy", + }) + } + if len(*eRefs) == 0 { + eRefs = nil + } + props := encodeProperties(distro, "syft:distro") + var properties *[]cyclonedx.Property + if len(props) > 0 { + properties = &props + } + return []cyclonedx.Component{ + { + Type: cyclonedx.ComponentTypeOS, + // FIXME is it idiomatic to be using SWID here for specific name and version information? + SWID: &cyclonedx.SWID{ + TagID: distro.ID, + Name: distro.ID, + Version: distro.VersionID, + }, + Description: distro.PrettyName, + Name: distro.ID, + Version: distro.VersionID, + // TODO should we add a PURL? + CPE: distro.CPEName, + ExternalReferences: eRefs, + Properties: properties, + }, + } +} + +// NewBomDescriptor returns a new BomDescriptor tailored for the current time and "syft" tool details. +func toBomDescriptor(name, version string, srcMetadata source.Metadata) *cyclonedx.Metadata { + return &cyclonedx.Metadata{ + Timestamp: time.Now().Format(time.RFC3339), + Tools: &[]cyclonedx.Tool{ + { + Vendor: "anchore", + Name: name, + Version: version, + }, + }, + Component: toBomDescriptorComponent(srcMetadata), + } +} + +// used to indicate that a relationship listed under the syft artifact package can be represented as a cyclonedx dependency. +// NOTE: CycloneDX provides the ability to describe components and their dependency on other components. +// The dependency graph is capable of representing both direct and transitive relationships. +// If a relationship is either direct or transitive it can be included in this function. +// An example of a relationship to not include would be: OwnershipByFileOverlapRelationship. +func isExpressiblePackageRelationship(ty artifact.RelationshipType) bool { + switch ty { + case artifact.RuntimeDependencyOfRelationship: + return true + case artifact.DevDependencyOfRelationship: + return true + case artifact.BuildDependencyOfRelationship: + return true + case artifact.DependencyOfRelationship: + return true + } + return false +} + +func toDependencies(relationships []artifact.Relationship) []cyclonedx.Dependency { + result := make([]cyclonedx.Dependency, 0) + for _, r := range relationships { + exists := isExpressiblePackageRelationship(r.Type) + if !exists { + log.Debugf("unable to convert relationship from CycloneDX 1.4 JSON, dropping: %+v", r) + continue + } + + innerDeps := []cyclonedx.Dependency{} + innerDeps = append(innerDeps, cyclonedx.Dependency{Ref: string(r.From.ID())}) + result = append(result, cyclonedx.Dependency{ + Ref: string(r.To.ID()), + Dependencies: &innerDeps, + }) + } + return result +} + +func toBomDescriptorComponent(srcMetadata source.Metadata) *cyclonedx.Component { + switch srcMetadata.Scheme { + case source.ImageScheme: + bomRef, err := artifact.IDByHash(srcMetadata.ImageMetadata.ID) + if err != nil { + log.Warnf("unable to get fingerprint of image metadata=%s: %+v", srcMetadata.ImageMetadata.ID, err) + } + return &cyclonedx.Component{ + BOMRef: string(bomRef), + Type: cyclonedx.ComponentTypeContainer, + Name: srcMetadata.ImageMetadata.UserInput, + Version: srcMetadata.ImageMetadata.ManifestDigest, + } + case source.DirectoryScheme, source.FileScheme: + bomRef, err := artifact.IDByHash(srcMetadata.Path) + if err != nil { + log.Warnf("unable to get fingerprint of source metadata path=%s: %+v", srcMetadata.Path, err) + } + return &cyclonedx.Component{ + BOMRef: string(bomRef), + Type: cyclonedx.ComponentTypeFile, + Name: srcMetadata.Path, + } + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/group.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/group.go new file mode 100644 index 0000000000000000000000000000000000000000..6e452aeeef7d1b8efd46e22f3f17a5326954dafc --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/group.go @@ -0,0 +1,21 @@ +package cyclonedxhelpers + +import "github.com/anchore/syft/syft/pkg" + +func encodeGroup(p pkg.Package) string { + if hasMetadata(p) { + if metadata, ok := p.Metadata.(pkg.JavaMetadata); ok && metadata.PomProperties != nil { + return metadata.PomProperties.GroupID + } + } + return "" +} + +func decodeGroup(group string, metadata interface{}) { + if meta, ok := metadata.(*pkg.JavaMetadata); ok { + if meta.PomProperties == nil { + meta.PomProperties = &pkg.PomProperties{} + } + meta.PomProperties.GroupID = group + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/group_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/group_test.go new file mode 100644 index 0000000000000000000000000000000000000000..38352131fadb96c47210b9550e2c62a3337e3c76 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/group_test.go @@ -0,0 +1,52 @@ +package cyclonedxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_encodeGroup(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + name: "no metadata", + input: pkg.Package{}, + expected: "", + }, + { + name: "metadata is not Java", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{}, + }, + expected: "", + }, + { + name: "metadata is Java but pom properties is empty", + input: pkg.Package{ + Metadata: pkg.JavaMetadata{}, + }, + expected: "", + }, + { + name: "metadata is Java and contains pomProperties", + input: pkg.Package{ + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "test", + }, + }, + }, + expected: "test", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, encodeGroup(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/licenses.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/licenses.go new file mode 100644 index 0000000000000000000000000000000000000000..9acf70d39ef18f363a0093b67d859a571287f470 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/licenses.go @@ -0,0 +1,35 @@ +package cyclonedxhelpers + +import ( + "github.com/CycloneDX/cyclonedx-go" + "github.com/anchore/syft/internal/spdxlicense" + "github.com/anchore/syft/syft/pkg" +) + +func encodeLicenses(p pkg.Package) *cyclonedx.Licenses { + lc := cyclonedx.Licenses{} + for _, licenseName := range p.Licenses { + if value, exists := spdxlicense.ID(licenseName); exists { + lc = append(lc, cyclonedx.LicenseChoice{ + License: &cyclonedx.License{ + ID: value, + }, + }) + } + } + if len(lc) > 0 { + return &lc + } + return nil +} + +func decodeLicenses(c *cyclonedx.Component) (out []string) { + if c.Licenses != nil { + for _, l := range *c.Licenses { + if l.License != nil { + out = append(out, l.License.ID) + } + } + } + return +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/licenses_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/licenses_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4b3745adc8f0c44467e2d8cf75652649e28d2dcf --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/licenses_test.go @@ -0,0 +1,83 @@ +package cyclonedxhelpers + +import ( + "testing" + + "github.com/CycloneDX/cyclonedx-go" + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_encodeLicense(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected *cyclonedx.Licenses + }{ + { + name: "no licenses", + input: pkg.Package{}, + expected: nil, + }, + { + name: "no SPDX licenses", + input: pkg.Package{ + Licenses: []string{ + "made-up", + }, + }, + expected: nil, + }, + { + name: "with SPDX license", + input: pkg.Package{ + Licenses: []string{ + "MIT", + }, + }, + expected: &cyclonedx.Licenses{ + {License: &cyclonedx.License{ID: "MIT"}}, + }, + }, + { + name: "with SPDX license expression", + input: pkg.Package{ + Licenses: []string{ + "MIT", + "GPL-3.0", + }, + }, + expected: &cyclonedx.Licenses{ + {License: &cyclonedx.License{ID: "MIT"}}, + {License: &cyclonedx.License{ID: "GPL-3.0-only"}}, + }, + }, + { + name: "cap insensitive", + input: pkg.Package{ + Licenses: []string{ + "gpl-3.0", + }, + }, + expected: &cyclonedx.Licenses{ + {License: &cyclonedx.License{ID: "GPL-3.0-only"}}, + }, + }, + { + name: "debian to spdx conversion", + input: pkg.Package{ + Licenses: []string{ + "GPL-2", + }, + }, + expected: &cyclonedx.Licenses{ + {License: &cyclonedx.License{ID: "GPL-2.0-only"}}, + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, encodeLicenses(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/properties.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/properties.go new file mode 100644 index 0000000000000000000000000000000000000000..a43052b92692f2ab3682c8128a02f0d7a18e8ff4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/properties.go @@ -0,0 +1,21 @@ +package cyclonedxhelpers + +import ( + "github.com/CycloneDX/cyclonedx-go" + + "github.com/anchore/syft/internal/formats/common" +) + +var ( + CycloneDXFields = common.RequiredTag("cyclonedx") +) + +func encodeProperties(obj interface{}, prefix string) (out []cyclonedx.Property) { + for _, p := range common.Sorted(common.Encode(obj, prefix, CycloneDXFields)) { + out = append(out, cyclonedx.Property{ + Name: p.Name, + Value: p.Value, + }) + } + return +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/publisher.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/publisher.go new file mode 100644 index 0000000000000000000000000000000000000000..9b0c469bcf53c9e9b934383d5c40c998dd863ce1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/publisher.go @@ -0,0 +1,30 @@ +package cyclonedxhelpers + +import ( + "github.com/anchore/syft/syft/pkg" +) + +func encodePublisher(p pkg.Package) string { + if hasMetadata(p) { + switch metadata := p.Metadata.(type) { + case pkg.ApkMetadata: + return metadata.Maintainer + case pkg.RpmMetadata: + return metadata.Vendor + case pkg.DpkgMetadata: + return metadata.Maintainer + } + } + return "" +} + +func decodePublisher(publisher string, metadata interface{}) { + switch meta := metadata.(type) { + case *pkg.ApkMetadata: + meta.Maintainer = publisher + case *pkg.RpmMetadata: + meta.Vendor = publisher + case *pkg.DpkgMetadata: + meta.Maintainer = publisher + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/publisher_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/publisher_test.go new file mode 100644 index 0000000000000000000000000000000000000000..0673059864bfca6eacea29ca1b1a706159d26053 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/cyclonedxhelpers/publisher_test.go @@ -0,0 +1,65 @@ +package cyclonedxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_encodePublisher(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "no metadata", + input: pkg.Package{}, + expected: "", + }, + { + name: "from apk", + input: pkg.Package{ + Metadata: pkg.ApkMetadata{ + Maintainer: "auth", + }, + }, + expected: "auth", + }, + { + name: "from rpm", + input: pkg.Package{ + Metadata: pkg.RpmMetadata{ + Vendor: "auth", + }, + }, + expected: "auth", + }, + { + name: "from dpkg", + input: pkg.Package{ + Metadata: pkg.DpkgMetadata{ + Maintainer: "auth", + }, + }, + expected: "auth", + }, + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "empty", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Author: "", + }, + }, + expected: "", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, encodePublisher(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/property_encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/property_encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..271a22afa80102ca08b15d12d4baf9063663acb5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/property_encoder.go @@ -0,0 +1,322 @@ +package common + +import ( + "fmt" + "reflect" + "sort" + "strconv" + "strings" + + "github.com/anchore/syft/internal/log" +) + +// FieldName return a flag to indicate this is a valid field and a name to use +type FieldName func(field reflect.StructField) (string, bool) + +// OptionalTag given a tag name, will return the defined tag or fall back to lower camel case field name +func OptionalTag(tag string) FieldName { + return func(f reflect.StructField) (string, bool) { + if n, ok := f.Tag.Lookup(tag); ok { + return n, true + } + return lowerFirst(f.Name), true + } +} + +// TrimOmitempty trims `,omitempty` from the name +func TrimOmitempty(fn FieldName) FieldName { + return func(f reflect.StructField) (string, bool) { + if v, ok := fn(f); ok { + return strings.TrimSuffix(v, ",omitempty"), true + } + return "", false + } +} + +// RequiredTag based on the given tag, only use a field if present +func RequiredTag(tag string) FieldName { + return func(f reflect.StructField) (string, bool) { + if n, ok := f.Tag.Lookup(tag); ok { + return n, true + } + return "", false + } +} + +var ( + // OptionalJSONTag uses field names defined in json tags, if available + OptionalJSONTag = TrimOmitempty(OptionalTag("json")) +) + +// lowerFirst converts the first character of the string to lower case +func lowerFirst(s string) string { + return strings.ToLower(s[0:1]) + s[1:] +} + +// Encode recursively encodes the object's properties as an ordered set of NameValue pairs +func Encode(obj interface{}, prefix string, fn FieldName) map[string]string { + if obj == nil { + return nil + } + props := map[string]string{} + encode(props, reflect.ValueOf(obj), prefix, fn) + return props +} + +// NameValue a simple type to store stringified name/value pairs +type NameValue struct { + Name string + Value string +} + +// Sorted returns a sorted set of NameValue pairs +func Sorted(values map[string]string) (out []NameValue) { + var keys []string + for k := range values { + keys = append(keys, k) + } + sort.Strings(keys) + for _, k := range keys { + out = append(out, NameValue{ + Name: k, + Value: values[k], + }) + } + return +} + +func encode(out map[string]string, value reflect.Value, prefix string, fn FieldName) { + if !value.IsValid() || value.Type() == nil { + return + } + + typ := value.Type() + + switch typ.Kind() { + case reflect.Ptr: + if value.IsNil() { + return + } + value = value.Elem() + encode(out, value, prefix, fn) + case reflect.String: + v := value.String() + if v != "" { + out[prefix] = v + } + case reflect.Bool: + v := value.Bool() + out[prefix] = strconv.FormatBool(v) + case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64: + v := value.Int() + out[prefix] = strconv.FormatInt(v, 10) + case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64: + v := value.Uint() + out[prefix] = strconv.FormatUint(v, 10) + case reflect.Float32, reflect.Float64: + v := value.Float() + out[prefix] = fmt.Sprintf("%f", v) + case reflect.Array, reflect.Slice: + for idx := 0; idx < value.Len(); idx++ { + encode(out, value.Index(idx), fmt.Sprintf("%s:%d", prefix, idx), fn) + } + case reflect.Struct: + for i := 0; i < typ.NumField(); i++ { + pv := value.Field(i) + f := typ.Field(i) + name, ok := fieldName(f, prefix, fn) + if !ok { + continue + } + encode(out, pv, name, fn) + } + default: + log.Warnf("skipping encoding of unsupported property: %s", prefix) + } +} + +// fieldName gets the name of the field using the provided FieldName function +func fieldName(f reflect.StructField, prefix string, fn FieldName) (string, bool) { + name, ok := fn(f) + if !ok { + return "", false + } + if name == "" { + return prefix, true + } + if prefix != "" { + name = fmt.Sprintf("%s:%s", prefix, name) + } + return name, true +} + +// Decode based on the given type, applies all values to hydrate a new instance +func Decode(typ reflect.Type, values map[string]string, prefix string, fn FieldName) interface{} { + isPtr := false + for typ.Kind() == reflect.Ptr { + typ = typ.Elem() + isPtr = true + } + + isSlice := false + if typ.Kind() == reflect.Slice { + typ = reflect.PtrTo(typ) + isSlice = true + } + + v := reflect.New(typ) + + decode(values, v, prefix, fn) + + switch { + case isSlice && isPtr: + return v.Elem().Interface() + case isSlice: + return PtrToStruct(v.Elem().Interface()) + case isPtr: + return v.Interface() + } + return v.Elem().Interface() +} + +// DecodeInto decodes all values to hydrate the given object instance +func DecodeInto(obj interface{}, values map[string]string, prefix string, fn FieldName) { + value := reflect.ValueOf(obj) + + for value.Type().Kind() == reflect.Ptr { + value = value.Elem() + } + + decode(values, value, prefix, fn) +} + +//nolint:funlen,gocognit,gocyclo +func decode(vals map[string]string, value reflect.Value, prefix string, fn FieldName) bool { + if !value.IsValid() || value.Type() == nil { + return false + } + + typ := value.Type() + + incoming, valid := vals[prefix] + switch typ.Kind() { + case reflect.Ptr: + t := typ.Elem() + v := value + if v.IsNil() { + v = reflect.New(t) + } + if decode(vals, v.Elem(), prefix, fn) && value.CanSet() { + o := v.Interface() + log.Infof("%v", o) + value.Set(v) + } else { + return false + } + case reflect.String: + if valid { + value.SetString(incoming) + } else { + return false + } + case reflect.Bool: + if !valid { + return false + } + if b, err := strconv.ParseBool(incoming); err == nil { + value.SetBool(b) + } else { + return false + } + case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64: + if !valid { + return false + } + if i, err := strconv.ParseInt(incoming, 10, 64); err == nil { + value.SetInt(i) + } else { + return false + } + case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64: + if !valid { + return false + } + if i, err := strconv.ParseUint(incoming, 10, 64); err == nil { + value.SetUint(i) + } else { + return false + } + case reflect.Float32, reflect.Float64: + if !valid { + return false + } + if i, err := strconv.ParseFloat(incoming, 64); err == nil { + value.SetFloat(i) + } else { + return false + } + case reflect.Array, reflect.Slice: + values := false + t := typ.Elem() + slice := reflect.MakeSlice(typ, 0, 0) + for idx := 0; ; idx++ { + // test for index + str := fmt.Sprintf("%s:%d", prefix, idx) + // create new placeholder and decode values + newType := t + if t.Kind() == reflect.Ptr { + newType = t.Elem() + } + v := reflect.New(newType) + if decode(vals, v.Elem(), str, fn) { + // append to slice + if t.Kind() != reflect.Ptr { + v = v.Elem() + } + slice = reflect.Append(slice, v) + values = true + } else { + break + } + } + if values { + value.Set(slice) + } else { + return false + } + case reflect.Struct: + values := false + for i := 0; i < typ.NumField(); i++ { + f := typ.Field(i) + v := value.Field(i) + + name, ok := fieldName(f, prefix, fn) + if !ok { + continue + } + + if decode(vals, v, name, fn) { + values = true + } + } + return values + default: + log.Warnf("unable to set field: %s", prefix) + return false + } + return true +} + +func PtrToStruct(ptr interface{}) interface{} { + v := reflect.ValueOf(ptr) + if v.IsZero() { + return nil + } + switch v.Type().Kind() { + case reflect.Ptr: + return PtrToStruct(v.Elem().Interface()) + case reflect.Interface: + return PtrToStruct(v.Elem().Interface()) + } + return v.Interface() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/property_encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/property_encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..2ff63a1f239c2c9363013af6f5ce936617e98602 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/property_encoder_test.go @@ -0,0 +1,143 @@ +package common + +import ( + "reflect" + "testing" + + "github.com/stretchr/testify/assert" +) + +type T1 struct { + Name string + Val int + ValU uint + Flag bool `json:"bool_flag"` + Float float64 + T2 T2 + T2Ptr *T2 + T2Arr []T2 + T2PtrArr []*T2 + StrArr []string + IntArr []int + FloatArr []float64 + BoolArr []bool + T3Arr []T3 +} + +type T2 struct { + Name string +} + +type T3 struct { + T4Arr []T4 +} + +type T4 struct { + Typ string + IntPtr *int +} + +func Test_EncodeDecodeCycle(t *testing.T) { + val := 99 + + tests := []struct { + name string + value interface{} + }{ + { + name: "all values", + value: T1{ + Name: "name", + Val: 10, + ValU: 16, + Flag: true, + Float: 1.2, + T2: T2{ + Name: "embedded t2", + }, + T2Ptr: &T2{ + "t2 ptr", + }, + T2Arr: []T2{ + {"t2 elem 0"}, + {"t2 elem 1"}, + }, + T2PtrArr: []*T2{ + {"t2 ptr v1"}, + {"t2 ptr v2"}, + }, + StrArr: []string{"s 1", "s 2", "s 3"}, + IntArr: []int{9, 12, -1}, + FloatArr: []float64{-23.99, 15.234321, 39912342314}, + BoolArr: []bool{false, true, true, true, false}, + T3Arr: []T3{ + { + T4Arr: []T4{ + { + Typ: "t4 nested typ 1", + }, + { + Typ: "t4 nested typ 2", + IntPtr: &val, + }, + }, + }, + }, + }, + }, + { + name: "nil values", + value: T1{ + Name: "t1 test", + Val: 0, + ValU: 0, + Flag: false, + Float: 0, + T2: T2{}, + T2Ptr: nil, + T2Arr: nil, + T2PtrArr: nil, + StrArr: nil, + IntArr: nil, + FloatArr: nil, + BoolArr: nil, + T3Arr: nil, + }, + }, + { + name: "array values", + value: []T2{ + {"t2 elem 0"}, + {"t2 elem 1"}, + }, + }, + { + name: "array ptr", + value: &[]T2{ + {"t2 elem 0"}, + {"t2 elem 1"}, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + vals := Encode(test.value, "props", OptionalJSONTag) + + typ := reflect.TypeOf(test.value) + + if typ.Kind() != reflect.Slice && typ.Kind() != reflect.Ptr { + assert.NotEmpty(t, vals["props:bool_flag"]) + + t2 := T1{} + DecodeInto(&t2, vals, "props", OptionalJSONTag) + + assert.EqualValues(t, test.value, t2) + } + + t3 := Decode(typ, vals, "props", OptionalJSONTag) + + assert.EqualValues(t, test.value, t3) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/description.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/description.go new file mode 100644 index 0000000000000000000000000000000000000000..8bad4797ae069b892735a7a49f654d5962d7e19c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/description.go @@ -0,0 +1,19 @@ +package spdxhelpers + +import "github.com/anchore/syft/syft/pkg" + +func Description(p pkg.Package) string { + if hasMetadata(p) { + switch metadata := p.Metadata.(type) { + case pkg.ApkMetadata: + return metadata.Description + case pkg.NpmPackageJSONMetadata: + return metadata.Description + } + } + return "" +} + +func hasMetadata(p pkg.Package) bool { + return p.Metadata != nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/description_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/description_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e620186220e0deda24f9c40813fdda0ae5fd0810 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/description_test.go @@ -0,0 +1,56 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_Description(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "no metadata", + input: pkg.Package{}, + expected: "", + }, + { + name: "from apk", + input: pkg.Package{ + Metadata: pkg.ApkMetadata{ + Description: "a description!", + }, + }, + expected: "a description!", + }, + { + name: "from npm", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Description: "a description!", + }, + }, + expected: "a description!", + }, + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "empty", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Homepage: "", + }, + }, + expected: "", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, Description(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_name.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_name.go new file mode 100644 index 0000000000000000000000000000000000000000..4e896427acbed34e58c874a11e48abf9db80d551 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_name.go @@ -0,0 +1,30 @@ +package spdxhelpers + +import ( + "path" + "strings" + + "github.com/anchore/syft/syft/source" +) + +func DocumentName(srcMetadata source.Metadata) string { + switch srcMetadata.Scheme { + case source.ImageScheme: + return cleanName(srcMetadata.ImageMetadata.UserInput) + case source.DirectoryScheme, source.FileScheme: + return cleanName(srcMetadata.Path) + default: + return "unknown" + } +} + +func cleanName(name string) string { + // remove # according to specification + name = strings.ReplaceAll(name, "#", "-") + + // remove : for url construction + name = strings.ReplaceAll(name, ":", "-") + + // clean relative pathing + return path.Clean(name) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_name_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_name_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e3d0ff5b5ed4d08d233da03d2bb9f1d8e8191bcd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_name_test.go @@ -0,0 +1,70 @@ +package spdxhelpers + +import ( + "fmt" + "strings" + "testing" + + "github.com/anchore/syft/syft/source" + "github.com/scylladb/go-set/strset" + "github.com/stretchr/testify/assert" +) + +func Test_DocumentName(t *testing.T) { + allSchemes := strset.New() + for _, s := range source.AllSchemes { + allSchemes.Add(string(s)) + } + testedSchemes := strset.New() + + tests := []struct { + name string + inputName string + srcMetadata source.Metadata + expected string + }{ + { + name: "image", + inputName: "my-name", + srcMetadata: source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: source.ImageMetadata{ + UserInput: "image-repo/name:tag", + ID: "id", + ManifestDigest: "digest", + }, + }, + expected: "image-repo/name-tag", + }, + { + name: "directory", + inputName: "my-name", + srcMetadata: source.Metadata{ + Scheme: source.DirectoryScheme, + Path: "some/path/to/place", + }, + expected: "some/path/to/place", + }, + { + name: "file", + inputName: "my-name", + srcMetadata: source.Metadata{ + Scheme: source.FileScheme, + Path: "some/path/to/place", + }, + expected: "some/path/to/place", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := DocumentName(test.srcMetadata) + assert.True(t, strings.HasPrefix(actual, test.expected), fmt.Sprintf("actual name %q", actual)) + + // track each scheme tested (passed or not) + testedSchemes.Add(string(test.srcMetadata.Scheme)) + }) + } + + // assert all possible schemes were under test + assert.ElementsMatch(t, allSchemes.List(), testedSchemes.List(), "not all source.Schemes are under test") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_namespace.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_namespace.go new file mode 100644 index 0000000000000000000000000000000000000000..9110efef54c8790ff68e361274a91cf8bea03282 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_namespace.go @@ -0,0 +1,42 @@ +package spdxhelpers + +import ( + "fmt" + "net/url" + "path" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/source" + "github.com/google/uuid" +) + +func DocumentNameAndNamespace(srcMetadata source.Metadata) (string, string) { + name := DocumentName(srcMetadata) + return name, DocumentNamespace(name, srcMetadata) +} + +func DocumentNamespace(name string, srcMetadata source.Metadata) string { + input := "unknown-source-type" + switch srcMetadata.Scheme { + case source.ImageScheme: + input = "image" + case source.DirectoryScheme: + input = "dir" + case source.FileScheme: + input = "file" + } + + uniqueID := uuid.Must(uuid.NewRandom()) + identifier := path.Join(input, uniqueID.String()) + if name != "." { + identifier = path.Join(input, fmt.Sprintf("%s-%s", name, uniqueID.String())) + } + + u := url.URL{ + Scheme: "https", + Host: "anchore.com", + Path: path.Join(internal.ApplicationName, identifier), + } + + return u.String() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_namespace_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_namespace_test.go new file mode 100644 index 0000000000000000000000000000000000000000..12030100e3dc3076cdb452b3b81343be98322c0d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/document_namespace_test.go @@ -0,0 +1,71 @@ +package spdxhelpers + +import ( + "fmt" + "strings" + "testing" + + "github.com/anchore/syft/syft/source" + "github.com/scylladb/go-set/strset" + "github.com/stretchr/testify/assert" +) + +func Test_documentNamespace(t *testing.T) { + allSchemes := strset.New() + for _, s := range source.AllSchemes { + allSchemes.Add(string(s)) + } + testedSchemes := strset.New() + + tests := []struct { + name string + inputName string + srcMetadata source.Metadata + expected string + }{ + { + name: "image", + inputName: "my-name", + srcMetadata: source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: source.ImageMetadata{ + UserInput: "image-repo/name:tag", + ID: "id", + ManifestDigest: "digest", + }, + }, + expected: "https://anchore.com/syft/image/my-name-", + }, + { + name: "directory", + inputName: "my-name", + srcMetadata: source.Metadata{ + Scheme: source.DirectoryScheme, + Path: "some/path/to/place", + }, + expected: "https://anchore.com/syft/dir/my-name-", + }, + { + name: "file", + inputName: "my-name", + srcMetadata: source.Metadata{ + Scheme: source.FileScheme, + Path: "some/path/to/place", + }, + expected: "https://anchore.com/syft/file/my-name-", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := DocumentNamespace(test.inputName, test.srcMetadata) + // note: since the namespace ends with a UUID we check the prefix + assert.True(t, strings.HasPrefix(actual, test.expected), fmt.Sprintf("actual namespace %q", actual)) + + // track each scheme tested (passed or not) + testedSchemes.Add(string(test.srcMetadata.Scheme)) + }) + } + + // assert all possible schemes were under test + assert.ElementsMatch(t, allSchemes.List(), testedSchemes.List(), "not all source.Schemes are under test") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/download_location.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/download_location.go new file mode 100644 index 0000000000000000000000000000000000000000..060f78359f3ea8f9db4bface7dab862f4dfb4c10 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/download_location.go @@ -0,0 +1,26 @@ +package spdxhelpers + +import "github.com/anchore/syft/syft/pkg" + +const NONE = "NONE" +const NOASSERTION = "NOASSERTION" + +func DownloadLocation(p pkg.Package) string { + // 3.7: Package Download Location + // Cardinality: mandatory, one + // NONE if there is no download location whatsoever. + // NOASSERTION if: + // (i) the SPDX file creator has attempted to but cannot reach a reasonable objective determination; + // (ii) the SPDX file creator has made no attempt to determine this field; or + // (iii) the SPDX file creator has intentionally provided no information (no meaning should be implied by doing so). + + if hasMetadata(p) { + switch metadata := p.Metadata.(type) { + case pkg.ApkMetadata: + return NoneIfEmpty(metadata.URL) + case pkg.NpmPackageJSONMetadata: + return NoneIfEmpty(metadata.URL) + } + } + return NOASSERTION +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/download_location_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/download_location_test.go new file mode 100644 index 0000000000000000000000000000000000000000..42b205a1e4234943d01da7eb33ae88495b29e5e7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/download_location_test.go @@ -0,0 +1,54 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_DownloadLocation(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + name: "no metadata", + input: pkg.Package{}, + expected: NOASSERTION, + }, + { + name: "from apk", + input: pkg.Package{ + Metadata: pkg.ApkMetadata{ + URL: "http://a-place.gov", + }, + }, + expected: "http://a-place.gov", + }, + { + name: "from npm", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + URL: "http://a-place.gov", + }, + }, + expected: "http://a-place.gov", + }, + { + name: "empty", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + URL: "", + }, + }, + expected: NONE, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, DownloadLocation(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_ref.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_ref.go new file mode 100644 index 0000000000000000000000000000000000000000..98a1bc37ecefebbd12d28eeb2ba8d8f29bcb9237 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_ref.go @@ -0,0 +1,43 @@ +package spdxhelpers + +type ReferenceCategory string + +const ( + SecurityReferenceCategory ReferenceCategory = "SECURITY" + PackageManagerReferenceCategory ReferenceCategory = "PACKAGE_MANAGER" + OtherReferenceCategory ReferenceCategory = "OTHER" +) + +// source: https://spdx.github.io/spdx-spec/appendix-VI-external-repository-identifiers/ + +type ExternalRefType string + +const ( + // see https://nvd.nist.gov/cpe + Cpe22ExternalRefType ExternalRefType = "cpe22Type" + // see https://nvd.nist.gov/cpe + Cpe23ExternalRefType ExternalRefType = "cpe23Type" + // see http://repo1.maven.org/maven2/ + MavenCentralExternalRefType ExternalRefType = "maven-central" + // see https://www.npmjs.com/ + NpmExternalRefType ExternalRefType = "npm" + // see https://www.nuget.org/ + NugetExternalRefType ExternalRefType = "nuget" + // see http://bower.io/ + BowerExternalRefType ExternalRefType = "bower" + // see https://github.com/package-url/purl-spec + PurlExternalRefType ExternalRefType = "purl" + // These point to objects present in the Software Heritage archive by the means of SoftWare Heritage persistent Identifiers (SWHID) + SwhExternalRefType ExternalRefType = "swh" +) + +type ExternalRef struct { + Comment string `json:"comment,omitempty"` + // Category for the external reference. + ReferenceCategory ReferenceCategory `json:"referenceCategory"` + // The unique string with no spaces necessary to access the package-specific information, metadata, or content + // within the target location. The format of the locator is subject to constraints defined by the . + ReferenceLocator string `json:"referenceLocator"` + // Type of the external reference. These are defined in an appendix in the SPDX specification. + ReferenceType ExternalRefType `json:"referenceType"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_refs.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_refs.go new file mode 100644 index 0000000000000000000000000000000000000000..d114c2ab27916bd99b1d9b48e2ea49c849faecaf --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_refs.go @@ -0,0 +1,27 @@ +package spdxhelpers + +import ( + "github.com/anchore/syft/syft/pkg" +) + +func ExternalRefs(p pkg.Package) (externalRefs []ExternalRef) { + externalRefs = make([]ExternalRef, 0) + + for _, c := range p.CPEs { + externalRefs = append(externalRefs, ExternalRef{ + ReferenceCategory: SecurityReferenceCategory, + ReferenceLocator: pkg.CPEString(c), + ReferenceType: Cpe23ExternalRefType, + }) + } + + if p.PURL != "" { + externalRefs = append(externalRefs, ExternalRef{ + ReferenceCategory: PackageManagerReferenceCategory, + ReferenceLocator: p.PURL, + ReferenceType: PurlExternalRefType, + }) + } + + return externalRefs +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_refs_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_refs_test.go new file mode 100644 index 0000000000000000000000000000000000000000..180a5c4dbd128fb07fde0f1c215469f6046dc23b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/external_refs_test.go @@ -0,0 +1,44 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_ExternalRefs(t *testing.T) { + testCPE := pkg.MustCPE("cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*") + tests := []struct { + name string + input pkg.Package + expected []ExternalRef + }{ + { + name: "cpe + purl", + input: pkg.Package{ + CPEs: []pkg.CPE{ + testCPE, + }, + PURL: "a-purl", + }, + expected: []ExternalRef{ + { + ReferenceCategory: SecurityReferenceCategory, + ReferenceLocator: pkg.CPEString(testCPE), + ReferenceType: Cpe23ExternalRefType, + }, + { + ReferenceCategory: PackageManagerReferenceCategory, + ReferenceLocator: "a-purl", + ReferenceType: PurlExternalRefType, + }, + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.ElementsMatch(t, test.expected, ExternalRefs(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/file_type.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/file_type.go new file mode 100644 index 0000000000000000000000000000000000000000..97e4ab4786df1bbcd93bca7d4b012a86f35f6aaf --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/file_type.go @@ -0,0 +1,17 @@ +package spdxhelpers + +type FileType string + +const ( + DocumentationFileType FileType = "DOCUMENTATION" // if the file serves as documentation + ImageFileType FileType = "IMAGE" // if the file is associated with a picture image file (MIME type of image/*, e.g., .jpg, .gif) + VideoFileType FileType = "VIDEO" // if the file is associated with a video file type (MIME type of video/*) + ArchiveFileType FileType = "ARCHIVE" // if the file represents an archive (.tar, .jar, etc.) + SpdxFileType FileType = "SPDX" // if the file is an SPDX document + ApplicationFileType FileType = "APPLICATION" // if the file is associated with a specific application type (MIME type of application/*) + SourceFileType FileType = "SOURCE" // if the file is human readable source code (.c, .html, etc.) + BinaryFileType FileType = "BINARY" // if the file is a compiled object, target image or binary executable (.o, .a, etc.) + TextFileType FileType = "TEXT" // if the file is human readable text file (MIME type of text/*) + AudioFileType FileType = "AUDIO" // if the file is associated with an audio file (MIME type of audio/* , e.g. .mp3) + OtherFileType FileType = "OTHER" // if the file doesn't fit into the above categories (generated artifacts, data files, etc.) +) diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/homepage.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/homepage.go new file mode 100644 index 0000000000000000000000000000000000000000..b790ba6140fcec649a6c0c5c2bbf1ccc16a4d100 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/homepage.go @@ -0,0 +1,15 @@ +package spdxhelpers + +import "github.com/anchore/syft/syft/pkg" + +func Homepage(p pkg.Package) string { + if hasMetadata(p) { + switch metadata := p.Metadata.(type) { + case pkg.GemMetadata: + return metadata.Homepage + case pkg.NpmPackageJSONMetadata: + return metadata.Homepage + } + } + return "" +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/homepage_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/homepage_test.go new file mode 100644 index 0000000000000000000000000000000000000000..371f45bfb9b67692b4d1e58c23558eb3b56e1667 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/homepage_test.go @@ -0,0 +1,56 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_Homepage(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "no metadata", + input: pkg.Package{}, + expected: "", + }, + { + name: "from gem", + input: pkg.Package{ + Metadata: pkg.GemMetadata{ + Homepage: "http://a-place.gov", + }, + }, + expected: "http://a-place.gov", + }, + { + name: "from npm", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Homepage: "http://a-place.gov", + }, + }, + expected: "http://a-place.gov", + }, + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "empty", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Homepage: "", + }, + }, + expected: "", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, Homepage(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/license.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/license.go new file mode 100644 index 0000000000000000000000000000000000000000..3feaee9944b4d9c0b60bdcd12f2622f3f44afe33 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/license.go @@ -0,0 +1,37 @@ +package spdxhelpers + +import ( + "strings" + + "github.com/anchore/syft/internal/spdxlicense" + "github.com/anchore/syft/syft/pkg" +) + +func License(p pkg.Package) string { + // source: https://spdx.github.io/spdx-spec/3-package-information/#313-concluded-license + // The options to populate this field are limited to: + // A valid SPDX License Expression as defined in Appendix IV; + // NONE, if the SPDX file creator concludes there is no license available for this package; or + // NOASSERTION if: + // (i) the SPDX file creator has attempted to but cannot reach a reasonable objective determination; + // (ii) the SPDX file creator has made no attempt to determine this field; or + // (iii) the SPDX file creator has intentionally provided no information (no meaning should be implied by doing so). + + if len(p.Licenses) == 0 { + return NONE + } + + // take all licenses and assume an AND expression; for information about license expressions see https://spdx.github.io/spdx-spec/appendix-IV-SPDX-license-expressions/ + var parsedLicenses []string + for _, l := range p.Licenses { + if value, exists := spdxlicense.ID(l); exists { + parsedLicenses = append(parsedLicenses, value) + } + } + + if len(parsedLicenses) == 0 { + return NOASSERTION + } + + return strings.Join(parsedLicenses, " AND ") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/license_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/license_test.go new file mode 100644 index 0000000000000000000000000000000000000000..94c32f9f67c11b4a4f23c45979a024cf2c8d6986 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/license_test.go @@ -0,0 +1,73 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_License(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + name: "no licenses", + input: pkg.Package{}, + expected: NONE, + }, + { + name: "no SPDX licenses", + input: pkg.Package{ + Licenses: []string{ + "made-up", + }, + }, + expected: NOASSERTION, + }, + { + name: "with SPDX license", + input: pkg.Package{ + Licenses: []string{ + "MIT", + }, + }, + expected: "MIT", + }, + { + name: "with SPDX license expression", + input: pkg.Package{ + Licenses: []string{ + "MIT", + "GPL-3.0", + }, + }, + expected: "MIT AND GPL-3.0-only", + }, + { + name: "cap insensitive", + input: pkg.Package{ + Licenses: []string{ + "gpl-3.0", + }, + }, + expected: "GPL-3.0-only", + }, + { + name: "debian to spdx conversion", + input: pkg.Package{ + Licenses: []string{ + "GPL-2", + }, + }, + expected: "GPL-2.0-only", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, License(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/none_if_empty.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/none_if_empty.go new file mode 100644 index 0000000000000000000000000000000000000000..6cc272f1f847584f2cc7d062dd650977d9ac31cb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/none_if_empty.go @@ -0,0 +1,12 @@ +package spdxhelpers + +import ( + "strings" +) + +func NoneIfEmpty(value string) string { + if strings.TrimSpace(value) == "" { + return NONE + } + return value +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/none_if_empty_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/none_if_empty_test.go new file mode 100644 index 0000000000000000000000000000000000000000..3fc95893493acbc83ac54f88617d7641b5176928 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/none_if_empty_test.go @@ -0,0 +1,41 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func Test_noneIfEmpty(t *testing.T) { + tests := []struct { + name string + value string + expected string + }{ + { + name: "non-zero value", + value: "something", + expected: "something", + }, + { + name: "empty", + value: "", + expected: NONE, + }, + { + name: "space", + value: " ", + expected: NONE, + }, + { + name: "tab", + value: "\t", + expected: NONE, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, NoneIfEmpty(test.value)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/originator_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/originator_test.go new file mode 100644 index 0000000000000000000000000000000000000000..be8e9e97b93f0c5138af8457c8823eab0a579d70 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/originator_test.go @@ -0,0 +1,114 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_Originator(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected string + }{ + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "no metadata", + input: pkg.Package{}, + expected: "", + }, + { + name: "from gem", + input: pkg.Package{ + Metadata: pkg.GemMetadata{ + Authors: []string{ + "auth1", + "auth2", + }, + }, + }, + expected: "Person: auth1", + }, + { + name: "from npm", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Author: "auth", + }, + }, + expected: "Person: auth", + }, + { + name: "from apk", + input: pkg.Package{ + Metadata: pkg.ApkMetadata{ + Maintainer: "auth", + }, + }, + expected: "Person: auth", + }, + { + name: "from python - just name", + input: pkg.Package{ + Metadata: pkg.PythonPackageMetadata{ + Author: "auth", + }, + }, + expected: "Person: auth", + }, + { + name: "from python - just email", + input: pkg.Package{ + Metadata: pkg.PythonPackageMetadata{ + AuthorEmail: "auth@auth.gov", + }, + }, + expected: "Person: auth@auth.gov", + }, + { + name: "from python - both name and email", + input: pkg.Package{ + Metadata: pkg.PythonPackageMetadata{ + Author: "auth", + AuthorEmail: "auth@auth.gov", + }, + }, + expected: "Person: auth (auth@auth.gov)", + }, + { + name: "from rpm", + input: pkg.Package{ + Metadata: pkg.RpmMetadata{ + Vendor: "auth", + }, + }, + expected: "Organization: auth", + }, + { + name: "from dpkg", + input: pkg.Package{ + Metadata: pkg.DpkgMetadata{ + Maintainer: "auth", + }, + }, + expected: "Person: auth", + }, + { + // note: since this is an optional field, no value is preferred over NONE or NOASSERTION + name: "empty", + input: pkg.Package{ + Metadata: pkg.NpmPackageJSONMetadata{ + Author: "", + }, + }, + expected: "", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, Originator(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/origintor.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/origintor.go new file mode 100644 index 0000000000000000000000000000000000000000..dd718cbf4c099608505c57ae92cb81ca738c10d4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/origintor.go @@ -0,0 +1,41 @@ +package spdxhelpers + +import ( + "fmt" + + "github.com/anchore/syft/syft/pkg" +) + +// Originator needs to conform to the SPDX spec here: +// https://spdx.github.io/spdx-spec/package-information/#76-package-originator-field +// Available options are: , NOASSERTION, Person: , Organization: +func Originator(p pkg.Package) string { + if hasMetadata(p) { + author := "" + switch metadata := p.Metadata.(type) { + case pkg.ApkMetadata: + author = metadata.Maintainer + case pkg.NpmPackageJSONMetadata: + author = metadata.Author + case pkg.PythonPackageMetadata: + author = metadata.Author + if author == "" { + author = metadata.AuthorEmail + } else if metadata.AuthorEmail != "" { + author = fmt.Sprintf("%s (%s)", author, metadata.AuthorEmail) + } + case pkg.GemMetadata: + if len(metadata.Authors) > 0 { + author = metadata.Authors[0] + } + case pkg.RpmMetadata: + return "Organization: " + metadata.Vendor + case pkg.DpkgMetadata: + author = metadata.Maintainer + } + if author != "" { + return "Person: " + author + } + } + return "" +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/relationship_type.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/relationship_type.go new file mode 100644 index 0000000000000000000000000000000000000000..564dd32ec023f2f5f0af93209a8fb95cdb02160b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/relationship_type.go @@ -0,0 +1,173 @@ +package spdxhelpers + +// source: https://spdx.github.io/spdx-spec/7-relationships-between-SPDX-elements/ +type RelationshipType string + +const ( + // DescribedByRelationship is to be used when SPDXRef-A is described by SPDXREF-Document. + // Example: The package 'WildFly' is described by SPDX document WildFly.spdx. + DescribedByRelationship RelationshipType = "DESCRIBED_BY" + + // ContainsRelationship is to be used when SPDXRef-A contains SPDXRef-B. + // Example: An ARCHIVE file bar.tgz contains a SOURCE file foo.c. + ContainsRelationship RelationshipType = "CONTAINS" + + // ContainedByRelationship is to be used when SPDXRef-A is contained by SPDXRef-B. + // Example: A SOURCE file foo.c is contained by ARCHIVE file bar.tgz + ContainedByRelationship RelationshipType = "CONTAINED_BY" + + // DependsOnRelationship is to be used when SPDXRef-A depends on SPDXRef-B. + // Example: Package A depends on the presence of package B in order to build and run + DependsOnRelationship RelationshipType = "DEPENDS_ON" + + // DependencyOfRelationship is to be used when SPDXRef-A is dependency of SPDXRef-B. + // Example: A is explicitly stated as a dependency of B in a machine-readable file. Use when a package manager does not define scopes. + DependencyOfRelationship RelationshipType = "DEPENDENCY_OF" + + // DependencyManifestOfRelationship is to be used when SPDXRef-A is a manifest file that lists a set of dependencies for SPDXRef-B. + // Example: A file package.json is the dependency manifest of a package foo. Note that only one manifest should be used to define the same dependency graph. + DependencyManifestOfRelationship RelationshipType = "DEPENDENCY_MANIFEST_OF" + + // BuildDependencyOfRelationship is to be used when SPDXRef-A is a build dependency of SPDXRef-B. + // Example: A is in the compile scope of B in a Maven project. + BuildDependencyOfRelationship RelationshipType = "BUILD_DEPENDENCY_OF" + + // DevDependencyOfRelationship is to be used when SPDXRef-A is a development dependency of SPDXRef-B. + // Example: A is in the devDependencies scope of B in a Maven project. + DevDependencyOfRelationship RelationshipType = "DEV_DEPENDENCY_OF" + + // OptionalDependencyOfRelationship is to be used when SPDXRef-A is an optional dependency of SPDXRef-B. + // Example: Use when building the code will proceed even if a dependency cannot be found, fails to install, or is only installed on a specific platform. For example, A is in the optionalDependencies scope of npm project B. + OptionalDependencyOfRelationship RelationshipType = "OPTIONAL_DEPENDENCY_OF" + + // ProvidedDependencyOfRelationship is to be used when SPDXRef-A is a to be provided dependency of SPDXRef-B. + // Example: A is in the provided scope of B in a Maven project, indicating that the project expects it to be provided, for instance, by the container or JDK. + ProvidedDependencyOfRelationship RelationshipType = "PROVIDED_DEPENDENCY_OF" + + // TestDependencyOfRelationship is to be used when SPDXRef-A is a test dependency of SPDXRef-B. + // Example: A is in the test scope of B in a Maven project. + TestDependencyOfRelationship RelationshipType = "TEST_DEPENDENCY_OF" + + // RuntimeDependencyOfRelationship is to be used when SPDXRef-A is a dependency required for the execution of SPDXRef-B. + // Example: A is in the runtime scope of B in a Maven project. + RuntimeDependencyOfRelationship RelationshipType = "RUNTIME_DEPENDENCY_OF" + + // ExampleOfRelationship is to be used when SPDXRef-A is an example of SPDXRef-B. + // Example: The file or snippet that illustrates how to use an application or library. + ExampleOfRelationship RelationshipType = "EXAMPLE_OF" + + // GeneratesRelationship is to be used when SPDXRef-A generates SPDXRef-B. + // Example: A SOURCE file makefile.mk generates a BINARY file a.out + GeneratesRelationship RelationshipType = "GENERATES" + + // GeneratedFromRelationship is to be used when SPDXRef-A was generated from SPDXRef-B. + // Example: A BINARY file a.out has been generated from a SOURCE file makefile.mk. A BINARY file foolib.a is generated from a SOURCE file bar.c. + GeneratedFromRelationship RelationshipType = "GENERATED_FROM" + + // AncestorOfRelationship is to be used when SPDXRef-A is an ancestor (same lineage but pre-dates) SPDXRef-B. + // Example: A SOURCE file makefile.mk is a version of the original ancestor SOURCE file 'makefile2.mk' + AncestorOfRelationship RelationshipType = "ANCESTOR_OF" + + // DescendantOfRelationship is to be used when SPDXRef-A is a descendant of (same lineage but postdates) SPDXRef-B. + // Example: A SOURCE file makefile2.mk is a descendant of the original SOURCE file 'makefile.mk' + DescendantOfRelationship RelationshipType = "DESCENDANT_OF" + + // VariantOfRelationship is to be used when SPDXRef-A is a variant of (same lineage but not clear which came first) SPDXRef-B. + // Example: A SOURCE file makefile2.mk is a variant of SOURCE file makefile.mk if they differ by some edit, but there is no way to tell which came first (no reliable date information). + VariantOfRelationship RelationshipType = "VARIANT_OF" + + // DistributionArtifactRelationship is to be used when distributing SPDXRef-A requires that SPDXRef-B also be distributed. + // Example: A BINARY file foo.o requires that the ARCHIVE file bar-sources.tgz be made available on distribution. + DistributionArtifactRelationship RelationshipType = "DISTRIBUTION_ARTIFACT" + + // PatchForRelationship is to be used when SPDXRef-A is a patch file for (to be applied to) SPDXRef-B. + // Example: A SOURCE file foo.diff is a patch file for SOURCE file foo.c. + PatchForRelationship RelationshipType = "PATCH_FOR" + + // PatchAppliedRelationship is to be used when SPDXRef-A is a patch file that has been applied to SPDXRef-B. + // Example: A SOURCE file foo.diff is a patch file that has been applied to SOURCE file 'foo-patched.c'. + PatchAppliedRelationship RelationshipType = "PATCH_APPLIED" + + // CopyOfRelationship is to be used when SPDXRef-A is an exact copy of SPDXRef-B. + // Example: A BINARY file alib.a is an exact copy of BINARY file a2lib.a. + CopyOfRelationship RelationshipType = "COPY_OF" + + // FileAddedRelationship is to be used when SPDXRef-A is a file that was added to SPDXRef-B. + // Example: A SOURCE file foo.c has been added to package ARCHIVE bar.tgz. + FileAddedRelationship RelationshipType = "FILE_ADDED" + + // FileDeletedRelationship is to be used when SPDXRef-A is a file that was deleted from SPDXRef-B. + // Example: A SOURCE file foo.diff has been deleted from package ARCHIVE bar.tgz. + FileDeletedRelationship RelationshipType = "FILE_DELETED" + + // FileModifiedRelationship is to be used when SPDXRef-A is a file that was modified from SPDXRef-B. + // Example: A SOURCE file foo.c has been modified from SOURCE file foo.orig.c. + FileModifiedRelationship RelationshipType = "FILE_MODIFIED" + + // ExpandedFromArchiveRelationship is to be used when SPDXRef-A is expanded from the archive SPDXRef-B. + // Example: A SOURCE file foo.c, has been expanded from the archive ARCHIVE file xyz.tgz. + ExpandedFromArchiveRelationship RelationshipType = "EXPANDED_FROM_ARCHIVE" + + // DynamicLinkRelationship is to be used when SPDXRef-A dynamically links to SPDXRef-B. + // Example: An APPLICATION file 'myapp' dynamically links to BINARY file zlib.so. + DynamicLinkRelationship RelationshipType = "DYNAMIC_LINK" + + // StaticLinkRelationship is to be used when SPDXRef-A statically links to SPDXRef-B. + // Example: An APPLICATION file 'myapp' statically links to BINARY zlib.a. + StaticLinkRelationship RelationshipType = "STATIC_LINK" + + // DataFileOfRelationship is to be used when SPDXRef-A is a data file used in SPDXRef-B. + // Example: An IMAGE file 'kitty.jpg' is a data file of an APPLICATION 'hellokitty'. + DataFileOfRelationship RelationshipType = "DATA_FILE_OF" + + // TestCaseOfRelationship is to be used when SPDXRef-A is a test case used in testing SPDXRef-B. + // Example: A SOURCE file testMyCode.java is a unit test file used to test an APPLICATION MyPackage. + TestCaseOfRelationship RelationshipType = "TEST_CASE_OF" + + // BuildToolOfRelationship is to be used when SPDXRef-A is used to build SPDXRef-B. + // Example: A SOURCE file makefile.mk is used to build an APPLICATION 'zlib'. + BuildToolOfRelationship RelationshipType = "BUILD_TOOL_OF" + + // DevToolOfRelationship is to be used when SPDXRef-A is used as a development tool for SPDXRef-B. + // Example: Any tool used for development such as a code debugger. + DevToolOfRelationship RelationshipType = "DEV_TOOL_OF" + + // TestOfRelationship is to be used when SPDXRef-A is used for testing SPDXRef-B. + // Example: Generic relationship for cases where it's clear that something is used for testing but unclear whether it's TEST_CASE_OF or TEST_TOOL_OF. + TestOfRelationship RelationshipType = "TEST_OF" + + // TestToolOfRelationship is to be used when SPDXRef-A is used as a test tool for SPDXRef-B. + // Example: Any tool used to test the code such as ESlint. + TestToolOfRelationship RelationshipType = "TEST_TOOL_OF" + + // DocumentationOfRelationship is to be used when SPDXRef-A provides documentation of SPDXRef-B. + // Example: A DOCUMENTATION file readme.txt documents the APPLICATION 'zlib'. + DocumentationOfRelationship RelationshipType = "DOCUMENTATION_OF" + + // OptionalComponentOfRelationship is to be used when SPDXRef-A is an optional component of SPDXRef-B. + // Example: A SOURCE file fool.c (which is in the contributors directory) may or may not be included in the build of APPLICATION 'atthebar'. + OptionalComponentOfRelationship RelationshipType = "OPTIONAL_COMPONENT_OF" + + // MetafileOfRelationship is to be used when SPDXRef-A is a metafile of SPDXRef-B. + // Example: A SOURCE file pom.xml is a metafile of the APPLICATION 'Apache Xerces'. + MetafileOfRelationship RelationshipType = "METAFILE_OF" + + // PackageOfRelationship is to be used when SPDXRef-A is used as a package as part of SPDXRef-B. + // Example: A Linux distribution contains an APPLICATION package gawk as part of the distribution MyLinuxDistro. + PackageOfRelationship RelationshipType = "PACKAGE_OF" + + // AmendsRelationship is to be used when (current) SPDXRef-DOCUMENT amends the SPDX information in SPDXRef-B. + // Example: (Current) SPDX document A version 2 contains a correction to a previous version of the SPDX document A version 1. Note the reserved identifier SPDXRef-DOCUMENT for the current document is required. + AmendsRelationship RelationshipType = "AMENDS" + + // PrerequisiteForRelationship is to be used when SPDXRef-A is a prerequisite for SPDXRef-B. + // Example: A library bar.dll is a prerequisite or dependency for APPLICATION foo.exe + PrerequisiteForRelationship RelationshipType = "PREREQUISITE_FOR" + + // HasPrerequisiteRelationship is to be used when SPDXRef-A has as a prerequisite SPDXRef-B. + // Example: An APPLICATION foo.exe has prerequisite or dependency on bar.dll + HasPrerequisiteRelationship RelationshipType = "HAS_PREREQUISITE" + + // OtherRelationship is to be used for a relationship which has not been defined in the formal SPDX specification. A description of the relationship should be included in the Relationship comments field. + OtherRelationship RelationshipType = "OTHER" +) diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/source_info.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/source_info.go new file mode 100644 index 0000000000000000000000000000000000000000..81c63348d652df6fe3bbd8e03244282bceb44430 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/source_info.go @@ -0,0 +1,56 @@ +package spdxhelpers + +import ( + "strings" + + "github.com/anchore/syft/syft/pkg" +) + +//nolint:funlen +func SourceInfo(p pkg.Package) string { + answer := "" + switch p.Type { + case pkg.AlpmPkg: + answer = "acquired package info from ALPM DB" + case pkg.RpmPkg: + answer = "acquired package info from RPM DB" + case pkg.ApkPkg: + answer = "acquired package info from APK DB" + case pkg.DartPubPkg: + answer = "acquired package info from pubspec manifest" + case pkg.DebPkg: + answer = "acquired package info from DPKG DB" + case pkg.DotnetPkg: + answer = "acquired package info from dotnet project assets file" + case pkg.NpmPkg: + answer = "acquired package info from installed node module manifest file" + case pkg.PythonPkg: + answer = "acquired package info from installed python package manifest file" + case pkg.JavaPkg, pkg.JenkinsPluginPkg: + answer = "acquired package info from installed java archive" + case pkg.GemPkg: + answer = "acquired package info from installed gem metadata file" + case pkg.GoModulePkg: + answer = "acquired package info from go module information" + case pkg.RustPkg: + answer = "acquired package info from rust cargo manifest" + case pkg.PhpComposerPkg: + answer = "acquired package info from PHP composer manifest" + case pkg.CocoapodsPkg: + answer = "acquired package info from installed cocoapods manifest file" + case pkg.ConanPkg: + answer = "acquired package info from conan manifest" + case pkg.PortagePkg: + answer = "acquired package info from portage DB" + case pkg.HackagePkg: + answer = "acquired package info from cabal or stack manifest files" + default: + answer = "acquired package info from the following paths" + } + var paths []string + for _, l := range p.Locations.ToSlice() { + paths = append(paths, l.RealPath) + } + + return answer + ": " + strings.Join(paths, ", ") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/source_info_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/source_info_test.go new file mode 100644 index 0000000000000000000000000000000000000000..a403aed054a16d0b34a5d9a62e40eb0d31cc0a0d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/source_info_test.go @@ -0,0 +1,199 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" +) + +func Test_SourceInfo(t *testing.T) { + tests := []struct { + name string + input pkg.Package + expected []string + }{ + { + name: "locations are captured", + input: pkg.Package{ + // note: no type given + Locations: source.NewLocationSet( + source.NewVirtualLocation("/a-place", "/b-place"), + source.NewVirtualLocation("/c-place", "/d-place"), + ), + }, + expected: []string{ + "from the following paths", + "/a-place", + "/c-place", + }, + }, + { + // note: no specific support for this + input: pkg.Package{ + Type: pkg.KbPkg, + }, + expected: []string{ + "from the following paths", + }, + }, + { + input: pkg.Package{ + Type: pkg.RpmPkg, + }, + expected: []string{ + "from RPM DB", + }, + }, + { + input: pkg.Package{ + Type: pkg.ApkPkg, + }, + expected: []string{ + "from APK DB", + }, + }, + { + input: pkg.Package{ + Type: pkg.DebPkg, + }, + expected: []string{ + "from DPKG DB", + }, + }, + { + input: pkg.Package{ + Type: pkg.NpmPkg, + }, + expected: []string{ + "from installed node module manifest file", + }, + }, + { + input: pkg.Package{ + Type: pkg.PythonPkg, + }, + expected: []string{ + "from installed python package manifest file", + }, + }, + { + input: pkg.Package{ + Type: pkg.JavaPkg, + }, + expected: []string{ + "from installed java archive", + }, + }, + { + input: pkg.Package{ + Type: pkg.JenkinsPluginPkg, + }, + expected: []string{ + "from installed java archive", + }, + }, + { + input: pkg.Package{ + Type: pkg.GemPkg, + }, + expected: []string{ + "from installed gem metadata file", + }, + }, + { + input: pkg.Package{ + Type: pkg.GoModulePkg, + }, + expected: []string{ + "from go module information", + }, + }, + { + input: pkg.Package{ + Type: pkg.RustPkg, + }, + expected: []string{ + "from rust cargo manifest", + }, + }, + { + input: pkg.Package{ + Type: pkg.PhpComposerPkg, + }, + expected: []string{ + "from PHP composer manifest", + }, + }, + { + input: pkg.Package{ + Type: pkg.DartPubPkg, + }, + expected: []string{ + "from pubspec manifest", + }, + }, + { + input: pkg.Package{ + Type: pkg.DotnetPkg, + }, + expected: []string{ + "from dotnet project assets file", + }, + }, + { + input: pkg.Package{ + Type: pkg.AlpmPkg, + }, + expected: []string{ + "from ALPM DB", + }, + }, + { + input: pkg.Package{ + Type: pkg.CocoapodsPkg, + }, + expected: []string{ + "installed cocoapods manifest file", + }, + }, + { + input: pkg.Package{ + Type: pkg.ConanPkg, + }, + expected: []string{ + "from conan manifest", + }, + }, + { + input: pkg.Package{ + Type: pkg.PortagePkg, + }, + expected: []string{ + "from portage DB", + }, + }, + { + input: pkg.Package{ + Type: pkg.HackagePkg, + }, + expected: []string{ + "from cabal or stack manifest files", + }, + }, + } + var pkgTypes []pkg.Type + for _, test := range tests { + t.Run(test.name+" "+string(test.input.Type), func(t *testing.T) { + if test.input.Type != "" { + pkgTypes = append(pkgTypes, test.input.Type) + } + actual := SourceInfo(test.input) + for _, expected := range test.expected { + assert.Contains(t, actual, expected) + } + }) + } + assert.ElementsMatch(t, pkg.AllPkgs, pkgTypes, "missing one or more package types to test against (maybe a package type was added?)") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/spdxid.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/spdxid.go new file mode 100644 index 0000000000000000000000000000000000000000..f7a2180c98f61fc1ae2087629234a76b5153c01b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/spdxid.go @@ -0,0 +1,13 @@ +package spdxhelpers + +import ( + "regexp" +) + +var expr = regexp.MustCompile("[^a-zA-Z0-9.-]") + +// SPDX spec says SPDXID must be: +// "SPDXRef-"[idstring] where [idstring] is a unique string containing letters, numbers, ., and/or - +func SanitizeElementID(id string) string { + return expr.ReplaceAllString(id, "-") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/spdxid_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/spdxid_test.go new file mode 100644 index 0000000000000000000000000000000000000000..b66ccd45ebd01d332324251eabbc436e860e8f9c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/spdxid_test.go @@ -0,0 +1,39 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func Test_SanitizeElementID(t *testing.T) { + tests := []struct { + input string + expected string + }{ + { + input: "letters", + expected: "letters", + }, + { + input: "ssl-client", + expected: "ssl-client", + }, + { + input: "ssl_client", + expected: "ssl-client", + }, + { + input: "go-module-sigs.k8s.io/structured-merge-diff/v3", + expected: "go-module-sigs.k8s.io-structured-merge-diff-v3", + }, + } + + for _, test := range tests { + t.Run(test.input, func(t *testing.T) { + actual := SanitizeElementID(test.input) + + assert.Equal(t, test.expected, actual) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/to_syft_model.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/to_syft_model.go new file mode 100644 index 0000000000000000000000000000000000000000..9d7f05b3e00a892b846d663327fbedec614ea21e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/to_syft_model.go @@ -0,0 +1,387 @@ +package spdxhelpers + +import ( + "errors" + "net/url" + "strconv" + "strings" + + "github.com/spdx/tools-golang/spdx" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" +) + +func ToSyftModel(doc *spdx.Document2_2) (*sbom.SBOM, error) { + if doc == nil { + return nil, errors.New("cannot convert SPDX document to Syft model because document is nil") + } + + spdxIDMap := make(map[string]interface{}) + + src := source.Metadata{Scheme: source.UnknownScheme} + if doc.CreationInfo != nil { + src.Scheme = extractSchemeFromNamespace(doc.CreationInfo.DocumentNamespace) + } + + s := &sbom.SBOM{ + Source: src, + Artifacts: sbom.Artifacts{ + PackageCatalog: pkg.NewCatalog(), + FileMetadata: map[source.Coordinates]source.FileMetadata{}, + FileDigests: map[source.Coordinates][]file.Digest{}, + LinuxDistribution: findLinuxReleaseByPURL(doc), + }, + } + + collectSyftPackages(s, spdxIDMap, doc) + + collectSyftFiles(s, spdxIDMap, doc) + + s.Relationships = toSyftRelationships(spdxIDMap, doc) + + return s, nil +} + +// NOTE(jonas): SPDX doesn't inform what an SBOM is about, +// image, directory, for example. This is our best effort to determine +// the scheme. Syft-generated SBOMs have in the namespace +// field a type encoded, which we try to identify here. +func extractSchemeFromNamespace(ns string) source.Scheme { + u, err := url.Parse(ns) + if err != nil { + return source.UnknownScheme + } + + parts := strings.Split(u.Path, "/") + for _, p := range parts { + switch p { + case "file": + return source.FileScheme + case "image": + return source.ImageScheme + case "dir": + return source.DirectoryScheme + } + } + return source.UnknownScheme +} + +func findLinuxReleaseByPURL(doc *spdx.Document2_2) *linux.Release { + for _, p := range doc.Packages { + purlValue := findPURLValue(p) + if purlValue == "" { + continue + } + purl, err := packageurl.FromString(purlValue) + if err != nil { + log.Warnf("unable to parse purl: %s", purlValue) + continue + } + distro := findQualifierValue(purl, pkg.PURLQualifierDistro) + if distro != "" { + parts := strings.Split(distro, "-") + name := parts[0] + version := "" + if len(parts) > 1 { + version = parts[1] + } + return &linux.Release{ + PrettyName: name, + Name: name, + ID: name, + IDLike: []string{name}, + Version: version, + VersionID: version, + } + } + } + + return nil +} + +func collectSyftPackages(s *sbom.SBOM, spdxIDMap map[string]interface{}, doc *spdx.Document2_2) { + for _, p := range doc.Packages { + syftPkg := toSyftPackage(p) + spdxIDMap[string(p.PackageSPDXIdentifier)] = syftPkg + s.Artifacts.PackageCatalog.Add(*syftPkg) + } +} + +func collectSyftFiles(s *sbom.SBOM, spdxIDMap map[string]interface{}, doc *spdx.Document2_2) { + for _, f := range doc.UnpackagedFiles { + l := toSyftLocation(f) + spdxIDMap[string(f.FileSPDXIdentifier)] = l + + s.Artifacts.FileMetadata[l.Coordinates] = toFileMetadata(f) + s.Artifacts.FileDigests[l.Coordinates] = toFileDigests(f) + } +} + +func toFileDigests(f *spdx.File2_2) (digests []file.Digest) { + for _, digest := range f.FileChecksums { + digests = append(digests, file.Digest{ + Algorithm: string(digest.Algorithm), + Value: digest.Value, + }) + } + return digests +} + +func toFileMetadata(f *spdx.File2_2) (meta source.FileMetadata) { + // FIXME Syft is currently lossy due to the SPDX 2.2.1 spec not supporting arbitrary mimetypes + for _, typ := range f.FileType { + switch FileType(typ) { + case ImageFileType: + meta.MIMEType = "image/" + case VideoFileType: + meta.MIMEType = "video/" + case ApplicationFileType: + meta.MIMEType = "application/" + case TextFileType: + meta.MIMEType = "text/" + case AudioFileType: + meta.MIMEType = "audio/" + case BinaryFileType: + case ArchiveFileType: + case OtherFileType: + } + } + return meta +} + +func toSyftRelationships(spdxIDMap map[string]interface{}, doc *spdx.Document2_2) []artifact.Relationship { + var out []artifact.Relationship + for _, r := range doc.Relationships { + // FIXME what to do with r.RefA.DocumentRefID and r.RefA.SpecialID + if r.RefA.DocumentRefID != "" && requireAndTrimPrefix(r.RefA.DocumentRefID, "DocumentRef-") != string(doc.CreationInfo.SPDXIdentifier) { + log.Debugf("ignoring relationship to external document: %+v", r) + continue + } + a := spdxIDMap[string(r.RefA.ElementRefID)] + b := spdxIDMap[string(r.RefB.ElementRefID)] + from, fromOk := a.(*pkg.Package) + toPackage, toPackageOk := b.(*pkg.Package) + toLocation, toLocationOk := b.(*source.Location) + if !fromOk || !(toPackageOk || toLocationOk) { + log.Debugf("unable to find valid relationship mapping from SPDX 2.2 JSON, ignoring: (from: %+v) (to: %+v)", a, b) + continue + } + var to artifact.Identifiable + var typ artifact.RelationshipType + if toLocationOk { + if r.Relationship == string(ContainsRelationship) { + typ = artifact.ContainsRelationship + to = toLocation + } + } else { + switch RelationshipType(r.Relationship) { + case ContainsRelationship: + typ = artifact.ContainsRelationship + to = toPackage + case BuildDependencyOfRelationship: + typ = artifact.BuildDependencyOfRelationship + to = toPackage + case RuntimeDependencyOfRelationship: + typ = artifact.RuntimeDependencyOfRelationship + to = toPackage + case OtherRelationship: + // Encoding uses a specifically formatted comment... + if strings.Index(r.RelationshipComment, string(artifact.OwnershipByFileOverlapRelationship)) == 0 { + typ = artifact.RuntimeDependencyOfRelationship + to = toPackage + } + } + } + if typ != "" && to != nil { + out = append(out, artifact.Relationship{ + From: from, + To: to, + Type: typ, + }) + } + } + return out +} + +func toSyftCoordinates(f *spdx.File2_2) source.Coordinates { + const layerIDPrefix = "layerID: " + var fileSystemID string + if strings.Index(f.FileComment, layerIDPrefix) == 0 { + fileSystemID = strings.TrimPrefix(f.FileComment, layerIDPrefix) + } + if strings.Index(string(f.FileSPDXIdentifier), layerIDPrefix) == 0 { + fileSystemID = strings.TrimPrefix(string(f.FileSPDXIdentifier), layerIDPrefix) + } + return source.Coordinates{ + RealPath: f.FileName, + FileSystemID: fileSystemID, + } +} + +func toSyftLocation(f *spdx.File2_2) *source.Location { + return &source.Location{ + Coordinates: toSyftCoordinates(f), + VirtualPath: f.FileName, + } +} + +func requireAndTrimPrefix(val interface{}, prefix string) string { + if v, ok := val.(string); ok { + if i := strings.Index(v, prefix); i == 0 { + return strings.Replace(v, prefix, "", 1) + } + } + return "" +} + +type pkgInfo struct { + purl packageurl.PackageURL + typ pkg.Type + lang pkg.Language +} + +func (p *pkgInfo) qualifierValue(name string) string { + return findQualifierValue(p.purl, name) +} + +func findQualifierValue(purl packageurl.PackageURL, qualifier string) string { + for _, q := range purl.Qualifiers { + if q.Key == qualifier { + return q.Value + } + } + return "" +} + +func extractPkgInfo(p *spdx.Package2_2) pkgInfo { + pu := findPURLValue(p) + purl, err := packageurl.FromString(pu) + if err != nil { + return pkgInfo{} + } + return pkgInfo{ + purl, + pkg.TypeByName(purl.Type), + pkg.LanguageByName(purl.Type), + } +} + +func toSyftPackage(p *spdx.Package2_2) *pkg.Package { + info := extractPkgInfo(p) + metadataType, metadata := extractMetadata(p, info) + sP := pkg.Package{ + Type: info.typ, + Name: p.PackageName, + Version: p.PackageVersion, + Licenses: parseLicense(p.PackageLicenseDeclared), + CPEs: extractCPEs(p), + PURL: info.purl.String(), + Language: info.lang, + MetadataType: metadataType, + Metadata: metadata, + } + + sP.SetID() + + return &sP +} + +func extractMetadata(p *spdx.Package2_2, info pkgInfo) (pkg.MetadataType, interface{}) { + arch := info.qualifierValue(pkg.PURLQualifierArch) + upstreamValue := info.qualifierValue(pkg.PURLQualifierUpstream) + upstream := strings.SplitN(upstreamValue, "@", 2) + upstreamName := upstream[0] + upstreamVersion := "" + if len(upstream) > 1 { + upstreamVersion = upstream[1] + } + switch info.typ { + case pkg.ApkPkg: + return pkg.ApkMetadataType, pkg.ApkMetadata{ + Package: p.PackageName, + OriginPackage: upstreamName, + Maintainer: p.PackageSupplierPerson, + Version: p.PackageVersion, + License: p.PackageLicenseDeclared, + Architecture: arch, + URL: p.PackageHomePage, + Description: p.PackageDescription, + } + case pkg.RpmPkg: + converted, err := strconv.Atoi(info.qualifierValue(pkg.PURLQualifierEpoch)) + var epoch *int + if err != nil { + epoch = nil + } else { + epoch = &converted + } + license := p.PackageLicenseDeclared + if license == "" { + license = p.PackageLicenseConcluded + } + return pkg.RpmMetadataType, pkg.RpmMetadata{ + Name: p.PackageName, + Version: p.PackageVersion, + Epoch: epoch, + Arch: arch, + SourceRpm: upstreamValue, + License: license, + Vendor: p.PackageOriginatorOrganization, + } + case pkg.DebPkg: + return pkg.DpkgMetadataType, pkg.DpkgMetadata{ + Package: p.PackageName, + Source: upstreamName, + Version: p.PackageVersion, + SourceVersion: upstreamVersion, + Architecture: arch, + Maintainer: p.PackageOriginatorPerson, + } + case pkg.JavaPkg: + var digests []file.Digest + for algorithm, value := range p.PackageChecksums { + digests = append(digests, file.Digest{Algorithm: string(algorithm), Value: value.Value}) + } + return pkg.JavaMetadataType, pkg.JavaMetadata{ + ArchiveDigests: digests, + } + } + return pkg.UnknownMetadataType, nil +} + +func findPURLValue(p *spdx.Package2_2) string { + for _, r := range p.PackageExternalReferences { + if r.RefType == string(PurlExternalRefType) { + return r.Locator + } + } + return "" +} + +func extractCPEs(p *spdx.Package2_2) (cpes []pkg.CPE) { + for _, r := range p.PackageExternalReferences { + if r.RefType == string(Cpe23ExternalRefType) { + cpe, err := pkg.NewCPE(r.Locator) + if err != nil { + log.Warnf("unable to extract SPDX CPE=%q: %+v", r.Locator, err) + continue + } + cpes = append(cpes, cpe) + } + } + return cpes +} + +func parseLicense(l string) []string { + if l == NOASSERTION || l == NONE { + return nil + } + return strings.Split(l, " AND ") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/to_syft_model_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/to_syft_model_test.go new file mode 100644 index 0000000000000000000000000000000000000000..9f09b3da21811a5184fee95475e4061be53938e5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/spdxhelpers/to_syft_model_test.go @@ -0,0 +1,235 @@ +package spdxhelpers + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/spdx/tools-golang/spdx" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func TestToSyftModel(t *testing.T) { + sbom, err := ToSyftModel(&spdx.Document2_2{ + CreationInfo: &spdx.CreationInfo2_2{ + SPDXVersion: "1", + DataLicense: "GPL", + SPDXIdentifier: "id-doc-1", + DocumentName: "docName", + DocumentNamespace: "docNamespace", + ExternalDocumentReferences: nil, + LicenseListVersion: "", + CreatorPersons: nil, + CreatorOrganizations: nil, + CreatorTools: nil, + Created: "", + CreatorComment: "", + DocumentComment: "", + }, + Packages: map[spdx.ElementID]*spdx.Package2_2{ + "id-pkg-1": { + PackageName: "pkg-1", + PackageSPDXIdentifier: "id-pkg-1", + PackageVersion: "5.4.3", + PackageSupplierPerson: "", + PackageSupplierOrganization: "", + PackageLicenseDeclared: "", + PackageDescription: "", + PackageExternalReferences: []*spdx.PackageExternalReference2_2{ + { + Category: "SECURITY", + Locator: "cpe:2.3:a:pkg-1:pkg-1:5.4.3:*:*:*:*:*:*:*", + RefType: "cpe23Type", + }, + { + Category: "SECURITY", + Locator: "cpe:2.3:a:pkg_1:pkg_1:5.4.3:*:*:*:*:*:*:*", + RefType: "cpe23Type", + }, + { + Category: "PACKAGE_MANAGER", + Locator: "pkg:alpine/pkg-1@5.4.3?arch=x86_64&upstream=p1-origin&distro=alpine-3.10.9", + RefType: "purl", + }, + }, + Files: nil, + }, + "id-pkg-2": { + PackageName: "pkg-2", + PackageSPDXIdentifier: "id-pkg-2", + PackageVersion: "7.3.1", + PackageSupplierPerson: "", + PackageSupplierOrganization: "", + PackageLicenseDeclared: "", + PackageDescription: "", + PackageExternalReferences: []*spdx.PackageExternalReference2_2{ + { + Category: "SECURITY", + Locator: "cpe:2.3:a:pkg-2:pkg-2:7.3.1:*:*:*:*:*:*:*", + RefType: "cpe23Type", + }, + { + Category: "SECURITY", + Locator: "cpe:2.3:a:pkg_2:pkg_2:7.3.1:*:*:*:*:*:*:*", + RefType: "cpe23Type", + }, + { + Category: "SECURITY", + Locator: "cpe:2.3:a:pkg-2:pkg_2:7.3.1:*:*:*:*:*:*:*", + RefType: "cpe23Type", + }, + { + Category: "PACKAGE_MANAGER", + Locator: "pkg:deb/pkg-2@7.3.1?arch=x86_64&upstream=p2-origin@9.1.3&distro=debian-3.10.9", + RefType: "purl", + }, + }, + Files: nil, + }, + }, + UnpackagedFiles: map[spdx.ElementID]*spdx.File2_2{}, + Relationships: []*spdx.Relationship2_2{}, + }) + + assert.NoError(t, err) + + assert.NotNil(t, sbom) + + pkgs := sbom.Artifacts.PackageCatalog.Sorted() + + assert.Len(t, pkgs, 2) + + p1 := pkgs[0] + assert.Equal(t, p1.Name, "pkg-1") + assert.Equal(t, p1.MetadataType, pkg.ApkMetadataType) + p1meta := p1.Metadata.(pkg.ApkMetadata) + assert.Equal(t, p1meta.OriginPackage, "p1-origin") + assert.Len(t, p1.CPEs, 2) + + p2 := pkgs[1] + assert.Equal(t, p2.Name, "pkg-2") + assert.Equal(t, p2.MetadataType, pkg.DpkgMetadataType) + p2meta := p2.Metadata.(pkg.DpkgMetadata) + assert.Equal(t, p2meta.Source, "p2-origin") + assert.Equal(t, p2meta.SourceVersion, "9.1.3") + assert.Len(t, p2.CPEs, 3) +} + +func Test_extractMetadata(t *testing.T) { + oneTwoThreeFour := 1234 + tests := []struct { + pkg spdx.Package2_2 + metaType pkg.MetadataType + meta interface{} + }{ + { + pkg: spdx.Package2_2{ + PackageName: "SomeDebPkg", + PackageVersion: "43.1.235", + PackageExternalReferences: []*spdx.PackageExternalReference2_2{ + { + Category: "PACKAGE_MANAGER", + Locator: "pkg:deb/pkg-2@7.3.1?arch=x86_64&upstream=somedebpkg-origin@9.1.3&distro=debian-3.10.9", + RefType: "purl", + }, + }, + }, + metaType: pkg.DpkgMetadataType, + meta: pkg.DpkgMetadata{ + Package: "SomeDebPkg", + Source: "somedebpkg-origin", + Version: "43.1.235", + SourceVersion: "9.1.3", + Architecture: "x86_64", + }, + }, + { + pkg: spdx.Package2_2{ + PackageName: "SomeApkPkg", + PackageVersion: "3.2.9", + PackageExternalReferences: []*spdx.PackageExternalReference2_2{ + { + Category: "PACKAGE_MANAGER", + Locator: "pkg:alpine/pkg-2@7.3.1?arch=x86_64&upstream=apk-origin@9.1.3&distro=alpine-3.10.9", + RefType: "purl", + }, + }, + }, + metaType: pkg.ApkMetadataType, + meta: pkg.ApkMetadata{ + Package: "SomeApkPkg", + OriginPackage: "apk-origin", + Version: "3.2.9", + Architecture: "x86_64", + }, + }, + { + pkg: spdx.Package2_2{ + PackageName: "SomeRpmPkg", + PackageVersion: "13.2.79", + PackageExternalReferences: []*spdx.PackageExternalReference2_2{ + { + Category: "PACKAGE_MANAGER", + Locator: "pkg:rpm/pkg-2@7.3.1?arch=x86_64&epoch=1234&upstream=some-rpm-origin-1.16.3&distro=alpine-3.10.9", + RefType: "purl", + }, + }, + }, + metaType: pkg.RpmMetadataType, + meta: pkg.RpmMetadata{ + Name: "SomeRpmPkg", + Version: "13.2.79", + Epoch: &oneTwoThreeFour, + Arch: "x86_64", + Release: "", + SourceRpm: "some-rpm-origin-1.16.3", + }, + }, + } + + for _, test := range tests { + t.Run(test.pkg.PackageName, func(t *testing.T) { + info := extractPkgInfo(&test.pkg) + metaType, meta := extractMetadata(&test.pkg, info) + assert.Equal(t, test.metaType, metaType) + assert.EqualValues(t, test.meta, meta) + }) + } +} + +func TestExtractSourceFromNamespaces(t *testing.T) { + tests := []struct { + namespace string + expected source.Scheme + }{ + { + namespace: "https://anchore.com/syft/file/d42b01d0-7325-409b-b03f-74082935c4d3", + expected: source.FileScheme, + }, + { + namespace: "https://anchore.com/syft/image/d42b01d0-7325-409b-b03f-74082935c4d3", + expected: source.ImageScheme, + }, + { + namespace: "https://anchore.com/syft/dir/d42b01d0-7325-409b-b03f-74082935c4d3", + expected: source.DirectoryScheme, + }, + { + namespace: "https://another-host/blob/123", + expected: source.UnknownScheme, + }, + { + namespace: "bla bla", + expected: source.UnknownScheme, + }, + { + namespace: "", + expected: source.UnknownScheme, + }, + } + + for _, tt := range tests { + require.Equal(t, tt.expected, extractSchemeFromNamespace(tt.namespace)) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/common/testutils/utils.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/testutils/utils.go new file mode 100644 index 0000000000000000000000000000000000000000..b1004d506fb88b9ac6d23f55e2f2b6fc8ad656f3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/common/testutils/utils.go @@ -0,0 +1,277 @@ +package testutils + +import ( + "bytes" + "strings" + "testing" + + "github.com/anchore/go-testutils" + "github.com/anchore/stereoscope/pkg/filetree" + "github.com/anchore/stereoscope/pkg/image" + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" + "github.com/sergi/go-diff/diffmatchpatch" + "github.com/stretchr/testify/assert" +) + +type redactor func(s []byte) []byte + +type imageCfg struct { + fromSnapshot bool +} + +type ImageOption func(cfg *imageCfg) + +func FromSnapshot() ImageOption { + return func(cfg *imageCfg) { + cfg.fromSnapshot = true + } +} + +func AssertEncoderAgainstGoldenImageSnapshot(t *testing.T, format sbom.Format, sbom sbom.SBOM, testImage string, updateSnapshot bool, redactors ...redactor) { + var buffer bytes.Buffer + + // grab the latest image contents and persist + if updateSnapshot { + imagetest.UpdateGoldenFixtureImage(t, testImage) + } + + err := format.Encode(&buffer, sbom) + assert.NoError(t, err) + actual := buffer.Bytes() + + // replace the expected snapshot contents with the current encoder contents + if updateSnapshot { + testutils.UpdateGoldenFileContents(t, actual) + } + + var expected = testutils.GetGoldenFileContents(t) + + // remove dynamic values, which should be tested independently + redactors = append(redactors, carriageRedactor) + for _, r := range redactors { + actual = r(actual) + expected = r(expected) + } + + // assert that the golden file snapshot matches the actual contents + if !bytes.Equal(expected, actual) { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(string(expected), string(actual), true) + t.Errorf("mismatched output:\n%s", dmp.DiffPrettyText(diffs)) + } +} + +func AssertEncoderAgainstGoldenSnapshot(t *testing.T, format sbom.Format, sbom sbom.SBOM, updateSnapshot bool, redactors ...redactor) { + var buffer bytes.Buffer + + err := format.Encode(&buffer, sbom) + assert.NoError(t, err) + actual := buffer.Bytes() + + // replace the expected snapshot contents with the current encoder contents + if updateSnapshot { + testutils.UpdateGoldenFileContents(t, actual) + } + + var expected = testutils.GetGoldenFileContents(t) + + // remove dynamic values, which should be tested independently + redactors = append(redactors, carriageRedactor) + for _, r := range redactors { + actual = r(actual) + expected = r(expected) + } + + if !bytes.Equal(expected, actual) { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(string(expected), string(actual), true) + t.Logf("len: %d\nexpected: %s", len(expected), expected) + t.Logf("len: %d\nactual: %s", len(actual), actual) + t.Errorf("mismatched output:\n%s", dmp.DiffPrettyText(diffs)) + } +} + +func ImageInput(t testing.TB, testImage string, options ...ImageOption) sbom.SBOM { + t.Helper() + catalog := pkg.NewCatalog() + var cfg imageCfg + var img *image.Image + for _, opt := range options { + opt(&cfg) + } + + switch cfg.fromSnapshot { + case true: + img = imagetest.GetGoldenFixtureImage(t, testImage) + default: + img = imagetest.GetFixtureImage(t, "docker-archive", testImage) + } + + populateImageCatalog(catalog, img) + + // this is a hard coded value that is not given by the fixture helper and must be provided manually + img.Metadata.ManifestDigest = "sha256:2731251dc34951c0e50fcc643b4c5f74922dad1a5d98f302b504cf46cd5d9368" + + src, err := source.NewFromImage(img, "user-image-input") + assert.NoError(t, err) + + return sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: catalog, + LinuxDistribution: &linux.Release{ + PrettyName: "debian", + Name: "debian", + ID: "debian", + IDLike: []string{"like!"}, + Version: "1.2.3", + VersionID: "1.2.3", + }, + }, + Source: src.Metadata, + Descriptor: sbom.Descriptor{ + Name: "syft", + Version: "v0.42.0-bogus", + // the application configuration should be persisted here, however, we do not want to import + // the application configuration in this package (it's reserved only for ingestion by the cmd package) + Configuration: map[string]string{ + "config-key": "config-value", + }, + }, + } +} + +func carriageRedactor(s []byte) []byte { + msg := strings.ReplaceAll(string(s), "\r\n", "\n") + return []byte(msg) +} + +func populateImageCatalog(catalog *pkg.Catalog, img *image.Image) { + _, ref1, _ := img.SquashedTree().File("/somefile-1.txt", filetree.FollowBasenameLinks) + _, ref2, _ := img.SquashedTree().File("/somefile-2.txt", filetree.FollowBasenameLinks) + + // populate catalog with test data + catalog.Add(pkg.Package{ + Name: "package-1", + Version: "1.0.1", + Locations: source.NewLocationSet( + source.NewLocationFromImage(string(ref1.RealPath), *ref1, img), + ), + Type: pkg.PythonPkg, + FoundBy: "the-cataloger-1", + Language: pkg.Python, + MetadataType: pkg.PythonPackageMetadataType, + Licenses: []string{"MIT"}, + Metadata: pkg.PythonPackageMetadata{ + Name: "package-1", + Version: "1.0.1", + }, + PURL: "a-purl-1", // intentionally a bad pURL for test fixtures + CPEs: []pkg.CPE{ + pkg.MustCPE("cpe:2.3:*:some:package:1:*:*:*:*:*:*:*"), + }, + }) + catalog.Add(pkg.Package{ + Name: "package-2", + Version: "2.0.1", + Locations: source.NewLocationSet( + source.NewLocationFromImage(string(ref2.RealPath), *ref2, img), + ), + Type: pkg.DebPkg, + FoundBy: "the-cataloger-2", + MetadataType: pkg.DpkgMetadataType, + Metadata: pkg.DpkgMetadata{ + Package: "package-2", + Version: "2.0.1", + }, + PURL: "pkg:deb/debian/package-2@2.0.1", + CPEs: []pkg.CPE{ + pkg.MustCPE("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"), + }, + }) +} + +func DirectoryInput(t testing.TB) sbom.SBOM { + catalog := newDirectoryCatalog() + + src, err := source.NewFromDirectory("/some/path") + assert.NoError(t, err) + + return sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: catalog, + LinuxDistribution: &linux.Release{ + PrettyName: "debian", + Name: "debian", + ID: "debian", + IDLike: []string{"like!"}, + Version: "1.2.3", + VersionID: "1.2.3", + }, + }, + Source: src.Metadata, + Descriptor: sbom.Descriptor{ + Name: "syft", + Version: "v0.42.0-bogus", + // the application configuration should be persisted here, however, we do not want to import + // the application configuration in this package (it's reserved only for ingestion by the cmd package) + Configuration: map[string]string{ + "config-key": "config-value", + }, + }, + } +} + +func newDirectoryCatalog() *pkg.Catalog { + catalog := pkg.NewCatalog() + + // populate catalog with test data + catalog.Add(pkg.Package{ + Name: "package-1", + Version: "1.0.1", + Type: pkg.PythonPkg, + FoundBy: "the-cataloger-1", + Locations: source.NewLocationSet( + source.NewLocation("/some/path/pkg1"), + ), + Language: pkg.Python, + MetadataType: pkg.PythonPackageMetadataType, + Licenses: []string{"MIT"}, + Metadata: pkg.PythonPackageMetadata{ + Name: "package-1", + Version: "1.0.1", + Files: []pkg.PythonFileRecord{ + { + Path: "/some/path/pkg1/dependencies/foo", + }, + }, + }, + PURL: "a-purl-2", // intentionally a bad pURL for test fixtures + CPEs: []pkg.CPE{ + pkg.MustCPE("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"), + }, + }) + catalog.Add(pkg.Package{ + Name: "package-2", + Version: "2.0.1", + Type: pkg.DebPkg, + FoundBy: "the-cataloger-2", + Locations: source.NewLocationSet( + source.NewLocation("/some/path/pkg1"), + ), + MetadataType: pkg.DpkgMetadataType, + Metadata: pkg.DpkgMetadata{ + Package: "package-2", + Version: "2.0.1", + }, + PURL: "pkg:deb/debian/package-2@2.0.1", + CPEs: []pkg.CPE{ + pkg.MustCPE("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"), + }, + }) + + return catalog +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/decoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/decoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e561ff13757d036e5733bf9cead5134abf11cd2c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/decoder_test.go @@ -0,0 +1,70 @@ +package cyclonedxjson + +import ( + "fmt" + "os" + "strings" + "testing" + + "github.com/stretchr/testify/assert" +) + +func Test_decodeJSON(t *testing.T) { + tests := []struct { + file string + err bool + distro string + packages []string + }{ + { + file: "snapshot/TestCycloneDxDirectoryEncoder.golden", + distro: "debian:1.2.3", + packages: []string{"package-1:1.0.1", "package-2:2.0.1"}, + }, + { + file: "snapshot/TestCycloneDxImageEncoder.golden", + distro: "debian:1.2.3", + packages: []string{"package-1:1.0.1", "package-2:2.0.1"}, + }, + { + file: "image-simple/Dockerfile", + err: true, + }, + } + for _, test := range tests { + t.Run(test.file, func(t *testing.T) { + reader, err := os.Open("test-fixtures/" + test.file) + assert.NoError(t, err) + + if test.err { + err = Format().Validate(reader) + assert.Error(t, err) + return + } + + bom, err := Format().Decode(reader) + + assert.NoError(t, err) + + split := strings.SplitN(test.distro, ":", 2) + name := split[0] + version := split[1] + assert.Equal(t, bom.Artifacts.LinuxDistribution.ID, name) + assert.Equal(t, bom.Artifacts.LinuxDistribution.Version, version) + + pkgs: + for _, pkg := range test.packages { + split = strings.SplitN(pkg, ":", 2) + name = split[0] + version = split[1] + for p := range bom.Artifacts.PackageCatalog.Enumerate() { + if p.Name == name { + assert.Equal(t, version, p.Version) + continue pkgs + } + } + assert.Fail(t, fmt.Sprintf("package should be present: %s", pkg)) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..aa83029152618483bdb505be7d1827cf492c82fe --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/encoder.go @@ -0,0 +1,18 @@ +package cyclonedxjson + +import ( + "io" + + "github.com/CycloneDX/cyclonedx-go" + "github.com/anchore/syft/internal/formats/common/cyclonedxhelpers" + "github.com/anchore/syft/syft/sbom" +) + +func encoder(output io.Writer, s sbom.SBOM) error { + bom := cyclonedxhelpers.ToFormatModel(s) + enc := cyclonedx.NewBOMEncoder(output, cyclonedx.BOMFileFormatJSON) + enc.SetPretty(true) + + err := enc.Encode(bom) + return err +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..06ad8293c44a477570458eef244597d79f6a645b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/encoder_test.go @@ -0,0 +1,44 @@ +package cyclonedxjson + +import ( + "flag" + "regexp" + "testing" + + "github.com/anchore/syft/internal/formats/common/testutils" +) + +var updateCycloneDx = flag.Bool("update-cyclonedx", false, "update the *.golden files for cyclone-dx encoders") + +func TestCycloneDxDirectoryEncoder(t *testing.T) { + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + testutils.DirectoryInput(t), + *updateCycloneDx, + cycloneDxRedactor, + ) +} + +func TestCycloneDxImageEncoder(t *testing.T) { + testImage := "image-simple" + testutils.AssertEncoderAgainstGoldenImageSnapshot(t, + Format(), + testutils.ImageInput(t, testImage), + testImage, + *updateCycloneDx, + cycloneDxRedactor, + ) +} + +func cycloneDxRedactor(s []byte) []byte { + serialPattern := regexp.MustCompile(`urn:uuid:[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}`) + rfc3339Pattern := regexp.MustCompile(`([0-9]+)-(0[1-9]|1[012])-(0[1-9]|[12][0-9]|3[01])[Tt]([01][0-9]|2[0-3]):([0-5][0-9]):([0-5][0-9]|60)(\.[0-9]+)?(([Zz])|([\+|\-]([01][0-9]|2[0-3]):[0-5][0-9]))`) + sha256Pattern := regexp.MustCompile(`sha256:[A-Fa-f0-9]{64}`) + for _, pattern := range []*regexp.Regexp{serialPattern, rfc3339Pattern, sha256Pattern} { + s = pattern.ReplaceAll(s, []byte("redacted")) + } + // the bom-ref will be autogenerated every time, the value here should not be directly tested in snapshot tests + s = regexp.MustCompile(` "bom-ref": .*\n`).ReplaceAll(s, []byte("")) + + return s +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/format.go new file mode 100644 index 0000000000000000000000000000000000000000..9802120919bb16eb308d6ef409e7f958046704db --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/format.go @@ -0,0 +1,18 @@ +package cyclonedxjson + +import ( + "github.com/CycloneDX/cyclonedx-go" + "github.com/anchore/syft/internal/formats/common/cyclonedxhelpers" + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "cyclonedx-1-json" + +func Format() sbom.Format { + return sbom.NewFormat( + ID, + encoder, + cyclonedxhelpers.GetDecoder(cyclonedx.BOMFileFormatJSON), + cyclonedxhelpers.GetValidator(cyclonedx.BOMFileFormatJSON), + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/Dockerfile b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..79cfa759e357be9628894dea6332a0e6a2c33bb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/Dockerfile @@ -0,0 +1,4 @@ +# Note: changes to this file will result in updating several test values. Consider making a new image fixture instead of editing this one. +FROM scratch +ADD file-1.txt /somefile-1.txt +ADD file-2.txt /somefile-2.txt diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/file-1.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..985d3408e98cb9f41c01376c698451fdef0e4b32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/file-1.txt @@ -0,0 +1 @@ +this file has contents \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/file-2.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..396d08bbc72f810ec6d057d1713a84a75d1cd542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/image-simple/file-2.txt @@ -0,0 +1 @@ +file-2 contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/TestCycloneDxDirectoryEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/TestCycloneDxDirectoryEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..3b23a84e5165dbf61701cce828057339780271a0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/TestCycloneDxDirectoryEncoder.golden @@ -0,0 +1,119 @@ +{ + "bomFormat": "CycloneDX", + "specVersion": "1.4", + "serialNumber": "urn:uuid:3ea3363f-3945-4859-9ba1-9a395983d248", + "version": 1, + "metadata": { + "timestamp": "2022-05-23T12:05:00-07:00", + "tools": [ + { + "vendor": "anchore", + "name": "syft", + "version": "v0.42.0-bogus" + } + ], + "component": { + "bom-ref": "163686ac6e30c752", + "type": "file", + "name": "/some/path" + } + }, + "components": [ + { + "bom-ref": "b85dbb4e6ece5082", + "type": "library", + "name": "package-1", + "version": "1.0.1", + "licenses": [ + { + "license": { + "id": "MIT" + } + } + ], + "cpe": "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*", + "purl": "a-purl-2", + "properties": [ + { + "name": "syft:package:foundBy", + "value": "the-cataloger-1" + }, + { + "name": "syft:package:language", + "value": "python" + }, + { + "name": "syft:package:metadataType", + "value": "PythonPackageMetadata" + }, + { + "name": "syft:package:type", + "value": "python" + }, + { + "name": "syft:location:0:path", + "value": "/some/path/pkg1" + } + ] + }, + { + "bom-ref": "pkg:deb/debian/package-2@2.0.1?package-id=ceda99598967ae8d", + "type": "library", + "name": "package-2", + "version": "2.0.1", + "cpe": "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*", + "purl": "pkg:deb/debian/package-2@2.0.1", + "properties": [ + { + "name": "syft:package:foundBy", + "value": "the-cataloger-2" + }, + { + "name": "syft:package:metadataType", + "value": "DpkgMetadata" + }, + { + "name": "syft:package:type", + "value": "deb" + }, + { + "name": "syft:location:0:path", + "value": "/some/path/pkg1" + }, + { + "name": "syft:metadata:installedSize", + "value": "0" + } + ] + }, + { + "type": "operating-system", + "name": "debian", + "version": "1.2.3", + "description": "debian", + "swid": { + "tagId": "debian", + "name": "debian", + "version": "1.2.3" + }, + "properties": [ + { + "name": "syft:distro:id", + "value": "debian" + }, + { + "name": "syft:distro:idLike:0", + "value": "like!" + }, + { + "name": "syft:distro:prettyName", + "value": "debian" + }, + { + "name": "syft:distro:versionID", + "value": "1.2.3" + } + ] + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/TestCycloneDxImageEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/TestCycloneDxImageEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..6dac17e18d554a358287419308946f4989f2c6e9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/TestCycloneDxImageEncoder.golden @@ -0,0 +1,128 @@ +{ + "bomFormat": "CycloneDX", + "specVersion": "1.4", + "serialNumber": "urn:uuid:c825402b-bbfa-4ad5-81b1-6a8332a6a8b6", + "version": 1, + "metadata": { + "timestamp": "2022-05-23T12:05:01-07:00", + "tools": [ + { + "vendor": "anchore", + "name": "syft", + "version": "v0.42.0-bogus" + } + ], + "component": { + "bom-ref": "e779c1ed804ba529", + "type": "container", + "name": "user-image-input", + "version": "sha256:2731251dc34951c0e50fcc643b4c5f74922dad1a5d98f302b504cf46cd5d9368" + } + }, + "components": [ + { + "bom-ref": "2a46171f91c8d4bc", + "type": "library", + "name": "package-1", + "version": "1.0.1", + "licenses": [ + { + "license": { + "id": "MIT" + } + } + ], + "cpe": "cpe:2.3:*:some:package:1:*:*:*:*:*:*:*", + "purl": "a-purl-1", + "properties": [ + { + "name": "syft:package:foundBy", + "value": "the-cataloger-1" + }, + { + "name": "syft:package:language", + "value": "python" + }, + { + "name": "syft:package:metadataType", + "value": "PythonPackageMetadata" + }, + { + "name": "syft:package:type", + "value": "python" + }, + { + "name": "syft:location:0:layerID", + "value": "sha256:cd8f3884f1211d65c19ce5bbc5174bcd2ce8ba96b63e5b3693969a53279c4405" + }, + { + "name": "syft:location:0:path", + "value": "/somefile-1.txt" + } + ] + }, + { + "bom-ref": "pkg:deb/debian/package-2@2.0.1?package-id=ae77680e9b1d087e", + "type": "library", + "name": "package-2", + "version": "2.0.1", + "cpe": "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*", + "purl": "pkg:deb/debian/package-2@2.0.1", + "properties": [ + { + "name": "syft:package:foundBy", + "value": "the-cataloger-2" + }, + { + "name": "syft:package:metadataType", + "value": "DpkgMetadata" + }, + { + "name": "syft:package:type", + "value": "deb" + }, + { + "name": "syft:location:0:layerID", + "value": "sha256:42d2ea51c688e6dc7be81a305acbe006d27a6ef0c26ae3888fd0d4ce44f69265" + }, + { + "name": "syft:location:0:path", + "value": "/somefile-2.txt" + }, + { + "name": "syft:metadata:installedSize", + "value": "0" + } + ] + }, + { + "type": "operating-system", + "name": "debian", + "version": "1.2.3", + "description": "debian", + "swid": { + "tagId": "debian", + "name": "debian", + "version": "1.2.3" + }, + "properties": [ + { + "name": "syft:distro:id", + "value": "debian" + }, + { + "name": "syft:distro:idLike:0", + "value": "like!" + }, + { + "name": "syft:distro:prettyName", + "value": "debian" + }, + { + "name": "syft:distro:versionID", + "value": "1.2.3" + } + ] + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden new file mode 100644 index 0000000000000000000000000000000000000000..3d93b6d3ad1c86098e440073bcf8cfdf5eea53e1 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxjson/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden differ diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/decoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/decoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..7a6643339952c34fda91603c0f15916084c442d0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/decoder_test.go @@ -0,0 +1,70 @@ +package cyclonedxxml + +import ( + "fmt" + "os" + "strings" + "testing" + + "github.com/stretchr/testify/assert" +) + +func Test_decodeXML(t *testing.T) { + tests := []struct { + file string + err bool + distro string + packages []string + }{ + { + file: "snapshot/TestCycloneDxDirectoryEncoder.golden", + distro: "debian:1.2.3", + packages: []string{"package-1:1.0.1", "package-2:2.0.1"}, + }, + { + file: "snapshot/TestCycloneDxImageEncoder.golden", + distro: "debian:1.2.3", + packages: []string{"package-1:1.0.1", "package-2:2.0.1"}, + }, + { + file: "image-simple/Dockerfile", + err: true, + }, + } + for _, test := range tests { + t.Run(test.file, func(t *testing.T) { + reader, err := os.Open("test-fixtures/" + test.file) + assert.NoError(t, err) + + if test.err { + err = Format().Validate(reader) + assert.Error(t, err) + return + } + + bom, err := Format().Decode(reader) + + assert.NoError(t, err) + + split := strings.SplitN(test.distro, ":", 2) + name := split[0] + version := split[1] + assert.Equal(t, bom.Artifacts.LinuxDistribution.ID, name) + assert.Equal(t, bom.Artifacts.LinuxDistribution.Version, version) + + pkgs: + for _, pkg := range test.packages { + split = strings.SplitN(pkg, ":", 2) + name = split[0] + version = split[1] + for p := range bom.Artifacts.PackageCatalog.Enumerate() { + if p.Name == name { + assert.Equal(t, version, p.Version) + continue pkgs + } + } + assert.Fail(t, fmt.Sprintf("package should be present: %s", pkg)) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..315fcd0c2ee9e060297a49a3845f0e6f32d9b926 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/encoder.go @@ -0,0 +1,18 @@ +package cyclonedxxml + +import ( + "io" + + "github.com/CycloneDX/cyclonedx-go" + "github.com/anchore/syft/internal/formats/common/cyclonedxhelpers" + "github.com/anchore/syft/syft/sbom" +) + +func encoder(output io.Writer, s sbom.SBOM) error { + bom := cyclonedxhelpers.ToFormatModel(s) + enc := cyclonedx.NewBOMEncoder(output, cyclonedx.BOMFileFormatXML) + enc.SetPretty(true) + + err := enc.Encode(bom) + return err +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..5c4129aa74a115904fd9c32506b4f854c25f11e9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/encoder_test.go @@ -0,0 +1,50 @@ +package cyclonedxxml + +import ( + "flag" + "regexp" + "testing" + + "github.com/anchore/syft/internal/formats/common/testutils" +) + +var updateCycloneDx = flag.Bool("update-cyclonedx", false, "update the *.golden files for cyclone-dx encoders") + +func TestCycloneDxDirectoryEncoder(t *testing.T) { + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + testutils.DirectoryInput(t), + *updateCycloneDx, + cycloneDxRedactor, + ) +} + +func TestCycloneDxImageEncoder(t *testing.T) { + testImage := "image-simple" + testutils.AssertEncoderAgainstGoldenImageSnapshot(t, + Format(), + testutils.ImageInput(t, testImage), + testImage, + *updateCycloneDx, + cycloneDxRedactor, + ) +} + +func cycloneDxRedactor(s []byte) []byte { + serialPattern := regexp.MustCompile(`serialNumber="[a-zA-Z0-9\-:]+"`) + rfc3339Pattern := regexp.MustCompile(`([0-9]+)-(0[1-9]|1[012])-(0[1-9]|[12][0-9]|3[01])[Tt]([01][0-9]|2[0-3]):([0-5][0-9]):([0-5][0-9]|60)(\.[0-9]+)?(([Zz])|([\+|\-]([01][0-9]|2[0-3]):[0-5][0-9]))`) + sha256Pattern := regexp.MustCompile(`sha256:[A-Fa-f0-9]{64}`) + + for _, pattern := range []*regexp.Regexp{serialPattern, rfc3339Pattern, sha256Pattern} { + s = pattern.ReplaceAll(s, []byte("redacted")) + } + + // the bom-ref will be autogenerated every time, the value here should not be directly tested in snapshot tests + bomRefPattern := regexp.MustCompile(` bom-ref="[a-zA-Z0-9\-:]+"`) + bomRef3339Pattern := regexp.MustCompile(`([0-9]+)-(0[1-9]|1[012])-(0[1-9]|[12][0-9]|3[01])[Tt]([01][0-9]|2[0-3]):([0-5][0-9]):([0-5][0-9]|60)(\.[0-9]+)?(([Zz])|([\+|\-]([01][0-9]|2[0-3]):[0-5][0-9]))`) + for _, pattern := range []*regexp.Regexp{bomRefPattern, bomRef3339Pattern} { + s = pattern.ReplaceAll(s, []byte("")) + } + + return s +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/format.go new file mode 100644 index 0000000000000000000000000000000000000000..07ac3ad297fbcb8a95796fccfdd84f34bfbb1e50 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/format.go @@ -0,0 +1,18 @@ +package cyclonedxxml + +import ( + "github.com/CycloneDX/cyclonedx-go" + "github.com/anchore/syft/internal/formats/common/cyclonedxhelpers" + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "cyclonedx-1-xml" + +func Format() sbom.Format { + return sbom.NewFormat( + ID, + encoder, + cyclonedxhelpers.GetDecoder(cyclonedx.BOMFileFormatXML), + cyclonedxhelpers.GetValidator(cyclonedx.BOMFileFormatXML), + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/Dockerfile b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..79cfa759e357be9628894dea6332a0e6a2c33bb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/Dockerfile @@ -0,0 +1,4 @@ +# Note: changes to this file will result in updating several test values. Consider making a new image fixture instead of editing this one. +FROM scratch +ADD file-1.txt /somefile-1.txt +ADD file-2.txt /somefile-2.txt diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/file-1.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..985d3408e98cb9f41c01376c698451fdef0e4b32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/file-1.txt @@ -0,0 +1 @@ +this file has contents \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/file-2.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..396d08bbc72f810ec6d057d1713a84a75d1cd542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/image-simple/file-2.txt @@ -0,0 +1 @@ +file-2 contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/TestCycloneDxDirectoryEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/TestCycloneDxDirectoryEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..7505cd83b93a02752afbed7c913cb63b0138a8a0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/TestCycloneDxDirectoryEncoder.golden @@ -0,0 +1,61 @@ + + + + 2022-05-23T12:02:41-07:00 + + + anchore + syft + v0.42.0-bogus + + + + /some/path + + + + + package-1 + 1.0.1 + + + MIT + + + cpe:2.3:*:some:package:2:*:*:*:*:*:*:* + a-purl-2 + + the-cataloger-1 + python + PythonPackageMetadata + python + /some/path/pkg1 + + + + package-2 + 2.0.1 + cpe:2.3:*:some:package:2:*:*:*:*:*:*:* + pkg:deb/debian/package-2@2.0.1 + + the-cataloger-2 + DpkgMetadata + deb + /some/path/pkg1 + 0 + + + + debian + 1.2.3 + debian + + + debian + like! + debian + 1.2.3 + + + + \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/TestCycloneDxImageEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/TestCycloneDxImageEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..6ef8367e66a6a2909c2570be12b79a8e3a657311 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/TestCycloneDxImageEncoder.golden @@ -0,0 +1,64 @@ + + + + 2022-05-23T12:02:42-07:00 + + + anchore + syft + v0.42.0-bogus + + + + user-image-input + sha256:2731251dc34951c0e50fcc643b4c5f74922dad1a5d98f302b504cf46cd5d9368 + + + + + package-1 + 1.0.1 + + + MIT + + + cpe:2.3:*:some:package:1:*:*:*:*:*:*:* + a-purl-1 + + the-cataloger-1 + python + PythonPackageMetadata + python + sha256:cd8f3884f1211d65c19ce5bbc5174bcd2ce8ba96b63e5b3693969a53279c4405 + /somefile-1.txt + + + + package-2 + 2.0.1 + cpe:2.3:*:some:package:2:*:*:*:*:*:*:* + pkg:deb/debian/package-2@2.0.1 + + the-cataloger-2 + DpkgMetadata + deb + sha256:42d2ea51c688e6dc7be81a305acbe006d27a6ef0c26ae3888fd0d4ce44f69265 + /somefile-2.txt + 0 + + + + debian + 1.2.3 + debian + + + debian + like! + debian + 1.2.3 + + + + \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden new file mode 100644 index 0000000000000000000000000000000000000000..3d93b6d3ad1c86098e440073bcf8cfdf5eea53e1 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/internal/formats/cyclonedxxml/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden differ diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/github/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/github/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..6a2b2b66bed8d69f267b83e9cca513b7b5fadbcf --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/github/encoder.go @@ -0,0 +1,184 @@ +package github + +import ( + "fmt" + "strings" + "time" + + "github.com/mholt/archiver/v3" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" +) + +// toGithubModel converts the provided SBOM to a GitHub dependency model +func toGithubModel(s *sbom.SBOM) DependencySnapshot { + scanTime := time.Now().Format(time.RFC3339) // TODO is there a record of this somewhere? + v := s.Descriptor.Version + if v == "[not provided]" || v == "" { + v = "0.0.0-dev" + } + return DependencySnapshot{ + Version: 0, + // TODO allow property input to specify the Job, Sha, and Ref + Detector: DetectorMetadata{ + Name: internal.ApplicationName, + URL: "https://github.com/anchore/syft", + Version: v, + }, + Metadata: toSnapshotMetadata(s), + Manifests: toGithubManifests(s), + Scanned: scanTime, + } +} + +// toSnapshotMetadata captures the linux distribution information and other metadata +func toSnapshotMetadata(s *sbom.SBOM) Metadata { + out := Metadata{} + + if s.Artifacts.LinuxDistribution != nil { + d := s.Artifacts.LinuxDistribution + qualifiers := packageurl.Qualifiers{} + if len(d.IDLike) > 0 { + qualifiers = append(qualifiers, packageurl.Qualifier{ + Key: "like", + Value: strings.Join(d.IDLike, ","), + }) + } + purl := packageurl.NewPackageURL("generic", "", d.ID, d.VersionID, qualifiers, "") + out["syft:distro"] = purl.ToString() + } + + return out +} + +func filesystem(p pkg.Package) string { + locations := p.Locations.ToSlice() + if len(locations) > 0 { + return locations[0].FileSystemID + } + return "" +} + +// isArchive returns true if the path appears to be an archive +func isArchive(path string) bool { + _, err := archiver.ByExtension(path) + return err == nil +} + +// toPath Generates a string representation of the package location, optionally including the layer hash +func toPath(s source.Metadata, p pkg.Package) string { + inputPath := strings.TrimPrefix(s.Path, "./") + if inputPath == "." { + inputPath = "" + } + locations := p.Locations.ToSlice() + if len(locations) > 0 { + location := locations[0] + packagePath := location.RealPath + if location.VirtualPath != "" { + packagePath = location.VirtualPath + } + packagePath = strings.TrimPrefix(packagePath, "/") + switch s.Scheme { + case source.ImageScheme: + image := strings.ReplaceAll(s.ImageMetadata.UserInput, ":/", "//") + return fmt.Sprintf("%s:/%s", image, packagePath) + case source.FileScheme: + if isArchive(inputPath) { + return fmt.Sprintf("%s:/%s", inputPath, packagePath) + } + return inputPath + case source.DirectoryScheme: + if inputPath != "" { + return fmt.Sprintf("%s/%s", inputPath, packagePath) + } + return packagePath + } + } + return fmt.Sprintf("%s%s", inputPath, s.ImageMetadata.UserInput) +} + +// toGithubManifests manifests, each of which represents a specific location that has dependencies +func toGithubManifests(s *sbom.SBOM) Manifests { + manifests := map[string]*Manifest{} + + for _, p := range s.Artifacts.PackageCatalog.Sorted() { + path := toPath(s.Source, p) + manifest, ok := manifests[path] + if !ok { + manifest = &Manifest{ + Name: path, + File: FileInfo{ + SourceLocation: path, + }, + Resolved: DependencyGraph{}, + } + fs := filesystem(p) + if fs != "" { + manifest.Metadata = Metadata{ + "syft:filesystem": fs, + } + } + manifests[path] = manifest + } + + name := dependencyName(p) + manifest.Resolved[name] = DependencyNode{ + PackageURL: p.PURL, + Metadata: toDependencyMetadata(p), + Relationship: toDependencyRelationshipType(p), + Scope: toDependencyScope(p), + Dependencies: toDependencies(s, p), + } + } + + out := Manifests{} + for k, v := range manifests { + out[k] = *v + } + return out +} + +// dependencyName to make things a little nicer to read; this might end up being lossy +func dependencyName(p pkg.Package) string { + purl, err := packageurl.FromString(p.PURL) + if err != nil { + log.Warnf("Invalid PURL for package: '%s' PURL: '%s' (%w)", p.Name, p.PURL, err) + return "" + } + // don't use qualifiers for this + purl.Qualifiers = nil + return purl.ToString() +} + +func toDependencyScope(_ pkg.Package) DependencyScope { + return DependencyScopeRuntime +} + +func toDependencyRelationshipType(_ pkg.Package) DependencyRelationship { + return DependencyRelationshipDirect +} + +func toDependencyMetadata(_ pkg.Package) Metadata { + // We have limited properties: up to 8 with reasonably small values + // For now, we are encoding the location as part of the key, we are encoding PURLs with most + // of the other information Grype might need; and the distro information at the top level + // so we don't need anything here yet + return Metadata{} +} + +func toDependencies(s *sbom.SBOM, p pkg.Package) (out []string) { + for _, r := range s.Relationships { + if r.From.ID() == p.ID() { + if p, ok := r.To.(pkg.Package); ok { + out = append(out, dependencyName(p)) + } + } + } + return +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/github/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/github/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..3eb58c7557139579de71cc0684a0c8c0fe36a072 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/github/encoder_test.go @@ -0,0 +1,167 @@ +package github + +import ( + "encoding/json" + "testing" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" +) + +func Test_toGithubModel(t *testing.T) { + s := sbom.SBOM{ + Source: source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: source.ImageMetadata{ + UserInput: "ubuntu:18.04", + Architecture: "amd64", + }, + }, + Artifacts: sbom.Artifacts{ + LinuxDistribution: &linux.Release{ + ID: "ubuntu", + VersionID: "18.04", + IDLike: []string{"debian"}, + }, + PackageCatalog: pkg.NewCatalog(), + }, + } + for _, p := range []pkg.Package{ + { + Name: "pkg-1", + Version: "1.0.1", + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/usr/lib", + FileSystemID: "fsid-1", + }, + }, + ), + }, + { + Name: "pkg-2", + Version: "2.0.2", + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/usr/lib", + FileSystemID: "fsid-1", + }, + }, + ), + }, + { + Name: "pkg-3", + Version: "3.0.3", + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/etc", + FileSystemID: "fsid-1", + }, + }, + ), + }, + } { + p.PURL = packageurl.NewPackageURL( + "generic", + "", + p.Name, + p.Version, + nil, + "", + ).ToString() + s.Artifacts.PackageCatalog.Add(p) + } + + actual := toGithubModel(&s) + + expected := DependencySnapshot{ + Version: 0, + Detector: DetectorMetadata{ + Name: "syft", + Version: "0.0.0-dev", + URL: "https://github.com/anchore/syft", + }, + Metadata: Metadata{ + "syft:distro": "pkg:generic/ubuntu@18.04?like=debian", + }, + Scanned: actual.Scanned, + Manifests: Manifests{ + "ubuntu:18.04:/usr/lib": Manifest{ + Name: "ubuntu:18.04:/usr/lib", + File: FileInfo{ + SourceLocation: "ubuntu:18.04:/usr/lib", + }, + Metadata: Metadata{ + "syft:filesystem": "fsid-1", + }, + Resolved: DependencyGraph{ + "pkg:generic/pkg-1@1.0.1": DependencyNode{ + PackageURL: "pkg:generic/pkg-1@1.0.1", + Scope: DependencyScopeRuntime, + Relationship: DependencyRelationshipDirect, + }, + "pkg:generic/pkg-2@2.0.2": DependencyNode{ + PackageURL: "pkg:generic/pkg-2@2.0.2", + Scope: DependencyScopeRuntime, + Relationship: DependencyRelationshipDirect, + }, + }, + }, + "ubuntu:18.04:/etc": Manifest{ + Name: "ubuntu:18.04:/etc", + File: FileInfo{ + SourceLocation: "ubuntu:18.04:/etc", + }, + Metadata: Metadata{ + "syft:filesystem": "fsid-1", + }, + Resolved: DependencyGraph{ + "pkg:generic/pkg-3@3.0.3": DependencyNode{ + PackageURL: "pkg:generic/pkg-3@3.0.3", + Scope: DependencyScopeRuntime, + Relationship: DependencyRelationshipDirect, + }, + }, + }, + }, + } + + // just using JSONEq because it gives a comprehensible diff + s1, _ := json.Marshal(expected) + s2, _ := json.Marshal(actual) + assert.JSONEq(t, string(s1), string(s2)) + + // Just test the other schemes: + s.Source.Path = "." + s.Source.Scheme = source.DirectoryScheme + actual = toGithubModel(&s) + assert.Equal(t, "etc", actual.Manifests["etc"].Name) + + s.Source.Path = "./artifacts" + s.Source.Scheme = source.DirectoryScheme + actual = toGithubModel(&s) + assert.Equal(t, "artifacts/etc", actual.Manifests["artifacts/etc"].Name) + + s.Source.Path = "/artifacts" + s.Source.Scheme = source.DirectoryScheme + actual = toGithubModel(&s) + assert.Equal(t, "/artifacts/etc", actual.Manifests["/artifacts/etc"].Name) + + s.Source.Path = "./executable" + s.Source.Scheme = source.FileScheme + actual = toGithubModel(&s) + assert.Equal(t, "executable", actual.Manifests["executable"].Name) + + s.Source.Path = "./archive.tar.gz" + s.Source.Scheme = source.FileScheme + actual = toGithubModel(&s) + assert.Equal(t, "archive.tar.gz:/etc", actual.Manifests["archive.tar.gz:/etc"].Name) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/github/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/github/format.go new file mode 100644 index 0000000000000000000000000000000000000000..fad5dbff1a276a0fc79c662d73597afd69b988ca --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/github/format.go @@ -0,0 +1,29 @@ +package github + +import ( + "encoding/json" + "io" + + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "github-0-json" + +func Format() sbom.Format { + return sbom.NewFormat( + ID, + func(writer io.Writer, sbom sbom.SBOM) error { + bom := toGithubModel(&sbom) + + bytes, err := json.MarshalIndent(bom, "", " ") + if err != nil { + return err + } + _, err = writer.Write(bytes) + + return err + }, + nil, + nil, + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/github/github_dependency_api.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/github/github_dependency_api.go new file mode 100644 index 0000000000000000000000000000000000000000..fe873d41809a0a306271def28c859c2c3799195b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/github/github_dependency_api.go @@ -0,0 +1,78 @@ +package github + +// Derived from: https://gist.github.com/reiddraper/fdab2883db0f372c146d1a750fc1c43f + +type DependencySnapshot struct { + Version int `json:"version"` + Job Job `json:"job,omitempty"` // !omitempty + Sha string `json:"sha,omitempty"` // !omitempty sha of the Git commit + Ref string `json:"ref,omitempty"` // !omitempty ref of the Git commit example "refs/heads/main" + Detector DetectorMetadata `json:"detector,omitempty"` + Metadata Metadata `json:"metadata,omitempty"` + Manifests Manifests `json:"manifests,omitempty"` + Scanned ISO8601Date `json:"scanned,omitempty"` +} + +type Job struct { + Correlator string `json:"correlator,omitempty"` // !omitempty + ID string `json:"id,omitempty"` // !omitempty + HTMLURL string `json:"html_url,omitempty"` +} + +type DetectorMetadata struct { + Name string `json:"name,omitempty"` + URL string `json:"url,omitempty"` + Version string `json:"version,omitempty"` +} + +type Manifests map[string]Manifest + +// Manifest A collection of related dependencies, either declared in a file, +// or representing a logical group of dependencies. +type Manifest struct { + Name string `json:"name"` + File FileInfo `json:"file"` + Metadata Metadata `json:"metadata,omitempty"` + Resolved DependencyGraph `json:"resolved,omitempty"` +} + +type FileInfo struct { + SourceLocation string `json:"source_location,omitempty"` +} + +// DependencyRelationship A notation of whether a dependency is requested directly +// by this manifest, or is a dependency of another dependency. +type DependencyRelationship string + +const ( + DependencyRelationshipDirect DependencyRelationship = "direct" + DependencyRelationshipIndirect DependencyRelationship = "indirect" +) + +// DependencyScope A notation of whether the dependency is required for the primary +// build artifact (runtime), or is only used for development. +// Future versions of this specification may allow for more granular +// scopes, like `runtimeserver`, `runtimeshipped`, +// `developmenttest`, `developmentbenchmark`. +type DependencyScope string + +const ( + DependencyScopeRuntime DependencyScope = "runtime" + DependencyScopeDevelopment DependencyScope = "development" +) + +type DependencyNode struct { + PackageURL string `json:"package_url,omitempty"` + Metadata Metadata `json:"metadata,omitempty"` + Relationship DependencyRelationship `json:"relationship,omitempty"` + Scope DependencyScope `json:"scope,omitempty"` + Dependencies []string `json:"dependencies,omitempty"` +} + +type DependencyGraph map[string]DependencyNode + +type ISO8601Date = string + +type Scalar interface{} // should be: null | boolean | string | number + +type Metadata map[string]Scalar diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/decoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/decoder.go new file mode 100644 index 0000000000000000000000000000000000000000..f037cd5f402de132e1e65031868b498b1f27924b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/decoder.go @@ -0,0 +1,28 @@ +package spdx22json + +import ( + "fmt" + "io" + + "github.com/spdx/tools-golang/jsonloader" + + "github.com/anchore/syft/internal/formats/common/spdxhelpers" + "github.com/anchore/syft/syft/sbom" +) + +func decoder(reader io.Reader) (s *sbom.SBOM, err error) { + defer func() { + // The spdx tools JSON parser panics in quite a lot of situations, just handle this as a parse failure + if v := recover(); v != nil { + s = nil + err = fmt.Errorf("an error occurred during SPDX JSON document parsing: %+v", v) + } + }() + + doc, err := jsonloader.Load2_2(reader) + if err != nil { + return nil, fmt.Errorf("unable to decode spdx-json: %w", err) + } + + return spdxhelpers.ToSyftModel(doc) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/decoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/decoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..6f718dc4d7a18076998302253be48df5a20590d0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/decoder_test.go @@ -0,0 +1,103 @@ +package spdx22json + +import ( + "fmt" + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func TestSPDXJSONDecoder(t *testing.T) { + tests := []struct { + path string + fail bool + packages []string + relationships []string + }{ + { + path: "alpine-3.10.syft.spdx.json", + packages: []string{"busybox", "libssl1.1", "ssl_client"}, + relationships: []string{"busybox", "busybox", "libssl1.1", "libssl1.1"}, + }, + { + path: "alpine-3.10.vendor.spdx.json", + packages: []string{"alpine", "busybox", "ssl_client"}, + relationships: []string{}, + }, + { + path: "example7-bin.spdx.json", + }, + { + path: "example7-go-module.spdx.json", + }, + { + path: "example7-golang.spdx.json", + }, + { + path: "example7-third-party-modules.spdx.json", + }, + { + path: "bad/example7-bin.spdx.json", + fail: true, + }, + { + path: "bad/example7-go-module.spdx.json", + fail: true, + }, + { + path: "bad/example7-golang.spdx.json", + fail: true, + }, + { + path: "bad/example7-third-party-modules.spdx.json", + fail: true, + }, + } + + for _, test := range tests { + t.Run(test.path, func(t *testing.T) { + f, err := os.Open("test-fixtures/spdx/" + test.path) + assert.NoError(t, err) + + sbom, err := decoder(f) + + if test.fail { + assert.Error(t, err) + return + } else { + assert.NoError(t, err) + } + + if test.packages != nil { + assert.Equal(t, sbom.Artifacts.PackageCatalog.PackageCount(), len(test.packages)) + + packages: + for _, pkgName := range test.packages { + for _, p := range sbom.Artifacts.PackageCatalog.Sorted() { + if p.Name == pkgName { + continue packages + } + } + assert.NoError(t, fmt.Errorf("Unable to find package: %s", pkgName)) + } + } + + if test.relationships != nil { + assert.Len(t, sbom.Relationships, len(test.relationships)) + + relationships: + for _, pkgName := range test.relationships { + for _, rel := range sbom.Relationships { + p, ok := rel.From.(*pkg.Package) + if ok && p.Name == pkgName { + continue relationships + } + } + assert.NoError(t, fmt.Errorf("Unable to find relationship: %s", pkgName)) + } + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..36bfeb8a203ce74256eef4eb5ef9b0dfee193756 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/encoder.go @@ -0,0 +1,19 @@ +package spdx22json + +import ( + "encoding/json" + "io" + + "github.com/anchore/syft/syft/sbom" +) + +func encoder(output io.Writer, s sbom.SBOM) error { + doc := toFormatModel(s) + + enc := json.NewEncoder(output) + // prevent > and < from being escaped in the payload + enc.SetEscapeHTML(false) + enc.SetIndent("", " ") + + return enc.Encode(doc) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..ef5ccfce96e99c01b197840051e2c7016ecc0b27 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/encoder_test.go @@ -0,0 +1,42 @@ +package spdx22json + +import ( + "flag" + "regexp" + "testing" + + "github.com/anchore/syft/internal/formats/common/testutils" +) + +var updateSpdxJson = flag.Bool("update-spdx-json", false, "update the *.golden files for spdx-json encoders") + +func TestSPDXJSONDirectoryEncoder(t *testing.T) { + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + testutils.DirectoryInput(t), + *updateSpdxJson, + spdxJsonRedactor, + ) +} + +func TestSPDXJSONImageEncoder(t *testing.T) { + testImage := "image-simple" + testutils.AssertEncoderAgainstGoldenImageSnapshot(t, + Format(), + testutils.ImageInput(t, testImage, testutils.FromSnapshot()), + testImage, + *updateSpdxJson, + spdxJsonRedactor, + ) +} + +func spdxJsonRedactor(s []byte) []byte { + // each SBOM reports the time it was generated, which is not useful during snapshot testing + s = regexp.MustCompile(`"created": .*`).ReplaceAll(s, []byte("redacted")) + + // each SBOM reports a unique documentNamespace when generated, this is not useful for snapshot testing + s = regexp.MustCompile(`"documentNamespace": .*`).ReplaceAll(s, []byte("redacted")) + + // the license list will be updated periodically, the value here should not be directly tested in snapshot tests + return regexp.MustCompile(`"licenseListVersion": .*`).ReplaceAll(s, []byte("redacted")) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/format.go new file mode 100644 index 0000000000000000000000000000000000000000..ae40169100f94a2c6dce78bfc5fde889759d0ec3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/format.go @@ -0,0 +1,17 @@ +package spdx22json + +import ( + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "spdx-2-json" + +// note: this format is LOSSY relative to the syftjson format +func Format() sbom.Format { + return sbom.NewFormat( + ID, + encoder, + decoder, + validator, + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/annotation.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/annotation.go new file mode 100644 index 0000000000000000000000000000000000000000..e924cb7c67880181a33771d31e3009082f92a129 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/annotation.go @@ -0,0 +1,21 @@ +package model + +import "time" + +type AnnotationType string + +const ( + ReviewerAnnotationType AnnotationType = "REVIEWER" + OtherAnnotationType AnnotationType = "OTHER" +) + +type Annotation struct { + // Identify when the comment was made. This is to be specified according to the combined date and time in the + // UTC format, as specified in the ISO 8601 standard. + AnnotationDate time.Time `json:"annotationDate"` + // Type of the annotation + AnnotationType AnnotationType `json:"annotationType"` + // This field identifies the person, organization or tool that has commented on a file, package, or the entire document. + Annotator string `json:"annotator"` + Comment string `json:"comment"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/checksum.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/checksum.go new file mode 100644 index 0000000000000000000000000000000000000000..b995a95fb9f77e525d6304a88c2e986339ae13b6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/checksum.go @@ -0,0 +1,7 @@ +package model + +type Checksum struct { + // Identifies the algorithm used to produce the subject Checksum. One of: "SHA256", "SHA1", "SHA384", "MD2", "MD4", "SHA512", "MD6", "MD5", "SHA224" + Algorithm string `json:"algorithm"` + ChecksumValue string `json:"checksumValue"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/creation_info.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/creation_info.go new file mode 100644 index 0000000000000000000000000000000000000000..c7b545d98e14c25da7dbd4052962a032602617e9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/creation_info.go @@ -0,0 +1,19 @@ +package model + +import "time" + +type CreationInfo struct { + Comment string `json:"comment,omitempty"` + // Identify when the SPDX file was originally created. The date is to be specified according to combined date and + // time in UTC format as specified in ISO 8601 standard. This field is distinct from the fields in section 8, + // which involves the addition of information during a subsequent review. + Created time.Time `json:"created"` + // Identify who (or what, in the case of a tool) created the SPDX file. If the SPDX file was created by an + // individual, indicate the person's name. If the SPDX file was created on behalf of a company or organization, + // indicate the entity name. If the SPDX file was created using a software tool, indicate the name and version + // for that tool. If multiple participants or tools were involved, use multiple instances of this field. Person + // name or organization name may be designated as “anonymous” if appropriate. + Creators []string `json:"creators"` + // An optional field for creators of the SPDX file to provide the version of the SPDX License List used when the SPDX file was created. + LicenseListVersion string `json:"licenseListVersion"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/document.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/document.go new file mode 100644 index 0000000000000000000000000000000000000000..7675ff42635a93c9f09c10469730c938b6d19972 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/document.go @@ -0,0 +1,45 @@ +package model + +// derived from: +// - https://spdx.github.io/spdx-spec/appendix-III-RDF-data-model-implementation-and-identifier-syntax/ +// - https://github.com/spdx/spdx-spec/blob/v2.2/schemas/spdx-schema.json +// - https://github.com/spdx/spdx-spec/tree/v2.2/ontology + +type Document struct { + Element + SPDXVersion string `json:"spdxVersion"` + // One instance is required for each SPDX file produced. It provides the necessary information for forward + // and backward compatibility for processing tools. + CreationInfo CreationInfo `json:"creationInfo"` + // 2.2: Data License; should be "CC0-1.0" + // Cardinality: mandatory, one + // License expression for dataLicense. Compliance with the SPDX specification includes populating the SPDX + // fields therein with data related to such fields (\"SPDX-Metadata\"). The SPDX specification contains numerous + // fields where an SPDX document creator may provide relevant explanatory text in SPDX-Metadata. Without + // opining on the lawfulness of \"database rights\" (in jurisdictions where applicable), such explanatory text + // is copyrightable subject matter in most Berne Convention countries. By using the SPDX specification, or any + // portion hereof, you hereby agree that any copyright rights (as determined by your jurisdiction) in any + // SPDX-Metadata, including without limitation explanatory text, shall be subject to the terms of the Creative + // Commons CC0 1.0 Universal license. For SPDX-Metadata not containing any copyright rights, you hereby agree + // and acknowledge that the SPDX-Metadata is provided to you \"as-is\" and without any representations or + // warranties of any kind concerning the SPDX-Metadata, express, implied, statutory or otherwise, including + // without limitation warranties of title, merchantability, fitness for a particular purpose, non-infringement, + // or the absence of latent or other defects, accuracy, or the presence or absence of errors, whether or not + // discoverable, all to the greatest extent permissible under applicable law. + DataLicense string `json:"dataLicense"` + // Information about an external SPDX document reference including the checksum. This allows for verification of the external references. + ExternalDocumentRefs []ExternalDocumentRef `json:"externalDocumentRefs,omitempty"` + // Indicates that a particular ExtractedLicensingInfo was defined in the subject SpdxDocument. + HasExtractedLicensingInfos []HasExtractedLicensingInfo `json:"hasExtractedLicensingInfos,omitempty"` + // note: found in example documents from SPDX, but not in the JSON schema. See https://spdx.github.io/spdx-spec/2-document-creation-information/#25-spdx-document-namespace + DocumentNamespace string `json:"documentNamespace"` + // note: found in example documents from SPDX, but not in the JSON schema + // DocumentDescribes []string `json:"documentDescribes"` + Packages []Package `json:"packages"` + // Files referenced in the SPDX document + Files []File `json:"files,omitempty"` + // Snippets referenced in the SPDX document + Snippets []Snippet `json:"snippets,omitempty"` + // Relationships referenced in the SPDX document + Relationships []Relationship `json:"relationships,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/element.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/element.go new file mode 100644 index 0000000000000000000000000000000000000000..75d250442f291d8182c8f6a93017b8a246bc488c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/element.go @@ -0,0 +1,12 @@ +package model + +type Element struct { + SPDXID string `json:"SPDXID"` + // Identify name of this SpdxElement. + Name string `json:"name,omitempty"` + // Relationships referenced in the SPDX document + Relationships []Relationship `json:"relationships,omitempty"` + // Provide additional information about an SpdxElement. + Annotations []Annotation `json:"annotations,omitempty"` + Comment string `json:"comment,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/element_id.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/element_id.go new file mode 100644 index 0000000000000000000000000000000000000000..0973ce4bd211b7dfa75060b6f476384017b35055 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/element_id.go @@ -0,0 +1,13 @@ +package model + +import "github.com/anchore/syft/internal/formats/common/spdxhelpers" + +// ElementID represents the identifier string portion of an SPDX element +// identifier. DocElementID should be used for any attributes which can +// contain identifiers defined in a different SPDX document. +// ElementIDs should NOT contain the mandatory 'SPDXRef-' portion. +type ElementID string + +func (e ElementID) String() string { + return "SPDXRef-" + spdxhelpers.SanitizeElementID(string(e)) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/external_document_ref.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/external_document_ref.go new file mode 100644 index 0000000000000000000000000000000000000000..10e1d9ec3b175b6d62806cfce8c52af53cb1814e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/external_document_ref.go @@ -0,0 +1,9 @@ +package model + +type ExternalDocumentRef struct { + // externalDocumentId is a string containing letters, numbers, ., - and/or + which uniquely identifies an external document within this document. + ExternalDocumentID string `json:"externalDocumentId"` + Checksum Checksum `json:"checksum"` + // SPDX ID for SpdxDocument. A propoerty containing an SPDX document. + SpdxDocument string `json:"spdxDocument"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/file.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/file.go new file mode 100644 index 0000000000000000000000000000000000000000..cc039facb4aa56ce45cfdf218f7ce98c0495365b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/file.go @@ -0,0 +1,25 @@ +package model + +type File struct { + Item + // (At least one is required.) The checksum property provides a mechanism that can be used to verify that the + // contents of a File or Package have not changed. + Checksums []Checksum `json:"checksums,omitempty"` + // This field provides a place for the SPDX file creator to record file contributors. Contributors could include + // names of copyright holders and/or authors who may not be copyright holders yet contributed to the file content. + FileContributors []string `json:"fileContributors,omitempty"` + // Each element is a SPDX ID for a File. + FileDependencies []string `json:"fileDependencies,omitempty"` + // The name of the file relative to the root of the package. + FileName string `json:"fileName"` + // The type of the file + FileTypes []string `json:"fileTypes,omitempty"` + // This field provides a place for the SPDX file creator to record potential legal notices found in the file. + // This may or may not include copyright statements. + NoticeText string `json:"noticeText,omitempty"` + // Indicates the project in which the SpdxElement originated. Tools must preserve doap:homepage and doap:name + // properties and the URI (if one is known) of doap:Project resources that are values of this property. All other + // properties of doap:Projects are not directly supported by SPDX and may be dropped when translating to or + // from some SPDX formats (deprecated). + ArtifactOf []string `json:"artifactOf,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/has_extracted_licensing_info.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/has_extracted_licensing_info.go new file mode 100644 index 0000000000000000000000000000000000000000..8c0748073b373dd3ba8abbf644d5452c73a228de --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/has_extracted_licensing_info.go @@ -0,0 +1,14 @@ +package model + +type HasExtractedLicensingInfo struct { + // Verbatim license or licensing notice text that was discovered. + ExtractedText string `json:"extractedText"` + // A human readable short form license identifier for a license. The license ID is iether on the standard license + // oist or the form \"LicenseRef-\"[idString] where [idString] is a unique string containing letters, + // numbers, \".\", \"-\" or \"+\". + LicenseID string `json:"licenseId"` + Comment string `json:"comment,omitempty"` + // Identify name of this SpdxElement. + Name string `json:"name,omitempty"` + SeeAlsos []string `json:"seeAlsos,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/item.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/item.go new file mode 100644 index 0000000000000000000000000000000000000000..178fbf8421e7a801720b4965979257a1caba344f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/item.go @@ -0,0 +1,22 @@ +package model + +type Item struct { + Element + // The licenseComments property allows the preparer of the SPDX document to describe why the licensing in + // spdx:licenseConcluded was chosen. + LicenseComments string `json:"licenseComments,omitempty"` + LicenseConcluded string `json:"licenseConcluded"` + // The licensing information that was discovered directly within the package. There will be an instance of this + // property for each distinct value of alllicenseInfoInFile properties of all files contained in the package. + LicenseInfoFromFiles []string `json:"licenseInfoFromFiles,omitempty"` + // Licensing information that was discovered directly in the subject file. This is also considered a declared license for the file. + LicenseInfoInFiles []string `json:"licenseInfoInFiles,omitempty"` + // The text of copyright declarations recited in the Package or File. + CopyrightText string `json:"copyrightText,omitempty"` + // This field provides a place for the SPDX data creator to record acknowledgements that may be required to be + // communicated in some contexts. This is not meant to include the actual complete license text (see + // licenseConculded and licenseDeclared), and may or may not include copyright notices (see also copyrightText). + // The SPDX data creator may use this field to record other acknowledgements, such as particular clauses from + // license texts, which may be necessary or desirable to reproduce. + AttributionTexts []string `json:"attributionTexts,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/package.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/package.go new file mode 100644 index 0000000000000000000000000000000000000000..a4808e7e21e0d0e7ebeb7644caa7c29e0f600061 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/package.go @@ -0,0 +1,52 @@ +package model + +import "github.com/anchore/syft/internal/formats/common/spdxhelpers" + +type Package struct { + Item + // The checksum property provides a mechanism that can be used to verify that the contents of a File or + // Package have not changed. + Checksums []Checksum `json:"checksums,omitempty"` + // Provides a detailed description of the package. + Description string `json:"description,omitempty"` + // The URI at which this package is available for download. Private (i.e., not publicly reachable) URIs are + // acceptable as values of this property. The values http://spdx.org/rdf/terms#none and http://spdx.org/rdf/terms#noassertion + // may be used to specify that the package is not downloadable or that no attempt was made to determine its + // download location, respectively. + DownloadLocation string `json:"downloadLocation,omitempty"` + // An External Reference allows a Package to reference an external source of additional information, metadata, + // enumerations, asset identifiers, or downloadable content believed to be relevant to the Package. + ExternalRefs []spdxhelpers.ExternalRef `json:"externalRefs,omitempty"` + // Indicates whether the file content of this package has been available for or subjected to analysis when + // creating the SPDX document. If false indicates packages that represent metadata or URI references to a + // project, product, artifact, distribution or a component. If set to false, the package must not contain any files + FilesAnalyzed bool `json:"filesAnalyzed"` + // Indicates that a particular file belongs to a package (elements are SPDX ID for a File). + HasFiles []string `json:"hasFiles,omitempty"` + // Provide a place for the SPDX file creator to record a web site that serves as the package's home page. + // This link can also be used to reference further information about the package referenced by the SPDX file creator. + Homepage string `json:"homepage,omitempty"` + // List the licenses that have been declared by the authors of the package. Any license information that does not + // originate from the package authors, e.g. license information from a third party repository, should not be included in this field. + LicenseDeclared string `json:"licenseDeclared"` + // The name and, optionally, contact information of the person or organization that originally created the package. + // Values of this property must conform to the agent and tool syntax. + Originator string `json:"originator,omitempty"` + // The base name of the package file name. For example, zlib-1.2.5.tar.gz. + PackageFileName string `json:"packageFileName,omitempty"` + // A manifest based verification code (the algorithm is defined in section 4.7 of the full specification) of the + // SPDX Item. This allows consumers of this data and/or database to determine if an SPDX item they have in hand + // is identical to the SPDX item from which the data was produced. This algorithm works even if the SPDX document + // is included in the SPDX item. + PackageVerificationCode *PackageVerificationCode `json:"packageVerificationCode,omitempty"` + // Allows the producer(s) of the SPDX document to describe how the package was acquired and/or changed from the original source. + SourceInfo string `json:"sourceInfo,omitempty"` + // Provides a short description of the package. + Summary string `json:"summary,omitempty"` + // The name and, optionally, contact information of the person or organization who was the immediate supplier + // of this package to the recipient. The supplier may be different than originator when the software has been + // repackaged. Values of this property must conform to the agent and tool syntax. + Supplier string `json:"supplier,omitempty"` + // Provides an indication of the version of the package that is described by this SpdxDocument. + VersionInfo string `json:"versionInfo,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/package_verification_code.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/package_verification_code.go new file mode 100644 index 0000000000000000000000000000000000000000..508c9169ed04b17fb634e2678a9783fecccae744 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/package_verification_code.go @@ -0,0 +1,23 @@ +package model + +// Why are there two package identifier fields Package Checksum and Package Verification? +// Although the values of the two fields Package Checksum and Package Verification are similar, they each serve a +// different purpose. The Package Checksum provides a unique identifier of a software package which is computed by +// taking the SHA1 of the entire software package file. This enables one to quickly determine if two different copies +// of a package are the same. One disadvantage of this approach is that one cannot add an SPDX data file into the +// original package without changing the Package Checksum value. Alternatively, the Package Verification field enables +// the inclusion of an SPDX file. It enables one to quickly verify if one or more of the original package files has +// changed. The Package Verification field is a unique identifier that is based on SHAing only the original package +// files (e.g., excluding the SPDX file). This allows one to add an SPDX file to the original package without changing +// this unique identifier. +// source: https://wiki.spdx.org/view/SPDX_FAQ +type PackageVerificationCode struct { + // "A file that was excluded when calculating the package verification code. This is usually a file containing + // SPDX data regarding the package. If a package contains more than one SPDX file all SPDX files must be excluded + // from the package verification code. If this is not done it would be impossible to correctly calculate the + // verification codes in both files. + PackageVerificationCodeExcludedFiles []string `json:"packageVerificationCodeExcludedFiles"` + + // The actual package verification code as a hex encoded value. + PackageVerificationCodeValue string `json:"packageVerificationCodeValue"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/relationship.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/relationship.go new file mode 100644 index 0000000000000000000000000000000000000000..9c806c41c124e14b4e9c487f42edd658dd056e98 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/relationship.go @@ -0,0 +1,13 @@ +package model + +import "github.com/anchore/syft/internal/formats/common/spdxhelpers" + +type Relationship struct { + // Id to which the SPDX element is related + SpdxElementID string `json:"spdxElementId"` + // Describes the type of relationship between two SPDX elements. + RelationshipType spdxhelpers.RelationshipType `json:"relationshipType"` + // SPDX ID for SpdxElement. A related SpdxElement. + RelatedSpdxElement string `json:"relatedSpdxElement"` + Comment string `json:"comment,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/snippet.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/snippet.go new file mode 100644 index 0000000000000000000000000000000000000000..0d39e5dca3920dd4e96e1dbbe1f8e0156420f9d9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/snippet.go @@ -0,0 +1,32 @@ +package model + +type StartPointer struct { + Offset int `json:"offset,omitempty"` + LineNumber int `json:"lineNumber,omitempty"` + // SPDX ID for File + Reference string `json:"reference"` +} + +type EndPointer struct { + Offset int `json:"offset,omitempty"` + LineNumber int `json:"lineNumber,omitempty"` + // SPDX ID for File + Reference string `json:"reference"` +} + +type Range struct { + StartPointer StartPointer `json:"startPointer"` + EndPointer EndPointer `json:"endPointer"` +} + +type Snippet struct { + Item + // Licensing information that was discovered directly in the subject snippet. This is also considered a declared + // license for the snippet. (elements are license expressions) + LicenseInfoInSnippets []string `json:"licenseInfoInSnippets"` + // SPDX ID for File. File containing the SPDX element (e.g. the file contaning a snippet). + SnippetFromFile string `json:"snippetFromFile"` + // (At least 1 range is required). This field defines the byte range in the original host file (in X.2) that the + // snippet information applies to. + Ranges []Range `json:"ranges"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/version.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/version.go new file mode 100644 index 0000000000000000000000000000000000000000..8f105cbfa71a4bfd87e5d2c56206a7848323c9ca --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/model/version.go @@ -0,0 +1,3 @@ +package model + +const Version = "SPDX-2.2" diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/Dockerfile b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..79cfa759e357be9628894dea6332a0e6a2c33bb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/Dockerfile @@ -0,0 +1,4 @@ +# Note: changes to this file will result in updating several test values. Consider making a new image fixture instead of editing this one. +FROM scratch +ADD file-1.txt /somefile-1.txt +ADD file-2.txt /somefile-2.txt diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/file-1.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..985d3408e98cb9f41c01376c698451fdef0e4b32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/file-1.txt @@ -0,0 +1 @@ +this file has contents \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/file-2.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..396d08bbc72f810ec6d057d1713a84a75d1cd542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/image-simple/file-2.txt @@ -0,0 +1 @@ +file-2 contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/TestSPDXJSONDirectoryEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/TestSPDXJSONDirectoryEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..f237501b50779842598e34a4add78eacbe75d71d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/TestSPDXJSONDirectoryEncoder.golden @@ -0,0 +1,61 @@ +{ + "SPDXID": "SPDXRef-DOCUMENT", + "name": "/some/path", + "spdxVersion": "SPDX-2.2", + "creationInfo": { + "created": "2022-05-23T19:10:22.25645Z", + "creators": [ + "Organization: Anchore, Inc", + "Tool: syft-v0.42.0-bogus" + ], + "licenseListVersion": "3.17" + }, + "dataLicense": "CC0-1.0", + "documentNamespace": "https://anchore.com/syft/dir/some/path-81dbcbfa-251d-4ad5-9b01-be91afb16469", + "packages": [ + { + "SPDXID": "SPDXRef-b85dbb4e6ece5082", + "name": "package-1", + "licenseConcluded": "MIT", + "downloadLocation": "NOASSERTION", + "externalRefs": [ + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "PACKAGE_MANAGER", + "referenceLocator": "a-purl-2", + "referenceType": "purl" + } + ], + "filesAnalyzed": false, + "licenseDeclared": "MIT", + "sourceInfo": "acquired package info from installed python package manifest file: /some/path/pkg1", + "versionInfo": "1.0.1" + }, + { + "SPDXID": "SPDXRef-ceda99598967ae8d", + "name": "package-2", + "licenseConcluded": "NONE", + "downloadLocation": "NOASSERTION", + "externalRefs": [ + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "PACKAGE_MANAGER", + "referenceLocator": "pkg:deb/debian/package-2@2.0.1", + "referenceType": "purl" + } + ], + "filesAnalyzed": false, + "licenseDeclared": "NONE", + "sourceInfo": "acquired package info from DPKG DB: /some/path/pkg1", + "versionInfo": "2.0.1" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/TestSPDXJSONImageEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/TestSPDXJSONImageEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..f1891ad57aa2939b10b655640aa8d3e0b0b4fe2f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/TestSPDXJSONImageEncoder.golden @@ -0,0 +1,61 @@ +{ + "SPDXID": "SPDXRef-DOCUMENT", + "name": "user-image-input", + "spdxVersion": "SPDX-2.2", + "creationInfo": { + "created": "2022-05-23T19:10:22.412847Z", + "creators": [ + "Organization: Anchore, Inc", + "Tool: syft-v0.42.0-bogus" + ], + "licenseListVersion": "3.17" + }, + "dataLicense": "CC0-1.0", + "documentNamespace": "https://anchore.com/syft/image/user-image-input-c9945597-78ce-4e9b-89d2-68b8e4e4ccb9", + "packages": [ + { + "SPDXID": "SPDXRef-2a46171f91c8d4bc", + "name": "package-1", + "licenseConcluded": "MIT", + "downloadLocation": "NOASSERTION", + "externalRefs": [ + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:*:some:package:1:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "PACKAGE_MANAGER", + "referenceLocator": "a-purl-1", + "referenceType": "purl" + } + ], + "filesAnalyzed": false, + "licenseDeclared": "MIT", + "sourceInfo": "acquired package info from installed python package manifest file: /somefile-1.txt", + "versionInfo": "1.0.1" + }, + { + "SPDXID": "SPDXRef-ae77680e9b1d087e", + "name": "package-2", + "licenseConcluded": "NONE", + "downloadLocation": "NOASSERTION", + "externalRefs": [ + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "PACKAGE_MANAGER", + "referenceLocator": "pkg:deb/debian/package-2@2.0.1", + "referenceType": "purl" + } + ], + "filesAnalyzed": false, + "licenseDeclared": "NONE", + "sourceInfo": "acquired package info from DPKG DB: /somefile-2.txt", + "versionInfo": "2.0.1" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden new file mode 100644 index 0000000000000000000000000000000000000000..3d93b6d3ad1c86098e440073bcf8cfdf5eea53e1 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden differ diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/alpine-3.10.syft.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/alpine-3.10.syft.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..652aaeca430d14c782e671ef76cb630573049a58 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/alpine-3.10.syft.spdx.json @@ -0,0 +1,170 @@ +{ + "SPDXID": "SPDXRef-DOCUMENT", + "name": "alpine-3.10", + "spdxVersion": "SPDX-2.2", + "creationInfo": { + "created": "2022-01-20T21:40:24.439211Z", + "creators": [ + "Organization: Anchore, Inc", + "Tool: syft-[not provided]" + ], + "licenseListVersion": "3.15" + }, + "dataLicense": "CC0-1.0", + "documentNamespace": "https://anchore.com/syft/image/alpine-3.10-204b304b-beb3-4413-9b38-d8a2e58e3dfb", + "packages": [ + { + "SPDXID": "SPDXRef-a61243292e73923", + "name": "busybox", + "licenseConcluded": "GPL-2.0", + "description": "Size optimized toolbox of many common UNIX utilities", + "downloadLocation": "https://busybox.net/", + "externalRefs": [ + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:a:busybox:busybox:1.30.1-r5:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "PACKAGE_MANAGER", + "referenceLocator": "pkg:alpine/busybox@1.30.1-r5?arch=x86_64&distro=alpine-3.10.9", + "referenceType": "purl" + } + ], + "filesAnalyzed": false, + "licenseDeclared": "GPL-2.0", + "originator": "Person: Natanael Copa ", + "sourceInfo": "acquired package info from APK DB: /lib/apk/db/installed", + "versionInfo": "1.30.1-r5" + }, + { + "SPDXID": "SPDXRef-d2f55e316dbe92e4", + "name": "libssl1.1", + "licenseConcluded": "OpenSSL", + "description": "SSL shared libraries", + "downloadLocation": "https://www.openssl.org", + "externalRefs": [ + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:a:libssl1.1:libssl1.1:1.1.1k-r0:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "PACKAGE_MANAGER", + "referenceLocator": "pkg:alpine/libssl1.1@1.1.1k-r0?arch=x86_64&distro=alpine-3.10.9", + "referenceType": "purl" + } + ], + "filesAnalyzed": false, + "licenseDeclared": "OpenSSL", + "originator": "Person: Timo Teras ", + "sourceInfo": "acquired package info from APK DB: /lib/apk/db/installed", + "versionInfo": "1.1.1k-r0" + }, + { + "SPDXID": "SPDXRef-2b24657ad7aaafea", + "name": "ssl_client", + "licenseConcluded": "GPL-2.0", + "description": "EXternal ssl_client for busybox wget", + "downloadLocation": "https://busybox.net/", + "externalRefs": [ + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:a:ssl-client:ssl-client:1.30.1-r5:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:a:ssl-client:ssl_client:1.30.1-r5:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:a:ssl_client:ssl-client:1.30.1-r5:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:a:ssl_client:ssl_client:1.30.1-r5:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:a:ssl:ssl-client:1.30.1-r5:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "SECURITY", + "referenceLocator": "cpe:2.3:a:ssl:ssl_client:1.30.1-r5:*:*:*:*:*:*:*", + "referenceType": "cpe23Type" + }, + { + "referenceCategory": "PACKAGE_MANAGER", + "referenceLocator": "pkg:alpine/ssl_client@1.30.1-r5?arch=x86_64&upstream=busybox&distro=alpine-3.10.9", + "referenceType": "purl" + } + ], + "filesAnalyzed": false, + "licenseDeclared": "GPL-2.0", + "originator": "Person: Natanael Copa ", + "sourceInfo": "acquired package info from APK DB: /lib/apk/db/installed", + "versionInfo": "1.30.1-r5" + } + ], + "files": [ + { + "SPDXID": "SPDXRef-a07392483a2d0750", + "comment": "layerID: sha256:9fb3aa2f8b8023a4bebbf92aa567caf88e38e969ada9f0ac12643b2847391635", + "licenseConcluded": "NOASSERTION", + "fileName": "/bin/busybox" + }, + { + "SPDXID": "SPDXRef-aa3cfed221706d80", + "comment": "layerID: sha256:9fb3aa2f8b8023a4bebbf92aa567caf88e38e969ada9f0ac12643b2847391635", + "licenseConcluded": "NOASSERTION", + "fileName": "/lib/libssl.so.1.1" + } + ], + "relationships": [ + { + "spdxElementId": "SPDXRef-a61243292e73923", + "relationshipType": "CONTAINS", + "relatedSpdxElement": "SPDXRef-a07392483a2d0750" + }, + { + "spdxElementId": "SPDXRef-a61243292e73923", + "relationshipType": "CONTAINS", + "relatedSpdxElement": "SPDXRef-a07392483a2d0750" + }, + { + "spdxElementId": "SPDXRef-a61243292e73923", + "relationshipType": "CONTAINS", + "relatedSpdxElement": "SPDXRef-499bb68237b0f2b8" + }, + { + "spdxElementId": "SPDXRef-a61243292e73923", + "relationshipType": "CONTAINS", + "relatedSpdxElement": "SPDXRef-df78c68c8206be69" + }, + { + "spdxElementId": "SPDXRef-a61243292e73923", + "relationshipType": "CONTAINS", + "relatedSpdxElement": "SPDXRef-7c980486fc17af43" + }, + { + "spdxElementId": "SPDXRef-a61243292e73923", + "relationshipType": "CONTAINS", + "relatedSpdxElement": "SPDXRef-8762661e65166719" + }, + { + "spdxElementId": "SPDXRef-d2f55e316dbe92e4", + "relationshipType": "CONTAINS", + "relatedSpdxElement": "SPDXRef-aa3cfed221706d80" + }, + { + "spdxElementId": "SPDXRef-d2f55e316dbe92e4", + "relationshipType": "CONTAINS", + "relatedSpdxElement": "SPDXRef-aa3cfed221706d80" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/alpine-3.10.vendor.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/alpine-3.10.vendor.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..4cf8763708118a74f0f4334bc58fe7cb8f28cb3b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/alpine-3.10.vendor.spdx.json @@ -0,0 +1,78 @@ +{ + "SPDXID": "SPDXRef-DOCUMENT", + "spdxVersion": "SPDX-2.2", + "creationInfo": { + "created": "2022-01-18T22:16:16Z", + "creators": [ + "Tool: vendor" + ], + "licenseListVersion": "3.8" + }, + "name": "alpine:3.10", + "dataLicense": "CC0-1.0", + "documentNamespace": "https://spdx.org/spdxdocs/alpine-154c794c-4264-4e9f-a2ff-5c01bfbfc02c", + "documentDescribes": [ + "SPDXRef-alpine-3.10" + ], + "packages": [ + { + "name": "alpine", + "SPDXID": "SPDXRef-alpine-3.10", + "versionInfo": "3.10", + "downloadLocation": "NOASSERTION", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "NOASSERTION", + "copyrightText": "NOASSERTION" + }, + { + "name": "busybox", + "SPDXID": "SPDXRef-busybox-1.30.1-r5", + "versionInfo": "1.30.1-r5", + "downloadLocation": "NOASSERTION", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "LicenseRef-7d19a72", + "copyrightText": "NONE", + "comment": "busybox:\n\twarning: No metadata for key: copyright\n\twarning: No metadata for key: download_url\n\twarning: No metadata for key: checksum\n\twarning: No metadata for key: pkg_licenses\n\twarning: No metadata for key: pkg_format\n\twarning: No metadata for key: src_name\n\twarning: No metadata for key: src_version\n" + }, + { + "name": "ssl_client", + "SPDXID": "SPDXRef-ssl_client-1.30.1-r5", + "versionInfo": "1.30.1-r5", + "downloadLocation": "NOASSERTION", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "LicenseRef-de5acdd", + "copyrightText": "NONE", + "comment": "ssl_client:\n\twarning: No metadata for key: copyright\n\twarning: No metadata for key: download_url\n\twarning: No metadata for key: checksum\n\twarning: No metadata for key: pkg_licenses\n\twarning: No metadata for key: pkg_format\n\twarning: No metadata for key: src_name\n\twarning: No metadata for key: src_version\n" + } + ], + "relationships": [ + { + "spdxElementId": "SPDXRef-DOCUMENT", + "relatedSpdxElement": "SPDXRef-alpine-3.10", + "relationshipType": "DESCRIBES" + }, + { + "spdxElementId": "SPDXRef-9fb3aa2f8b", + "relatedSpdxElement": "SPDXRef-busybox-1.30.1-r5", + "relationshipType": "CONTAINS" + }, + { + "spdxElementId": "SPDXRef-9fb3aa2f8b", + "relatedSpdxElement": "SPDXRef-ssl_client-1.30.1-r5", + "relationshipType": "CONTAINS" + } + ], + "hasExtractedLicensingInfos": [ + { + "extractedText": "OpenSSL", + "licenseId": "LicenseRef-de5acdd" + }, + { + "extractedText": "GPL-2.0", + "licenseId": "LicenseRef-7d19a72" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-bin.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-bin.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..0d4ad52791123cbd6d897eb6060ce65c1d8832da --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-bin.spdx.json @@ -0,0 +1,72 @@ +{ + "spdxVersion": "SPDX-2.2", + "dataLicense": "CC0-1.0", + "SPDXID": "SPDXRef-DOCUMENT", + "creationInfo": { + "created": "2020-11-24T01:12:27Z", + "creators": [ + { + "Person": "Nisha K (nishak@vmware.com)" + } + ] + }, + "name": "hello-go-binary.spdx.json", + "documentNamespace": "https://swinslow.net/spdx-examples/example7/hello-go-binary", + "externalDocumentRefs": [ + { + "externalDocumentId": "DocumentRef-hello-go-module", + "checksum": { + "algorithm": "SHA1", + "checksumValue": "d661f8f831a99c288a64e5843b4794ad5181224a" + }, + "spdxDocument": "https://swinslow.net/spdx-examples/example7/hello-go-module-cfa0c58d-79db-4860-99b6-258477e4838b" + }, + { + "externalDocumentId": "DocumentRef-golang-dist", + "checksum": { + "algorithm": "SHA1", + "checksumValue": "b6cf54a46329e7cc7610aa5d244018b80103d111" + }, + "spdxDocument": "https://swinslow.net/spdx-examples/example7/golang-dist-492dfde4-318b-49f7-b48c-934bfafbde48" + }, + { + "externalDocumentId": "DocumentRef-hello-imports", + "checksum": { + "algorithm": "SHA1", + "checksumValue": "14ff98203c3ddd2bd4803c00b5225d2551ca603c" + }, + "spdxDocument": "https://swinslow.net/spdx-examples/example7/hello-imports-c2d068df-67aa-4c68-98c8-100b450fc408" + } + ], + "documentDescribes": [ + "SPDXRef-go-bin-hello" + ], + "packages": [ + { + "packageName": "hello", + "SPDXID": "SPDXRef-go-bin-hello", + "downloadLocation": "git@github.com:swinslow/spdx-examples.git#example7/content/build/hello", + "filesAnalyzed": "false", + "packageLicenseConcluded": "NOASSERTION", + "packageLicenseDeclared": "NOASSERTION", + "packageCopyrightText": "NOASSERTION" + } + ], + "relationships": [ + { + "spdxElementId": "DocumentRef-golang-dist", + "relatedSpdxElement": "DocumentRef-hello-go-module", + "relationshipType": "BUILD_TOOL_OF" + }, + { + "spdxElementId": "DocumentRef-golang-dist:SPDXRef-go-compiler", + "relatedSpdxElement": "SPDXRef-go-bin-hello", + "relationshipType": "GENERATES" + }, + { + "spdxElementId": "DocumentRef-hello-imports", + "relatedSpdxElement": "SPDXRef-go-bin-hello", + "relationshipType": "STATIC_LINK" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-go-module.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-go-module.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..9d0e2e8bbaec1cce810809d39d481541c80ae378 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-go-module.spdx.json @@ -0,0 +1,29 @@ +{ + "spdxVersion": "SPDX-2.2", + "dataLicense": "CC0-1.0", + "SPDXID": "SPDXRef-DOCUMENT", + "creationInfo": { + "created": "2020-11-24T01:12:27Z", + "creators": [ + { + "Person": "Nisha K (nishak@vmware.com)" + } + ] + }, + "name": "hello-go-module.spdx.json", + "documentNamespace": "https://swinslow.net/spdx-examples/example7/hello-go-module", + "documentDescribes": [ + "SPDXRef-go-module-example.com/hello" + ], + "packages": [ + { + "packageName": "example.com/hello", + "SPDXID": "SPDXRef-go-module-example.com/hello", + "downloadLocation": "git@github.com:swinslow/spdx-examples.git#example7/content/src/hello", + "filesAnalyzed": "false", + "packageLicenseConcluded": "NOASSERTION", + "packageLicenseDeclared": "NOASSERTION", + "packageCopyrightText": "NOASSERTION" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-golang.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-golang.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..9c1dc5c392c480231cd726c47861621ddac7656d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-golang.spdx.json @@ -0,0 +1,46 @@ +{ + "spdxVersion": "SPDX-2.2", + "dataLicense": "CC0-1.0", + "SPDXID": "SPDXRef-DOCUMENT", + "creationInfo": { + "created": "2020-11-24T01:12:27Z", + "creators": [ + { + "Person": "Nisha K (nishak@vmware.com)" + } + ] + }, + "name": "golang-dist", + "documentNamespace": "https://swinslow.net/spdx-examples/example7/golang-dist", + "documentDescribes": [ + "SPDXRef-golang-dist" + ], + "packages": [ + { + "packageName": "go1.16.4.linux-amd64", + "SPDXID": "SPDXRef-golang-dist", + "downloadLocation": "https://golang.org/dl/go1.16.4.linux-amd64.tar.gz", + "packageVersion": "1.16.4", + "filesAnalyzed": "false", + "checksums": [ + { + "algorithm": "SHA256", + "checksumValue": "7154e88f5a8047aad4b80ebace58a059e36e7e2e4eb3b383127a28c711b4ff59" + } + ], + "packageLicenseConcluded": "NOASSERTION", + "packageLicenseDeclared": "LicenseRef-Golang-BSD-plus-Patents", + "packageCopyrightText": "Copyright (c) 2009 The Go Authors. All rights reserved." + }, + { + "packageName": "go", + "SPDXID": "SPDXRef-go-compiler", + "downloadLocation": "https://golang.org/dl/go1.16.4.linux-amd64.tar.gz", + "packageVersion": "1.16.4", + "filesAnalyzed": "false", + "packageLicenseConcluded": "NOASSERTION", + "packageLicenseDeclared": "NOASSERTION", + "packageCopyrightText": "NOASSERTION" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-third-party-modules.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-third-party-modules.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..626ad04a26615304b55d325d87246fb3f50153c2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/bad/example7-third-party-modules.spdx.json @@ -0,0 +1,49 @@ +{ + "spdxVersion": "SPDX-2.2", + "dataLicense": "CC0-1.0", + "SPDXID": "SPDXRef-DOCUMENT", + "creationInfo": { + "created": "2020-11-24T01:12:27Z", + "creators": [ + { + "Person": "Nisha K (nishak@vmware.com)" + } + ] + }, + "name": "hello-imports.spdx.json", + "documentNamespace": "https://swinslow.net/spdx-examples/example7/hello-imports", + "documentDescribes": [ + "SPDXRef-go-module-golang.org/x/text", + "SPDXRef-go-module-rsc.io/quote", + "SPDXRef-go-module-rsc.io/sampler" + ], + "packages": [ + { + "packageName": "golang.org/x/text", + "SPDXID": "SPDXRef-go-module-golang.org/x/text", + "downloadLocation": "go://golang.org/x/text@v0.0.0-20170915032832-14c0d48ead0c", + "filesAnalyzed": "false", + "packageLicenseConcluded": "NOASSERTION", + "packageLicenseDeclared": "NOASSERTION", + "packageCopyrightText": "NOASSERTION" + }, + { + "packageName": "rsc.io/quote", + "SPDXID": "SPDXRef-go-module-rsc.io/quote", + "downloadLocation": "go://rsc.io/quote@v1.5.2", + "filesAnalyzed": "false", + "packageLicenseConcluded": "NOASSERTION", + "packageLicenseDeclared": "NOASSERTION", + "packageCopyrightText": "NOASSERTION" + }, + { + "packageName": "rsc.io/sampler", + "SPDXID": "SPDXRef-go-module-rsc.io/sampler", + "downloadLocation": "go://rsc.io/sampler@v1.3.0", + "filesAnalyzed": "false", + "packageLicenseConcluded": "NOASSERTION", + "packageLicenseDeclared": "NOASSERTION", + "packageCopyrightText": "NOASSERTION" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-bin.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-bin.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..563b40a785f1d7698e63d5fa682d14b5a79fabee --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-bin.spdx.json @@ -0,0 +1,68 @@ +{ + "spdxVersion": "SPDX-2.2", + "dataLicense": "CC0-1.0", + "SPDXID": "SPDXRef-DOCUMENT", + "creationInfo": { + "created": "2020-11-24T01:12:27Z", + "creators": [ "Person: Nisha K (nishak@vmware.com)" ] + }, + "name": "hello-go-binary.spdx.json", + "documentNamespace": "https://swinslow.net/spdx-examples/example7/hello-go-binary", + "externalDocumentRefs": [ + { + "externalDocumentId": "DocumentRef-hello-go-module", + "checksum": { + "algorithm": "SHA1", + "checksumValue": "d661f8f831a99c288a64e5843b4794ad5181224a" + }, + "spdxDocument": "https://swinslow.net/spdx-examples/example7/hello-go-module-cfa0c58d-79db-4860-99b6-258477e4838b" + }, + { + "externalDocumentId": "DocumentRef-golang-dist", + "checksum": { + "algorithm": "SHA1", + "checksumValue": "b6cf54a46329e7cc7610aa5d244018b80103d111" + }, + "spdxDocument": "https://swinslow.net/spdx-examples/example7/golang-dist-492dfde4-318b-49f7-b48c-934bfafbde48" + }, + { + "externalDocumentId": "DocumentRef-hello-imports", + "checksum": { + "algorithm": "SHA1", + "checksumValue": "14ff98203c3ddd2bd4803c00b5225d2551ca603c" + }, + "spdxDocument": "https://swinslow.net/spdx-examples/example7/hello-imports-c2d068df-67aa-4c68-98c8-100b450fc408" + } + ], + "documentDescribes": [ + "SPDXRef-go-bin-hello" + ], + "packages": [ + { + "name": "hello", + "SPDXID": "SPDXRef-go-bin-hello", + "downloadLocation": "git@github.com:swinslow/spdx-examples.git#example7/content/build/hello", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "NOASSERTION", + "copyrightText": "NOASSERTION" + } + ], + "relationships": [ + { + "spdxElementId": "DocumentRef-golang-dist:SPDXRef-golang-dist", + "relatedSpdxElement": "DocumentRef-hello-go-module:SPDXRef-hello-go-module", + "relationshipType": "BUILD_TOOL_OF" + }, + { + "spdxElementId": "DocumentRef-golang-dist:SPDXRef-go-compiler", + "relatedSpdxElement": "SPDXRef-go-bin-hello", + "relationshipType": "GENERATES" + }, + { + "spdxElementId": "DocumentRef-hello-imports:SPDXRef-hello-imports", + "relatedSpdxElement": "SPDXRef-go-bin-hello", + "relationshipType": "STATIC_LINK" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-go-module.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-go-module.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..682b0642510fe250c4c8e021ee5d0f947245b9c0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-go-module.spdx.json @@ -0,0 +1,25 @@ +{ + "spdxVersion": "SPDX-2.2", + "dataLicense": "CC0-1.0", + "SPDXID": "SPDXRef-DOCUMENT", + "creationInfo": { + "created": "2020-11-24T01:12:27Z", + "creators": [ "Person: Nisha K (nishak@vmware.com)" ] + }, + "name": "hello-go-module.spdx.json", + "documentNamespace": "https://swinslow.net/spdx-examples/example7/hello-go-module", + "documentDescribes": [ + "SPDXRef-go-module-example.com/hello" + ], + "packages": [ + { + "name": "example.com/hello", + "SPDXID": "SPDXRef-go-module-example.com/hello", + "downloadLocation": "git@github.com:swinslow/spdx-examples.git#example7/content/src/hello", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "NOASSERTION", + "copyrightText": "NOASSERTION" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-golang.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-golang.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..e980030997548ac340232d2096f5792e21c0fef0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-golang.spdx.json @@ -0,0 +1,42 @@ +{ + "spdxVersion": "SPDX-2.2", + "dataLicense": "CC0-1.0", + "SPDXID": "SPDXRef-DOCUMENT", + "creationInfo": { + "created": "2020-11-24T01:12:27Z", + "creators": [ "Person: Nisha K (nishak@vmware.com)" ] + }, + "name": "golang-dist", + "documentNamespace": "https://swinslow.net/spdx-examples/example7/golang-dist", + "documentDescribes": [ + "SPDXRef-golang-dist" + ], + "packages": [ + { + "name": "go1.16.4.linux-amd64", + "SPDXID": "SPDXRef-golang-dist", + "downloadLocation": "https://golang.org/dl/go1.16.4.linux-amd64.tar.gz", + "versionInfo": "1.16.4", + "filesAnalyzed": false, + "checksums": [ + { + "algorithm": "SHA256", + "checksumValue": "7154e88f5a8047aad4b80ebace58a059e36e7e2e4eb3b383127a28c711b4ff59" + } + ], + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "LicenseRef-Golang-BSD-plus-Patents", + "copyrightText": "Copyright (c) 2009 The Go Authors. All rights reserved." + }, + { + "name": "go", + "SPDXID": "SPDXRef-go-compiler", + "downloadLocation": "https://golang.org/dl/go1.16.4.linux-amd64.tar.gz", + "versionInfo": "1.16.4", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "NOASSERTION", + "copyrightText": "NOASSERTION" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-third-party-modules.spdx.json b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-third-party-modules.spdx.json new file mode 100644 index 0000000000000000000000000000000000000000..fa7ce80a3ec9e69688b352393f6d4d6a3eb7e181 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/test-fixtures/spdx/example7-third-party-modules.spdx.json @@ -0,0 +1,45 @@ +{ + "spdxVersion": "SPDX-2.2", + "dataLicense": "CC0-1.0", + "SPDXID": "SPDXRef-DOCUMENT", + "creationInfo": { + "created": "2020-11-24T01:12:27Z", + "creators": [ "Person: Nisha K (nishak@vmware.com)" ] + }, + "name": "hello-imports.spdx.json", + "documentNamespace": "https://swinslow.net/spdx-examples/example7/hello-imports", + "documentDescribes": [ + "SPDXRef-go-module-golang.org/x/text", + "SPDXRef-go-module-rsc.io/quote", + "SPDXRef-go-module-rsc.io/sampler" + ], + "packages": [ + { + "name": "golang.org/x/text", + "SPDXID": "SPDXRef-go-module-golang.org/x/text", + "downloadLocation": "go://golang.org/x/text@v0.0.0-20170915032832-14c0d48ead0c", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "NOASSERTION", + "copyrightText": "NOASSERTION" + }, + { + "name": "rsc.io/quote", + "SPDXID": "SPDXRef-go-module-rsc.io/quote", + "downloadLocation": "go://rsc.io/quote@v1.5.2", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "NOASSERTION", + "copyrightText": "NOASSERTION" + }, + { + "name": "rsc.io/sampler", + "SPDXID": "SPDXRef-go-module-rsc.io/sampler", + "downloadLocation": "go://rsc.io/sampler@v1.3.0", + "filesAnalyzed": false, + "licenseConcluded": "NOASSERTION", + "licenseDeclared": "NOASSERTION", + "copyrightText": "NOASSERTION" + } + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/to_format_model.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/to_format_model.go new file mode 100644 index 0000000000000000000000000000000000000000..d1f3d3d4678a54a80320b5ae77b364d64bb4e3a0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/to_format_model.go @@ -0,0 +1,246 @@ +package spdx22json + +import ( + "fmt" + "sort" + "strings" + "time" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/formats/common/spdxhelpers" + "github.com/anchore/syft/internal/formats/spdx22json/model" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/internal/spdxlicense" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" +) + +// toFormatModel creates and populates a new JSON document struct that follows the SPDX 2.2 spec from the given cataloging results. +func toFormatModel(s sbom.SBOM) *model.Document { + name, namespace := spdxhelpers.DocumentNameAndNamespace(s.Source) + + return &model.Document{ + Element: model.Element{ + SPDXID: model.ElementID("DOCUMENT").String(), + Name: name, + }, + SPDXVersion: model.Version, + CreationInfo: model.CreationInfo{ + Created: time.Now().UTC(), + Creators: []string{ + // note: key-value format derived from the JSON example document examples: https://github.com/spdx/spdx-spec/blob/v2.2/examples/SPDXJSONExample-v2.2.spdx.json + "Organization: Anchore, Inc", + "Tool: " + internal.ApplicationName + "-" + s.Descriptor.Version, + }, + LicenseListVersion: spdxlicense.Version, + }, + DataLicense: "CC0-1.0", + DocumentNamespace: namespace, + Packages: toPackages(s.Artifacts.PackageCatalog, s.Relationships), + Files: toFiles(s), + Relationships: toRelationships(s.Relationships), + } +} + +func toPackages(catalog *pkg.Catalog, relationships []artifact.Relationship) []model.Package { + packages := make([]model.Package, 0) + + for _, p := range catalog.Sorted() { + license := spdxhelpers.License(p) + packageSpdxID := model.ElementID(p.ID()).String() + filesAnalyzed := false + + // we generate digest for some Java packages + // see page 33 of the spdx specification for 2.2 + // spdx.github.io/spdx-spec/package-information/#710-package-checksum-field + var checksums []model.Checksum + if p.MetadataType == pkg.JavaMetadataType { + javaMetadata := p.Metadata.(pkg.JavaMetadata) + if len(javaMetadata.ArchiveDigests) > 0 { + filesAnalyzed = true + for _, digest := range javaMetadata.ArchiveDigests { + checksums = append(checksums, model.Checksum{ + Algorithm: strings.ToUpper(digest.Algorithm), + ChecksumValue: digest.Value, + }) + } + } + } + // note: the license concluded and declared should be the same since we are collecting license information + // from the project data itself (the installed package files). + packages = append(packages, model.Package{ + Checksums: checksums, + Description: spdxhelpers.Description(p), + DownloadLocation: spdxhelpers.DownloadLocation(p), + ExternalRefs: spdxhelpers.ExternalRefs(p), + FilesAnalyzed: filesAnalyzed, + HasFiles: fileIDsForPackage(packageSpdxID, relationships), + Homepage: spdxhelpers.Homepage(p), + // The Declared License is what the authors of a project believe govern the package + LicenseDeclared: license, + Originator: spdxhelpers.Originator(p), + SourceInfo: spdxhelpers.SourceInfo(p), + VersionInfo: p.Version, + Item: model.Item{ + // The Concluded License field is the license the SPDX file creator believes governs the package + LicenseConcluded: license, + Element: model.Element{ + SPDXID: packageSpdxID, + Name: p.Name, + }, + }, + }) + } + + return packages +} + +func fileIDsForPackage(packageSpdxID string, relationships []artifact.Relationship) (fileIDs []string) { + for _, relationship := range relationships { + if relationship.Type != artifact.ContainsRelationship { + continue + } + + if _, ok := relationship.From.(pkg.Package); !ok { + continue + } + + if _, ok := relationship.To.(source.Coordinates); !ok { + continue + } + + from := model.ElementID(relationship.From.ID()).String() + to := model.ElementID(relationship.To.ID()).String() + if from == packageSpdxID { + fileIDs = append(fileIDs, to) + } + } + return fileIDs +} + +func toFiles(s sbom.SBOM) []model.File { + results := make([]model.File, 0) + artifacts := s.Artifacts + + for _, coordinates := range sbom.AllCoordinates(s) { + var metadata *source.FileMetadata + if metadataForLocation, exists := artifacts.FileMetadata[coordinates]; exists { + metadata = &metadataForLocation + } + + var digests []file.Digest + if digestsForLocation, exists := artifacts.FileDigests[coordinates]; exists { + digests = digestsForLocation + } + + // TODO: add file classifications (?) and content as a snippet + + var comment string + if coordinates.FileSystemID != "" { + comment = fmt.Sprintf("layerID: %s", coordinates.FileSystemID) + } + + results = append(results, model.File{ + Item: model.Item{ + Element: model.Element{ + SPDXID: model.ElementID(coordinates.ID()).String(), + Comment: comment, + }, + // required, no attempt made to determine license information + LicenseConcluded: "NOASSERTION", + }, + Checksums: toFileChecksums(digests), + FileName: coordinates.RealPath, + FileTypes: toFileTypes(metadata), + }) + } + + // sort by real path then virtual path to ensure the result is stable across multiple runs + sort.SliceStable(results, func(i, j int) bool { + return results[i].FileName < results[j].FileName + }) + return results +} + +func toFileChecksums(digests []file.Digest) (checksums []model.Checksum) { + for _, digest := range digests { + checksums = append(checksums, model.Checksum{ + Algorithm: toChecksumAlgorithm(digest.Algorithm), + ChecksumValue: digest.Value, + }) + } + return checksums +} + +func toChecksumAlgorithm(algorithm string) string { + // basically, we need an uppercase version of our algorithm: + // https://github.com/spdx/spdx-spec/blob/development/v2.2.2/schemas/spdx-schema.json#L165 + return strings.ToUpper(algorithm) +} + +func toFileTypes(metadata *source.FileMetadata) (ty []string) { + if metadata == nil { + return nil + } + + mimeTypePrefix := strings.Split(metadata.MIMEType, "/")[0] + switch mimeTypePrefix { + case "image": + ty = append(ty, string(spdxhelpers.ImageFileType)) + case "video": + ty = append(ty, string(spdxhelpers.VideoFileType)) + case "application": + ty = append(ty, string(spdxhelpers.ApplicationFileType)) + case "text": + ty = append(ty, string(spdxhelpers.TextFileType)) + case "audio": + ty = append(ty, string(spdxhelpers.AudioFileType)) + } + + if internal.IsExecutable(metadata.MIMEType) { + ty = append(ty, string(spdxhelpers.BinaryFileType)) + } + + if internal.IsArchive(metadata.MIMEType) { + ty = append(ty, string(spdxhelpers.ArchiveFileType)) + } + + // TODO: add support for source, spdx, and documentation file types + if len(ty) == 0 { + ty = append(ty, string(spdxhelpers.OtherFileType)) + } + + return ty +} + +func toRelationships(relationships []artifact.Relationship) (result []model.Relationship) { + for _, r := range relationships { + exists, relationshipType, comment := lookupRelationship(r.Type) + + if !exists { + log.Warnf("unable to convert relationship from SPDX 2.2 JSON, dropping: %+v", r) + continue + } + + result = append(result, model.Relationship{ + SpdxElementID: model.ElementID(r.From.ID()).String(), + RelationshipType: relationshipType, + RelatedSpdxElement: model.ElementID(r.To.ID()).String(), + Comment: comment, + }) + } + return result +} + +func lookupRelationship(ty artifact.RelationshipType) (bool, spdxhelpers.RelationshipType, string) { + switch ty { + case artifact.ContainsRelationship: + return true, spdxhelpers.ContainsRelationship, "" + case artifact.OwnershipByFileOverlapRelationship: + return true, spdxhelpers.OtherRelationship, fmt.Sprintf("%s: indicates that the parent package claims ownership of a child package since the parent metadata indicates overlap with a location that a cataloger found the child package by", ty) + } + return false, "", "" +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/to_format_model_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/to_format_model_test.go new file mode 100644 index 0000000000000000000000000000000000000000..ee4c1ed11449d7ee650f336692d98aa2c9c83f2d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/to_format_model_test.go @@ -0,0 +1,257 @@ +package spdx22json + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + + "github.com/anchore/syft/syft/file" + + "github.com/anchore/syft/syft/artifact" + + "github.com/anchore/syft/internal/formats/common/spdxhelpers" + "github.com/anchore/syft/internal/formats/spdx22json/model" + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" +) + +func Test_toFileTypes(t *testing.T) { + + tests := []struct { + name string + metadata source.FileMetadata + expected []string + }{ + { + name: "application", + metadata: source.FileMetadata{ + MIMEType: "application/vnd.unknown", + }, + expected: []string{ + string(spdxhelpers.ApplicationFileType), + }, + }, + { + name: "archive", + metadata: source.FileMetadata{ + MIMEType: "application/zip", + }, + expected: []string{ + string(spdxhelpers.ApplicationFileType), + string(spdxhelpers.ArchiveFileType), + }, + }, + { + name: "audio", + metadata: source.FileMetadata{ + MIMEType: "audio/ogg", + }, + expected: []string{ + string(spdxhelpers.AudioFileType), + }, + }, + { + name: "video", + metadata: source.FileMetadata{ + MIMEType: "video/3gpp", + }, + expected: []string{ + string(spdxhelpers.VideoFileType), + }, + }, + { + name: "text", + metadata: source.FileMetadata{ + MIMEType: "text/html", + }, + expected: []string{ + string(spdxhelpers.TextFileType), + }, + }, + { + name: "image", + metadata: source.FileMetadata{ + MIMEType: "image/png", + }, + expected: []string{ + string(spdxhelpers.ImageFileType), + }, + }, + { + name: "binary", + metadata: source.FileMetadata{ + MIMEType: "application/x-sharedlib", + }, + expected: []string{ + string(spdxhelpers.ApplicationFileType), + string(spdxhelpers.BinaryFileType), + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.ElementsMatch(t, test.expected, toFileTypes(&test.metadata)) + }) + } +} + +func Test_lookupRelationship(t *testing.T) { + + tests := []struct { + input artifact.RelationshipType + exists bool + ty spdxhelpers.RelationshipType + comment string + }{ + { + input: artifact.ContainsRelationship, + exists: true, + ty: spdxhelpers.ContainsRelationship, + }, + { + input: artifact.OwnershipByFileOverlapRelationship, + exists: true, + ty: spdxhelpers.OtherRelationship, + comment: "ownership-by-file-overlap: indicates that the parent package claims ownership of a child package since the parent metadata indicates overlap with a location that a cataloger found the child package by", + }, + { + input: "made-up", + exists: false, + }, + } + for _, test := range tests { + t.Run(string(test.input), func(t *testing.T) { + exists, ty, comment := lookupRelationship(test.input) + assert.Equal(t, exists, test.exists) + assert.Equal(t, ty, test.ty) + assert.Equal(t, comment, test.comment) + }) + } +} + +func Test_toFileChecksums(t *testing.T) { + tests := []struct { + name string + digests []file.Digest + expected []model.Checksum + }{ + { + name: "empty", + }, + { + name: "has digests", + digests: []file.Digest{ + { + Algorithm: "SHA256", + Value: "deadbeefcafe", + }, + { + Algorithm: "md5", + Value: "meh", + }, + }, + expected: []model.Checksum{ + { + Algorithm: "SHA256", + ChecksumValue: "deadbeefcafe", + }, + { + Algorithm: "MD5", + ChecksumValue: "meh", + }, + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.ElementsMatch(t, test.expected, toFileChecksums(test.digests)) + }) + } +} + +func Test_fileIDsForPackage(t *testing.T) { + + p := pkg.Package{ + Name: "bogus", + } + + c := source.Coordinates{ + RealPath: "/path", + FileSystemID: "nowhere", + } + + tests := []struct { + name string + id string + relationships []artifact.Relationship + expected []string + }{ + { + name: "find file IDs for packages with package-file relationships", + id: model.ElementID(p.ID()).String(), + relationships: []artifact.Relationship{ + { + From: p, + To: c, + Type: artifact.ContainsRelationship, + }, + }, + expected: []string{ + model.ElementID(c.ID()).String(), + }, + }, + { + name: "ignore package-to-package", + id: model.ElementID(p.ID()).String(), + relationships: []artifact.Relationship{ + { + From: p, + To: p, + Type: artifact.ContainsRelationship, + }, + }, + expected: []string{}, + }, + { + name: "ignore file-to-file", + id: model.ElementID(p.ID()).String(), + relationships: []artifact.Relationship{ + { + From: c, + To: c, + Type: artifact.ContainsRelationship, + }, + }, + expected: []string{}, + }, + { + name: "ignore file-to-package", + id: model.ElementID(p.ID()).String(), + relationships: []artifact.Relationship{ + { + From: c, + To: p, + Type: artifact.ContainsRelationship, + }, + }, + expected: []string{}, + }, + { + name: "filter by relationship type", + id: model.ElementID(p.ID()).String(), + relationships: []artifact.Relationship{ + { + From: p, + To: c, + Type: artifact.OwnershipByFileOverlapRelationship, + }, + }, + expected: []string{}, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.ElementsMatch(t, test.expected, fileIDsForPackage(test.id, test.relationships)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/validator.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/validator.go new file mode 100644 index 0000000000000000000000000000000000000000..47366b1de5c07ea7b14634e09a4c9423099cc1ca --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22json/validator.go @@ -0,0 +1,10 @@ +package spdx22json + +import ( + "io" +) + +func validator(reader io.Reader) error { + _, err := decoder(reader) + return err +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/decoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/decoder.go new file mode 100644 index 0000000000000000000000000000000000000000..adce71c3604153d1bf8ae2a38dfc624424daf620 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/decoder.go @@ -0,0 +1,20 @@ +package spdx22tagvalue + +import ( + "fmt" + "io" + + "github.com/spdx/tools-golang/tvloader" + + "github.com/anchore/syft/internal/formats/common/spdxhelpers" + "github.com/anchore/syft/syft/sbom" +) + +func decoder(reader io.Reader) (*sbom.SBOM, error) { + doc, err := tvloader.Load2_2(reader) + if err != nil { + return nil, fmt.Errorf("unable to decode spdx-json: %w", err) + } + + return spdxhelpers.ToSyftModel(doc) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..6f9fdf5d843001e7e30785f49e044719bbfd128d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/encoder.go @@ -0,0 +1,13 @@ +package spdx22tagvalue + +import ( + "io" + + "github.com/anchore/syft/syft/sbom" + "github.com/spdx/tools-golang/tvsaver" +) + +func encoder(output io.Writer, s sbom.SBOM) error { + model := toFormatModel(s) + return tvsaver.Save2_2(model, output) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..83992655d9c412f93ea42c11412f73b71dbd05c5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/encoder_test.go @@ -0,0 +1,78 @@ +package spdx22tagvalue + +import ( + "flag" + "regexp" + "testing" + + "github.com/anchore/syft/internal/formats/common/testutils" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" +) + +var updateSpdxTagValue = flag.Bool("update-spdx-tv", false, "update the *.golden files for spdx-tv encoders") + +func TestSPDXTagValueDirectoryEncoder(t *testing.T) { + + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + testutils.DirectoryInput(t), + *updateSpdxTagValue, + spdxTagValueRedactor, + ) +} + +func TestSPDXTagValueImageEncoder(t *testing.T) { + testImage := "image-simple" + testutils.AssertEncoderAgainstGoldenImageSnapshot(t, + Format(), + testutils.ImageInput(t, testImage, testutils.FromSnapshot()), + testImage, + *updateSpdxTagValue, + spdxTagValueRedactor, + ) +} + +func TestSPDXJSONSPDXIDs(t *testing.T) { + var pkgs []pkg.Package + for _, name := range []string{"some/slashes", "@at-sign", "under_scores"} { + p := pkg.Package{ + Name: name, + } + p.SetID() + pkgs = append(pkgs, p) + } + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: pkg.NewCatalog(pkgs...), + }, + Relationships: nil, + Source: source.Metadata{ + Scheme: source.DirectoryScheme, + }, + Descriptor: sbom.Descriptor{ + Name: "syft", + Version: "v0.42.0-bogus", + Configuration: map[string]string{ + "config-key": "config-value", + }, + }, + }, + *updateSpdxTagValue, + spdxTagValueRedactor, + ) +} + +func spdxTagValueRedactor(s []byte) []byte { + // each SBOM reports the time it was generated, which is not useful during snapshot testing + s = regexp.MustCompile(`Created: .*`).ReplaceAll(s, []byte("redacted")) + + // each SBOM reports a unique documentNamespace when generated, this is not useful for snapshot testing + s = regexp.MustCompile(`DocumentNamespace: https://anchore.com/syft/.*`).ReplaceAll(s, []byte("redacted")) + + // the license list will be updated periodically, the value here should not be directly tested in snapshot tests + return regexp.MustCompile(`LicenseListVersion: .*`).ReplaceAll(s, []byte("redacted")) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/format.go new file mode 100644 index 0000000000000000000000000000000000000000..8bd5856c5f84fb1a18d988a54219959ecc719381 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/format.go @@ -0,0 +1,17 @@ +package spdx22tagvalue + +import ( + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "spdx-2-tag-value" + +// note: this format is LOSSY relative to the syftjson formation, which means that decoding and validation is not supported at this time +func Format() sbom.Format { + return sbom.NewFormat( + ID, + encoder, + decoder, + validator, + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/Dockerfile b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..79cfa759e357be9628894dea6332a0e6a2c33bb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/Dockerfile @@ -0,0 +1,4 @@ +# Note: changes to this file will result in updating several test values. Consider making a new image fixture instead of editing this one. +FROM scratch +ADD file-1.txt /somefile-1.txt +ADD file-2.txt /somefile-2.txt diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/file-1.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..985d3408e98cb9f41c01376c698451fdef0e4b32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/file-1.txt @@ -0,0 +1 @@ +this file has contents \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/file-2.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..396d08bbc72f810ec6d057d1713a84a75d1cd542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/image-simple/file-2.txt @@ -0,0 +1 @@ +file-2 contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXJSONSPDXIDs.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXJSONSPDXIDs.golden new file mode 100644 index 0000000000000000000000000000000000000000..e9e540f62cecc8c9191348fbf27552226df825c4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXJSONSPDXIDs.golden @@ -0,0 +1,40 @@ +SPDXVersion: SPDX-2.2 +DataLicense: CC0-1.0 +SPDXID: SPDXRef-DOCUMENT +DocumentName: . +DocumentNamespace: https://anchore.com/syft/dir/bdb67358-651c-4dd8-b5ee-5318936eb16a +LicenseListVersion: 3.17 +Creator: Organization: Anchore, Inc +Creator: Tool: syft-v0.42.0-bogus +Created: 2022-06-07T19:33:39Z + +##### Package: @at-sign + +PackageName: @at-sign +SPDXID: SPDXRef-Package---at-sign-739e4f0d93fb8298 +PackageDownloadLocation: NOASSERTION +FilesAnalyzed: false +PackageLicenseConcluded: NONE +PackageLicenseDeclared: NONE +PackageCopyrightText: NOASSERTION + +##### Package: some/slashes + +PackageName: some/slashes +SPDXID: SPDXRef-Package--some-slashes-26db06648b24bff9 +PackageDownloadLocation: NOASSERTION +FilesAnalyzed: false +PackageLicenseConcluded: NONE +PackageLicenseDeclared: NONE +PackageCopyrightText: NOASSERTION + +##### Package: under_scores + +PackageName: under_scores +SPDXID: SPDXRef-Package--under-scores-250cbfefcdea318b +PackageDownloadLocation: NOASSERTION +FilesAnalyzed: false +PackageLicenseConcluded: NONE +PackageLicenseDeclared: NONE +PackageCopyrightText: NOASSERTION + diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXTagValueDirectoryEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXTagValueDirectoryEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..83e333e4b9dd498bb1da528ee21a90f3c20e16a0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXTagValueDirectoryEncoder.golden @@ -0,0 +1,36 @@ +SPDXVersion: SPDX-2.2 +DataLicense: CC0-1.0 +SPDXID: SPDXRef-DOCUMENT +DocumentName: /some/path +DocumentNamespace: https://anchore.com/syft/dir/some/path-c6b20d03-1478-4513-9feb-1ec427d4b547 +LicenseListVersion: 3.17 +Creator: Organization: Anchore, Inc +Creator: Tool: syft-v0.42.0-bogus +Created: 2022-05-24T22:51:02Z + +##### Package: package-2 + +PackageName: package-2 +SPDXID: SPDXRef-Package-deb-package-2-ceda99598967ae8d +PackageVersion: 2.0.1 +PackageDownloadLocation: NOASSERTION +FilesAnalyzed: false +PackageLicenseConcluded: NONE +PackageLicenseDeclared: NONE +PackageCopyrightText: NOASSERTION +ExternalRef: SECURITY cpe23Type cpe:2.3:*:some:package:2:*:*:*:*:*:*:* +ExternalRef: PACKAGE_MANAGER purl pkg:deb/debian/package-2@2.0.1 + +##### Package: package-1 + +PackageName: package-1 +SPDXID: SPDXRef-Package-python-package-1-b85dbb4e6ece5082 +PackageVersion: 1.0.1 +PackageDownloadLocation: NOASSERTION +FilesAnalyzed: false +PackageLicenseConcluded: MIT +PackageLicenseDeclared: MIT +PackageCopyrightText: NOASSERTION +ExternalRef: SECURITY cpe23Type cpe:2.3:*:some:package:2:*:*:*:*:*:*:* +ExternalRef: PACKAGE_MANAGER purl a-purl-2 + diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXTagValueImageEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXTagValueImageEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..aae5ebf530ff5dd087fcf083083d3623032529dd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/TestSPDXTagValueImageEncoder.golden @@ -0,0 +1,36 @@ +SPDXVersion: SPDX-2.2 +DataLicense: CC0-1.0 +SPDXID: SPDXRef-DOCUMENT +DocumentName: user-image-input +DocumentNamespace: https://anchore.com/syft/image/user-image-input-12a877bc-fe9b-40ef-aa9c-4d34f108d0d6 +LicenseListVersion: 3.17 +Creator: Organization: Anchore, Inc +Creator: Tool: syft-v0.42.0-bogus +Created: 2022-05-24T22:51:02Z + +##### Package: package-2 + +PackageName: package-2 +SPDXID: SPDXRef-Package-deb-package-2-ae77680e9b1d087e +PackageVersion: 2.0.1 +PackageDownloadLocation: NOASSERTION +FilesAnalyzed: false +PackageLicenseConcluded: NONE +PackageLicenseDeclared: NONE +PackageCopyrightText: NOASSERTION +ExternalRef: SECURITY cpe23Type cpe:2.3:*:some:package:2:*:*:*:*:*:*:* +ExternalRef: PACKAGE_MANAGER purl pkg:deb/debian/package-2@2.0.1 + +##### Package: package-1 + +PackageName: package-1 +SPDXID: SPDXRef-Package-python-package-1-2a46171f91c8d4bc +PackageVersion: 1.0.1 +PackageDownloadLocation: NOASSERTION +FilesAnalyzed: false +PackageLicenseConcluded: MIT +PackageLicenseDeclared: MIT +PackageCopyrightText: NOASSERTION +ExternalRef: SECURITY cpe23Type cpe:2.3:*:some:package:1:*:*:*:*:*:*:* +ExternalRef: PACKAGE_MANAGER purl a-purl-1 + diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden new file mode 100644 index 0000000000000000000000000000000000000000..3d93b6d3ad1c86098e440073bcf8cfdf5eea53e1 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden differ diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/to_format_model.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/to_format_model.go new file mode 100644 index 0000000000000000000000000000000000000000..41296665ee26d6da7395ccc7d10c4021044c16a5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/to_format_model.go @@ -0,0 +1,293 @@ +package spdx22tagvalue + +import ( + "fmt" + "time" + + "github.com/anchore/syft/syft/sbom" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/formats/common/spdxhelpers" + "github.com/anchore/syft/internal/spdxlicense" + "github.com/anchore/syft/syft/pkg" + "github.com/spdx/tools-golang/spdx" +) + +// toFormatModel creates and populates a new JSON document struct that follows the SPDX 2.2 spec from the given cataloging results. +// +//nolint:funlen +func toFormatModel(s sbom.SBOM) *spdx.Document2_2 { + name, namespace := spdxhelpers.DocumentNameAndNamespace(s.Source) + + return &spdx.Document2_2{ + CreationInfo: &spdx.CreationInfo2_2{ + // 2.1: SPDX Version; should be in the format "SPDX-2.2" + // Cardinality: mandatory, one + SPDXVersion: "SPDX-2.2", + + // 2.2: Data License; should be "CC0-1.0" + // Cardinality: mandatory, one + DataLicense: "CC0-1.0", + + // 2.3: SPDX Identifier; should be "DOCUMENT" to represent mandatory identifier of SPDXRef-DOCUMENT + // Cardinality: mandatory, one + SPDXIdentifier: spdx.ElementID("DOCUMENT"), + + // 2.4: Document Name + // Cardinality: mandatory, one + DocumentName: name, + + // 2.5: Document Namespace + // Cardinality: mandatory, one + // Purpose: Provide an SPDX document specific namespace as a unique absolute Uniform Resource + // Identifier (URI) as specified in RFC-3986, with the exception of the ‘#’ delimiter. The SPDX + // Document URI cannot contain a URI "part" (e.g. the "#" character), since the ‘#’ is used in SPDX + // element URIs (packages, files, snippets, etc) to separate the document namespace from the + // element’s SPDX identifier. Additionally, a scheme (e.g. “https:”) is required. + + // The URI must be unique for the SPDX document including the specific version of the SPDX document. + // If the SPDX document is updated, thereby creating a new version, a new URI for the updated + // document must be used. There can only be one URI for an SPDX document and only one SPDX document + // for a given URI. + + // Note that the URI does not have to be accessible. It is only intended to provide a unique ID. + // In many cases, the URI will point to a web accessible document, but this should not be assumed + // to be the case. + + DocumentNamespace: namespace, + + // 2.6: External Document References + // Cardinality: optional, one or many + ExternalDocumentReferences: nil, + + // 2.7: License List Version + // Cardinality: optional, one + LicenseListVersion: spdxlicense.Version, + + // 2.8: Creators: may have multiple keys for Person, Organization + // and/or Tool + // Cardinality: mandatory, one or many + CreatorPersons: nil, + CreatorOrganizations: []string{"Anchore, Inc"}, + CreatorTools: []string{internal.ApplicationName + "-" + s.Descriptor.Version}, + + // 2.9: Created: data format YYYY-MM-DDThh:mm:ssZ + // Cardinality: mandatory, one + Created: time.Now().UTC().Format(time.RFC3339), + + // 2.10: Creator Comment + // Cardinality: optional, one + CreatorComment: "", + + // 2.11: Document Comment + // Cardinality: optional, one + DocumentComment: "", + }, + Packages: toFormatPackages(s.Artifacts.PackageCatalog), + } +} + +// packages populates all Package Information from the package Catalog (see https://spdx.github.io/spdx-spec/3-package-information/) +// +//nolint:funlen +func toFormatPackages(catalog *pkg.Catalog) map[spdx.ElementID]*spdx.Package2_2 { + results := make(map[spdx.ElementID]*spdx.Package2_2) + + for _, p := range catalog.Sorted() { + // name should be guaranteed to be unique, but semantically useful and stable + id := spdxhelpers.SanitizeElementID(fmt.Sprintf("Package-%+v-%s-%s", p.Type, p.Name, p.ID())) + + // If the Concluded License is not the same as the Declared License, a written explanation should be provided + // in the Comments on License field (section 3.16). With respect to NOASSERTION, a written explanation in + // the Comments on License field (section 3.16) is preferred. + license := spdxhelpers.License(p) + + filesAnalyzed := false + checksums := make(map[spdx.ChecksumAlgorithm]spdx.Checksum) + + // If the pkg type is Java we have attempted to generated a digest + // FilesAnalyzed should be true in this case + if p.MetadataType == pkg.JavaMetadataType { + javaMetadata := p.Metadata.(pkg.JavaMetadata) + if len(javaMetadata.ArchiveDigests) > 0 { + filesAnalyzed = true + for _, digest := range javaMetadata.ArchiveDigests { + checksums[spdx.ChecksumAlgorithm(digest.Algorithm)] = spdx.Checksum{ + Algorithm: spdx.ChecksumAlgorithm(digest.Algorithm), + Value: digest.Value, + } + } + } + } + + results[spdx.ElementID(id)] = &spdx.Package2_2{ + + // NOT PART OF SPEC + // flag: does this "package" contain files that were in fact "unpackaged", + // e.g. included directly in the Document without being in a Package? + IsUnpackaged: false, + + // 3.1: Package Name + // Cardinality: mandatory, one + PackageName: p.Name, + + // 3.2: Package SPDX Identifier: "SPDXRef-[idstring]" + // Cardinality: mandatory, one + PackageSPDXIdentifier: spdx.ElementID(id), + + // 3.3: Package Version + // Cardinality: optional, one + PackageVersion: p.Version, + + // 3.4: Package File Name + // Cardinality: optional, one + PackageFileName: "", + + // 3.5: Package Supplier: may have single result for either Person or Organization, + // or NOASSERTION + // Cardinality: optional, one + PackageSupplierPerson: "", + PackageSupplierOrganization: "", + PackageSupplierNOASSERTION: false, + + // 3.6: Package Originator: may have single result for either Person or Organization, + // or NOASSERTION + // Cardinality: optional, one + PackageOriginatorPerson: "", + PackageOriginatorOrganization: "", + PackageOriginatorNOASSERTION: false, + + // 3.7: Package Download Location + // Cardinality: mandatory, one + // NONE if there is no download location whatsoever. + // NOASSERTION if: + // (i) the SPDX file creator has attempted to but cannot reach a reasonable objective determination; + // (ii) the SPDX file creator has made no attempt to determine this field; or + // (iii) the SPDX file creator has intentionally provided no information (no meaning should be implied by doing so). + PackageDownloadLocation: "NOASSERTION", + + // 3.8: FilesAnalyzed + // Cardinality: optional, one; default value is "true" if omitted + + // Purpose: Indicates whether the file content of this package has been available for or subjected to + // analysis when creating the SPDX document. If false, indicates packages that represent metadata or + // URI references to a project, product, artifact, distribution or a component. If false, the package + // must not contain any files. + + // Intent: A package can refer to a project, product, artifact, distribution or a component that is + // external to the SPDX document. + FilesAnalyzed: filesAnalyzed, + // NOT PART OF SPEC: did FilesAnalyzed tag appear? + IsFilesAnalyzedTagPresent: true, + + // 3.9: Package Verification Code + // Cardinality: mandatory, one if filesAnalyzed is true / omitted; + // zero (must be omitted) if filesAnalyzed is false + PackageVerificationCode: "", + // Spec also allows specifying a single file to exclude from the + // verification code algorithm; intended to enable exclusion of + // the SPDX document file itself. + PackageVerificationCodeExcludedFile: "", + + // 3.10: Package Checksum: may have keys for SHA1, SHA256 and/or MD5 + // Cardinality: optional, one or many + + // 3.10.1 Purpose: Provide an independently reproducible mechanism that permits unique identification of + // a specific package that correlates to the data in this SPDX file. This identifier enables a recipient + // to determine if any file in the original package has been changed. If the SPDX file is to be included + // in a package, this value should not be calculated. The SHA-1 algorithm will be used to provide the + // checksum by default. + PackageChecksums: checksums, + + // note: based on the purpose above no discovered checksums should be provided, but instead, only + // tool-derived checksums. + //FIXME: this got removed between 0.1.0 and 0.2.0, is this right? it looks like + // it wasn't being used anyway + //PackageChecksumSHA1: "", + //PackageChecksumSHA256: "", + //PackageChecksumMD5: "", + + // 3.11: Package Home Page + // Cardinality: optional, one + PackageHomePage: "", + + // 3.12: Source Information + // Cardinality: optional, one + PackageSourceInfo: "", + + // 3.13: Concluded License: SPDX License Expression, "NONE" or "NOASSERTION" + // Cardinality: mandatory, one + // Purpose: Contain the license the SPDX file creator has concluded as governing the + // package or alternative values, if the governing license cannot be determined. + PackageLicenseConcluded: license, + + // 3.14: All Licenses Info from Files: SPDX License Expression, "NONE" or "NOASSERTION" + // Cardinality: mandatory, one or many if filesAnalyzed is true / omitted; + // zero (must be omitted) if filesAnalyzed is false + PackageLicenseInfoFromFiles: nil, + + // 3.15: Declared License: SPDX License Expression, "NONE" or "NOASSERTION" + // Cardinality: mandatory, one + // Purpose: List the licenses that have been declared by the authors of the package. + // Any license information that does not originate from the package authors, e.g. license + // information from a third party repository, should not be included in this field. + PackageLicenseDeclared: license, + + // 3.16: Comments on License + // Cardinality: optional, one + PackageLicenseComments: "", + + // 3.17: Copyright Text: copyright notice(s) text, "NONE" or "NOASSERTION" + // Cardinality: mandatory, one + // Purpose: IdentifyFormat the copyright holders of the package, as well as any dates present. This will be a free form text field extracted from package information files. The options to populate this field are limited to: + // + // Any text related to a copyright notice, even if not complete; + // NONE if the package contains no copyright information whatsoever; or + // NOASSERTION, if + // (i) the SPDX document creator has made no attempt to determine this field; or + // (ii) the SPDX document creator has intentionally provided no information (no meaning should be implied by doing so). + // + PackageCopyrightText: "NOASSERTION", + + // 3.18: Package Summary Description + // Cardinality: optional, one + PackageSummary: "", + + // 3.19: Package Detailed Description + // Cardinality: optional, one + PackageDescription: "", + + // 3.20: Package Comment + // Cardinality: optional, one + PackageComment: "", + + // 3.21: Package External Reference + // Cardinality: optional, one or many + PackageExternalReferences: formatSPDXExternalRefs(p), + + // 3.22: Package External Reference Comment + // Cardinality: conditional (optional, one) for each External Reference + // contained within PackageExternalReference2_1 struct, if present + + // 3.23: Package Attribution Text + // Cardinality: optional, one or many + PackageAttributionTexts: nil, + + // Files contained in this Package + Files: nil, + } + } + return results +} + +func formatSPDXExternalRefs(p pkg.Package) (refs []*spdx.PackageExternalReference2_2) { + for _, ref := range spdxhelpers.ExternalRefs(p) { + refs = append(refs, &spdx.PackageExternalReference2_2{ + Category: string(ref.ReferenceCategory), + RefType: string(ref.ReferenceType), + Locator: ref.ReferenceLocator, + ExternalRefComment: ref.Comment, + }) + } + return refs +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/validator.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/validator.go new file mode 100644 index 0000000000000000000000000000000000000000..1a5c078bc3363d448c323db657fa8f23d57aaa3d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/spdx22tagvalue/validator.go @@ -0,0 +1,10 @@ +package spdx22tagvalue + +import ( + "io" +) + +func validator(reader io.Reader) error { + _, err := decoder(reader) + return err +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/decoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/decoder.go new file mode 100644 index 0000000000000000000000000000000000000000..95f16fdd22340e01d145ec99639c71b31809b199 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/decoder.go @@ -0,0 +1,23 @@ +package syftjson + +import ( + "encoding/json" + "fmt" + "io" + + "github.com/anchore/syft/syft/sbom" + + "github.com/anchore/syft/internal/formats/syftjson/model" +) + +func decoder(reader io.Reader) (*sbom.SBOM, error) { + dec := json.NewDecoder(reader) + + var doc model.Document + err := dec.Decode(&doc) + if err != nil { + return nil, fmt.Errorf("unable to decode syft-json: %w", err) + } + + return toSyftModel(doc) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/decoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/decoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..3dc069fc2bdaf03adb966f3f18438ebe344e6bc7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/decoder_test.go @@ -0,0 +1,50 @@ +package syftjson + +import ( + "bytes" + "strings" + "testing" + + "github.com/anchore/syft/internal/formats/common/testutils" + "github.com/go-test/deep" + "github.com/stretchr/testify/assert" +) + +func TestEncodeDecodeCycle(t *testing.T) { + testImage := "image-simple" + originalSBOM := testutils.ImageInput(t, testImage) + + var buf bytes.Buffer + assert.NoError(t, encoder(&buf, originalSBOM)) + + actualSBOM, err := decoder(bytes.NewReader(buf.Bytes())) + assert.NoError(t, err) + + for _, d := range deep.Equal(originalSBOM.Source, actualSBOM.Source) { + if strings.HasSuffix(d, " != []") { + // semantically the same + continue + } + t.Errorf("metadata difference: %+v", d) + } + + actualPackages := actualSBOM.Artifacts.PackageCatalog.Sorted() + for idx, p := range originalSBOM.Artifacts.PackageCatalog.Sorted() { + if !assert.Equal(t, p.Name, actualPackages[idx].Name) { + t.Errorf("different package at idx=%d: %s vs %s", idx, p.Name, actualPackages[idx].Name) + continue + } + + for _, d := range deep.Equal(p, actualPackages[idx]) { + if strings.Contains(d, ".VirtualPath: ") { + // location.Virtual path is not exposed in the json output + continue + } + if strings.HasSuffix(d, " != []") { + // semantically the same + continue + } + t.Errorf("package difference (%s): %+v", p.Name, d) + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..ae52818f34419bd16bfc3c7507cf8c0fced509f4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/encoder.go @@ -0,0 +1,19 @@ +package syftjson + +import ( + "encoding/json" + "io" + + "github.com/anchore/syft/syft/sbom" +) + +func encoder(output io.Writer, s sbom.SBOM) error { + doc := ToFormatModel(s) + + enc := json.NewEncoder(output) + // prevent > and < from being escaped in the payload + enc.SetEscapeHTML(false) + enc.SetIndent("", " ") + + return enc.Encode(&doc) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..9d8087d5e84de6147eda7a53f47c21fdd5e5055e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/encoder_test.go @@ -0,0 +1,205 @@ +package syftjson + +import ( + "flag" + "testing" + + "github.com/anchore/syft/syft/file" + + "github.com/anchore/syft/syft/artifact" + + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" + + "github.com/anchore/syft/internal/formats/common/testutils" +) + +var updateJson = flag.Bool("update-json", false, "update the *.golden files for json encoders") + +func TestDirectoryEncoder(t *testing.T) { + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + testutils.DirectoryInput(t), + *updateJson, + ) +} + +func TestImageEncoder(t *testing.T) { + testImage := "image-simple" + testutils.AssertEncoderAgainstGoldenImageSnapshot(t, + Format(), + testutils.ImageInput(t, testImage, testutils.FromSnapshot()), + testImage, + *updateJson, + ) +} + +func TestEncodeFullJSONDocument(t *testing.T) { + catalog := pkg.NewCatalog() + + p1 := pkg.Package{ + Name: "package-1", + Version: "1.0.1", + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a/place/a", + }, + }, + ), + Type: pkg.PythonPkg, + FoundBy: "the-cataloger-1", + Language: pkg.Python, + MetadataType: pkg.PythonPackageMetadataType, + Licenses: []string{"MIT"}, + Metadata: pkg.PythonPackageMetadata{ + Name: "package-1", + Version: "1.0.1", + Files: []pkg.PythonFileRecord{}, + }, + PURL: "a-purl-1", + CPEs: []pkg.CPE{ + pkg.MustCPE("cpe:2.3:*:some:package:1:*:*:*:*:*:*:*"), + }, + } + + p2 := pkg.Package{ + Name: "package-2", + Version: "2.0.1", + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/b/place/b", + }, + }, + ), + Type: pkg.DebPkg, + FoundBy: "the-cataloger-2", + MetadataType: pkg.DpkgMetadataType, + Metadata: pkg.DpkgMetadata{ + Package: "package-2", + Version: "2.0.1", + Files: []pkg.DpkgFileRecord{}, + }, + PURL: "a-purl-2", + CPEs: []pkg.CPE{ + pkg.MustCPE("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"), + }, + } + + catalog.Add(p1) + catalog.Add(p2) + + s := sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: catalog, + FileMetadata: map[source.Coordinates]source.FileMetadata{ + source.NewLocation("/a/place").Coordinates: { + Mode: 0775, + Type: "directory", + UserID: 0, + GroupID: 0, + }, + source.NewLocation("/a/place/a").Coordinates: { + Mode: 0775, + Type: "regularFile", + UserID: 0, + GroupID: 0, + }, + source.NewLocation("/b").Coordinates: { + Mode: 0775, + Type: "symbolicLink", + LinkDestination: "/c", + UserID: 0, + GroupID: 0, + }, + source.NewLocation("/b/place/b").Coordinates: { + Mode: 0644, + Type: "regularFile", + UserID: 1, + GroupID: 2, + }, + }, + FileDigests: map[source.Coordinates][]file.Digest{ + source.NewLocation("/a/place/a").Coordinates: { + { + Algorithm: "sha256", + Value: "366a3f5653e34673b875891b021647440d0127c2ef041e3b1a22da2a7d4f3703", + }, + }, + source.NewLocation("/b/place/b").Coordinates: { + { + Algorithm: "sha256", + Value: "1b3722da2a7d90d033b87581a2a3f12021647445653e34666ef041e3b4f3707c", + }, + }, + }, + FileContents: map[source.Coordinates]string{ + source.NewLocation("/a/place/a").Coordinates: "the-contents", + }, + LinuxDistribution: &linux.Release{ + ID: "redhat", + Version: "7", + VersionID: "7", + IDLike: []string{ + "rhel", + }, + }, + }, + Relationships: []artifact.Relationship{ + { + From: p1, + To: p2, + Type: artifact.OwnershipByFileOverlapRelationship, + Data: map[string]string{ + "file": "path", + }, + }, + }, + Source: source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: source.ImageMetadata{ + UserInput: "user-image-input", + ID: "sha256:c2b46b4eb06296933b7cf0722683964e9ecbd93265b9ef6ae9642e3952afbba0", + ManifestDigest: "sha256:2731251dc34951c0e50fcc643b4c5f74922dad1a5d98f302b504cf46cd5d9368", + MediaType: "application/vnd.docker.distribution.manifest.v2+json", + Tags: []string{ + "stereoscope-fixture-image-simple:85066c51088bdd274f7a89e99e00490f666c49e72ffc955707cd6e18f0e22c5b", + }, + Size: 38, + Layers: []source.LayerMetadata{ + { + MediaType: "application/vnd.docker.image.rootfs.diff.tar.gzip", + Digest: "sha256:3de16c5b8659a2e8d888b8ded8427be7a5686a3c8c4e4dd30de20f362827285b", + Size: 22, + }, + { + MediaType: "application/vnd.docker.image.rootfs.diff.tar.gzip", + Digest: "sha256:366a3f5653e34673b875891b021647440d0127c2ef041e3b1a22da2a7d4f3703", + Size: 16, + }, + }, + RawManifest: []byte("eyJzY2hlbWFWZXJzaW9uIjoyLCJtZWRpYVR5cGUiOiJh..."), + RawConfig: []byte("eyJhcmNoaXRlY3R1cmUiOiJhbWQ2NCIsImNvbmZp..."), + RepoDigests: []string{}, + }, + }, + Descriptor: sbom.Descriptor{ + Name: "syft", + Version: "v0.42.0-bogus", + // the application configuration should be persisted here, however, we do not want to import + // the application configuration in this package (it's reserved only for ingestion by the cmd package) + Configuration: map[string]string{ + "config-key": "config-value", + }, + }, + } + + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + s, + *updateJson, + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/format.go new file mode 100644 index 0000000000000000000000000000000000000000..c595699b79342dda40022d9bd9a1f87059c11eab --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/format.go @@ -0,0 +1,16 @@ +package syftjson + +import ( + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "syft-3-json" + +func Format() sbom.Format { + return sbom.NewFormat( + ID, + encoder, + decoder, + validator, + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/document.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/document.go new file mode 100644 index 0000000000000000000000000000000000000000..eb41ec79f11693f4706be876f7c9200ce7bf3401 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/document.go @@ -0,0 +1,25 @@ +package model + +// Document represents the syft cataloging findings as a JSON document +type Document struct { + Artifacts []Package `json:"artifacts"` // Artifacts is the list of packages discovered and placed into the catalog + ArtifactRelationships []Relationship `json:"artifactRelationships"` + Files []File `json:"files,omitempty"` // note: must have omitempty + Secrets []Secrets `json:"secrets,omitempty"` // note: must have omitempty + Source Source `json:"source"` // Source represents the original object that was cataloged + Distro LinuxRelease `json:"distro"` // Distro represents the Linux distribution that was detected from the source + Descriptor Descriptor `json:"descriptor"` // Descriptor is a block containing self-describing information about syft + Schema Schema `json:"schema"` // Schema is a block reserved for defining the version for the shape of this JSON document and where to find the schema document to validate the shape +} + +// Descriptor describes what created the document as well as surrounding metadata +type Descriptor struct { + Name string `json:"name"` + Version string `json:"version"` + Configuration interface{} `json:"configuration,omitempty"` +} + +type Schema struct { + Version string `json:"version"` + URL string `json:"url"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/file.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/file.go new file mode 100644 index 0000000000000000000000000000000000000000..be2c88df3bbb660ac05c4df4ce78cdea6fc51015 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/file.go @@ -0,0 +1,25 @@ +package model + +import ( + "github.com/anchore/syft/syft/file" + + "github.com/anchore/syft/syft/source" +) + +type File struct { + ID string `json:"id"` + Location source.Coordinates `json:"location"` + Metadata *FileMetadataEntry `json:"metadata,omitempty"` + Contents string `json:"contents,omitempty"` + Digests []file.Digest `json:"digests,omitempty"` + Classifications []file.Classification `json:"classifications,omitempty"` +} + +type FileMetadataEntry struct { + Mode int `json:"mode"` + Type source.FileType `json:"type"` + LinkDestination string `json:"linkDestination,omitempty"` + UserID int `json:"userID"` + GroupID int `json:"groupID"` + MIMEType string `json:"mimeType"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/linux_release.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/linux_release.go new file mode 100644 index 0000000000000000000000000000000000000000..3aa79a3d7a9cd077ccc8d2fafceb44870f909e5e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/linux_release.go @@ -0,0 +1,42 @@ +package model + +import ( + "encoding/json" +) + +type IDLikes []string + +type LinuxRelease struct { + PrettyName string `json:"prettyName,omitempty"` + Name string `json:"name,omitempty"` + ID string `json:"id,omitempty"` + IDLike IDLikes `json:"idLike,omitempty"` + Version string `json:"version,omitempty"` + VersionID string `json:"versionID,omitempty"` + VersionCodename string `json:"versionCodename,omitempty"` + BuildID string `json:"buildID,omitempty"` + ImageID string `json:"imageID,omitempty"` + ImageVersion string `json:"imageVersion,omitempty"` + Variant string `json:"variant,omitempty"` + VariantID string `json:"variantID,omitempty"` + HomeURL string `json:"homeURL,omitempty"` + SupportURL string `json:"supportURL,omitempty"` + BugReportURL string `json:"bugReportURL,omitempty"` + PrivacyPolicyURL string `json:"privacyPolicyURL,omitempty"` + CPEName string `json:"cpeName,omitempty"` +} + +func (s *IDLikes) UnmarshalJSON(data []byte) error { + var str string + var strSlice []string + + // we support unmarshalling from a single value to support syft json schema v2 + if err := json.Unmarshal(data, &str); err == nil { + *s = []string{str} + } else if err := json.Unmarshal(data, &strSlice); err == nil { + *s = strSlice + } else { + return err + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/linux_release_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/linux_release_test.go new file mode 100644 index 0000000000000000000000000000000000000000..66487f59d0d74fd4c255316e312f4e86f5ebc5aa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/linux_release_test.go @@ -0,0 +1,47 @@ +package model + +import ( + "encoding/json" + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func TestIDLikes_UnmarshalJSON(t *testing.T) { + tests := []struct { + name string + data interface{} + expected IDLikes + }{ + { + name: "single string", + data: "well hello there!", + expected: IDLikes{ + "well hello there!", + }, + }, + { + name: "multiple strings", + data: []string{ + "well hello there!", + "...hello there, john!", + }, + expected: IDLikes{ + "well hello there!", + "...hello there, john!", + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + data, err := json.Marshal(&tt.data) + require.NoError(t, err) + + var obj IDLikes + require.NoError(t, json.Unmarshal(data, &obj)) + + assert.Equal(t, tt.expected, obj) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/package.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/package.go new file mode 100644 index 0000000000000000000000000000000000000000..12ef3c335452a45682fb4116da86654b01d334da --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/package.go @@ -0,0 +1,195 @@ +package model + +import ( + "encoding/json" + "errors" + "fmt" + + "github.com/anchore/syft/syft/source" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" +) + +var errUnknownMetadataType = errors.New("unknown metadata type") + +// Package represents a pkg.Package object specialized for JSON marshaling and unmarshalling. +type Package struct { + PackageBasicData + PackageCustomData +} + +// PackageBasicData contains non-ambiguous values (type-wise) from pkg.Package. +type PackageBasicData struct { + ID string `json:"id"` + Name string `json:"name"` + Version string `json:"version"` + Type pkg.Type `json:"type"` + FoundBy string `json:"foundBy"` + Locations []source.Coordinates `json:"locations"` + Licenses []string `json:"licenses"` + Language pkg.Language `json:"language"` + CPEs []string `json:"cpes"` + PURL string `json:"purl"` +} + +// PackageCustomData contains ambiguous values (type-wise) from pkg.Package. +type PackageCustomData struct { + MetadataType pkg.MetadataType `json:"metadataType,omitempty"` + Metadata interface{} `json:"metadata,omitempty"` +} + +// packageMetadataUnpacker is all values needed from Package to disambiguate ambiguous fields during json unmarshaling. +type packageMetadataUnpacker struct { + MetadataType pkg.MetadataType `json:"metadataType"` + Metadata json.RawMessage `json:"metadata"` +} + +func (p *packageMetadataUnpacker) String() string { + return fmt.Sprintf("metadataType: %s, metadata: %s", p.MetadataType, string(p.Metadata)) +} + +// UnmarshalJSON is a custom unmarshaller for handling basic values and values with ambiguous types. +func (p *Package) UnmarshalJSON(b []byte) error { + var basic PackageBasicData + if err := json.Unmarshal(b, &basic); err != nil { + return err + } + p.PackageBasicData = basic + + var unpacker packageMetadataUnpacker + if err := json.Unmarshal(b, &unpacker); err != nil { + log.Warnf("failed to unmarshall into packageMetadataUnpacker: %v", err) + return err + } + + err := unpackMetadata(p, unpacker) + if errors.Is(err, errUnknownMetadataType) { + log.Warnf("unknown package metadata type=%q for packageID=%q", p.MetadataType, p.ID) + return nil + } + + return err +} + +//nolint:funlen,gocognit,gocyclo +func unpackMetadata(p *Package, unpacker packageMetadataUnpacker) error { + p.MetadataType = pkg.CleanMetadataType(unpacker.MetadataType) + + switch p.MetadataType { + case "": + // there is no metadata, skip + break + case pkg.AlpmMetadataType: + var payload pkg.AlpmMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.ApkMetadataType: + var payload pkg.ApkMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.RpmMetadataType: + var payload pkg.RpmMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.DpkgMetadataType: + var payload pkg.DpkgMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.JavaMetadataType: + var payload pkg.JavaMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.RustCargoPackageMetadataType: + var payload pkg.CargoPackageMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.GemMetadataType: + var payload pkg.GemMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.KbPackageMetadataType: + var payload pkg.KbPackageMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.PythonPackageMetadataType: + var payload pkg.PythonPackageMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.NpmPackageJSONMetadataType: + var payload pkg.NpmPackageJSONMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.PhpComposerJSONMetadataType: + var payload pkg.PhpComposerJSONMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.GolangBinMetadataType: + var payload pkg.GolangBinMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.DartPubMetadataType: + var payload pkg.DartPubMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.CocoapodsMetadataType: + var payload pkg.CocoapodsMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.ConanaMetadataType: + var payload pkg.ConanMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.DotnetDepsMetadataType: + var payload pkg.DotnetDepsMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.PortageMetadataType: + var payload pkg.PortageMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + case pkg.HackageMetadataType: + var payload pkg.HackageMetadata + if err := json.Unmarshal(unpacker.Metadata, &payload); err != nil { + return err + } + p.Metadata = payload + default: + return errUnknownMetadataType + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/package_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/package_test.go new file mode 100644 index 0000000000000000000000000000000000000000..da282f4260f8eff444c1d15b66723e3b62914498 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/package_test.go @@ -0,0 +1,218 @@ +package model + +import ( + "encoding/json" + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + "testing" +) + +func TestUnmarshalPackageGolang(t *testing.T) { + tests := []struct { + name string + packageData []byte + assert func(*Package) + }{ + { + name: "unmarshal package metadata", + packageData: []byte(`{ + "id": "8b594519bc23da50", + "name": "gopkg.in/square/go-jose.v2", + "version": "v2.6.0", + "type": "go-module", + "foundBy": "go-module-binary-cataloger", + "locations": [ + { + "path": "/Users/hal/go/bin/syft" + } + ], + "licenses": [], + "language": "go", + "cpes": [], + "purl": "pkg:golang/gopkg.in/square/go-jose.v2@v2.6.0", + "metadataType": "GolangBinMetadata", + "metadata": { + "goCompiledVersion": "go1.18", + "architecture": "amd64", + "h1Digest": "h1:NGk74WTnPKBNUhNzQX7PYcTLUjoq7mzKk2OKbvwk2iI=" + } + }`), + assert: func(p *Package) { + assert.NotNil(t, p.Metadata) + golangMetadata := p.Metadata.(pkg.GolangBinMetadata) + assert.NotEmpty(t, golangMetadata) + assert.Equal(t, "go1.18", golangMetadata.GoCompiledVersion) + }, + }, + { + name: "can handle package without metadata", + packageData: []byte(`{ + "id": "8b594519bc23da50", + "name": "gopkg.in/square/go-jose.v2", + "version": "v2.6.0", + "type": "go-module", + "foundBy": "go-mod-cataloger", + "locations": [ + { + "path": "/Users/hal/go/bin/syft" + } + ], + "licenses": [], + "language": "go", + "cpes": [], + "purl": "pkg:golang/gopkg.in/square/go-jose.v2@v2.6.0" + }`), + assert: func(p *Package) { + assert.Empty(t, p.MetadataType) + assert.Empty(t, p.Metadata) + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + p := &Package{} + err := p.UnmarshalJSON(test.packageData) + require.NoError(t, err) + test.assert(p) + }) + } +} + +func Test_unpackMetadata(t *testing.T) { + tests := []struct { + name string + packageData []byte + metadataType pkg.MetadataType + wantErr require.ErrorAssertionFunc + }{ + { + name: "unmarshal package metadata", + metadataType: pkg.GolangBinMetadataType, + packageData: []byte(`{ + "id": "8b594519bc23da50", + "name": "gopkg.in/square/go-jose.v2", + "version": "v2.6.0", + "type": "go-module", + "foundBy": "go-module-binary-cataloger", + "locations": [ + { + "path": "/Users/hal/go/bin/syft" + } + ], + "licenses": [], + "language": "go", + "cpes": [], + "purl": "pkg:golang/gopkg.in/square/go-jose.v2@v2.6.0", + "metadataType": "GolangBinMetadata", + "metadata": { + "goCompiledVersion": "go1.18", + "architecture": "amd64", + "h1Digest": "h1:NGk74WTnPKBNUhNzQX7PYcTLUjoq7mzKk2OKbvwk2iI=" + } + }`), + }, + { + name: "can handle package without metadata", + metadataType: "", + packageData: []byte(`{ + "id": "8b594519bc23da50", + "name": "gopkg.in/square/go-jose.v2", + "version": "v2.6.0", + "type": "go-module", + "foundBy": "go-mod-cataloger", + "locations": [ + { + "path": "/Users/hal/go/bin/syft" + } + ], + "licenses": [], + "language": "go", + "cpes": [], + "purl": "pkg:golang/gopkg.in/square/go-jose.v2@v2.6.0" + }`), + }, + { + name: "can handle RpmdbMetadata", + metadataType: pkg.RpmMetadataType, + packageData: []byte(`{ + "id": "4ac699c3b8fe1835", + "name": "acl", + "version": "2.2.53-1.el8", + "type": "rpm", + "foundBy": "rpm-db-cataloger", + "locations": [ + { + "path": "/var/lib/rpm/Packages", + "layerID": "sha256:74ddd0ec08fa43d09f32636ba91a0a3053b02cb4627c35051aff89f853606b59" + } + ], + "licenses": [ + "GPLv2+" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:centos:acl:2.2.53-1.el8:*:*:*:*:*:*:*", + "cpe:2.3:a:acl:acl:2.2.53-1.el8:*:*:*:*:*:*:*" + ], + "purl": "pkg:rpm/centos/acl@2.2.53-1.el8?arch=x86_64&upstream=acl-2.2.53-1.el8.src.rpm&distro=centos-8", + "metadataType": "RpmdbMetadata", + "metadata": { + "name": "acl", + "version": "2.2.53", + "epoch": null, + "architecture": "x86_64", + "release": "1.el8", + "sourceRpm": "acl-2.2.53-1.el8.src.rpm", + "size": 205740, + "license": "GPLv2+", + "vendor": "CentOS", + "modularityLabel": "" + } + }`), + }, + { + name: "bad metadata type is an error", + metadataType: "BOGOSITY", + wantErr: require.Error, + packageData: []byte(`{ + "id": "8b594519bc23da50", + "name": "gopkg.in/square/go-jose.v2", + "version": "v2.6.0", + "type": "go-module", + "foundBy": "go-mod-cataloger", + "locations": [ + { + "path": "/Users/hal/go/bin/syft" + } + ], + "licenses": [], + "language": "go", + "cpes": [], + "purl": "pkg:golang/gopkg.in/square/go-jose.v2@v2.6.0", + "metadataType": "BOGOSITY" + }`), + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + if test.wantErr == nil { + test.wantErr = require.NoError + } + p := &Package{} + + var basic PackageBasicData + require.NoError(t, json.Unmarshal(test.packageData, &basic)) + p.PackageBasicData = basic + + var unpacker packageMetadataUnpacker + require.NoError(t, json.Unmarshal(test.packageData, &unpacker)) + + err := unpackMetadata(p, unpacker) + assert.Equal(t, test.metadataType, p.MetadataType) + test.wantErr(t, err) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/relationship.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/relationship.go new file mode 100644 index 0000000000000000000000000000000000000000..46f6da22d4885f0b90556a35883ff581e0336ea2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/relationship.go @@ -0,0 +1,8 @@ +package model + +type Relationship struct { + Parent string `json:"parent"` + Child string `json:"child"` + Type string `json:"type"` + Metadata interface{} `json:"metadata,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/secrets.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/secrets.go new file mode 100644 index 0000000000000000000000000000000000000000..c5f4685765d02b6a978d3e491c3daabd5b01ba79 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/secrets.go @@ -0,0 +1,11 @@ +package model + +import ( + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/source" +) + +type Secrets struct { + Location source.Coordinates `json:"location"` + Secrets []file.SearchResult `json:"secrets"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/source.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/source.go new file mode 100644 index 0000000000000000000000000000000000000000..169405220d91656cceb3d2c5ea15e949e258170d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/source.go @@ -0,0 +1,52 @@ +package model + +import ( + "encoding/json" + "fmt" + "strconv" + + "github.com/anchore/syft/syft/source" +) + +// Source object represents the thing that was cataloged +type Source struct { + Type string `json:"type"` + Target interface{} `json:"target"` +} + +// sourceUnpacker is used to unmarshal Source objects +type sourceUnpacker struct { + Type string `json:"type"` + Target json.RawMessage `json:"target"` +} + +// UnmarshalJSON populates a source object from JSON bytes. +func (s *Source) UnmarshalJSON(b []byte) error { + var unpacker sourceUnpacker + if err := json.Unmarshal(b, &unpacker); err != nil { + return err + } + + s.Type = unpacker.Type + + switch s.Type { + case "directory", "file": + if target, err := strconv.Unquote(string(unpacker.Target)); err == nil { + s.Target = target + } else { + s.Target = string(unpacker.Target[:]) + } + + case "image": + var payload source.ImageMetadata + if err := json.Unmarshal(unpacker.Target, &payload); err != nil { + return err + } + s.Target = payload + + default: + return fmt.Errorf("unsupported package metadata type: %+v", s.Type) + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/source_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/source_test.go new file mode 100644 index 0000000000000000000000000000000000000000..cedf06e9decab3b398352c5fe7dd005041e75cd1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/model/source_test.go @@ -0,0 +1,136 @@ +package model + +import ( + "encoding/json" + "testing" + + "github.com/anchore/syft/syft/source" + + "github.com/google/go-cmp/cmp" + + "github.com/stretchr/testify/assert" +) + +func TestSource_UnmarshalJSON(t *testing.T) { + cases := []struct { + name string + input []byte + expectedSource *Source + errAssertion assert.ErrorAssertionFunc + }{ + { + name: "directory", + input: []byte(`{ + "type": "directory", + "target":"/var/lib/foo" + }`), + expectedSource: &Source{ + Type: "directory", + Target: "/var/lib/foo", + }, + errAssertion: assert.NoError, + }, + { + name: "image", + input: []byte(`{ + "type": "image", + "target": { + "userInput": "alpine:3.10", + "imageID": "sha256:e7b300aee9f9bf3433d32bc9305bfdd22183beb59d933b48d77ab56ba53a197a", + "manifestDigest": "sha256:e515aad2ed234a5072c4d2ef86a1cb77d5bfe4b11aa865d9214875734c4eeb3c", + "mediaType": "application/vnd.docker.distribution.manifest.v2+json", + "tags": [], + "imageSize": 5576169, + "layers": [ + { + "mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip", + "digest": "sha256:9fb3aa2f8b8023a4bebbf92aa567caf88e38e969ada9f0ac12643b2847391635", + "size": 5576169 + } + ], + "manifest": "ewogICAic2NoZW1hVmVyc2lvbiI6IDIsCiAgICJtZWRpYVR5cGUiOiAiYXBwbGljYXRpb24vdm5kLmRvY2tlci5kaXN0cmlidXRpb24ubWFuaWZlc3QudjIranNvbiIsCiAgICJjb25maWciOiB7CiAgICAgICJtZWRpYVR5cGUiOiAiYXBwbGljYXRpb24vdm5kLmRvY2tlci5jb250YWluZXIuaW1hZ2UudjEranNvbiIsCiAgICAgICJzaXplIjogMTQ3MiwKICAgICAgImRpZ2VzdCI6ICJzaGEyNTY6ZTdiMzAwYWVlOWY5YmYzNDMzZDMyYmM5MzA1YmZkZDIyMTgzYmViNTlkOTMzYjQ4ZDc3YWI1NmJhNTNhMTk3YSIKICAgfSwKICAgImxheWVycyI6IFsKICAgICAgewogICAgICAgICAibWVkaWFUeXBlIjogImFwcGxpY2F0aW9uL3ZuZC5kb2NrZXIuaW1hZ2Uucm9vdGZzLmRpZmYudGFyLmd6aXAiLAogICAgICAgICAic2l6ZSI6IDI3OTgzMzgsCiAgICAgICAgICJkaWdlc3QiOiAic2hhMjU2OjM5NmMzMTgzNzExNmFjMjkwNDU4YWZjYjkyOGY2OGI2Y2MxYzdiZGQ2OTYzZmM3MmY1MmYzNjVhMmE4OWMxYjUiCiAgICAgIH0KICAgXQp9", + "config": "eyJhcmNoaXRlY3R1cmUiOiJhbWQ2NCIsImNvbmZpZyI6eyJIb3N0bmFtZSI6IiIsIkRvbWFpbm5hbWUiOiIiLCJVc2VyIjoiIiwiQXR0YWNoU3RkaW4iOmZhbHNlLCJBdHRhY2hTdGRvdXQiOmZhbHNlLCJBdHRhY2hTdGRlcnIiOmZhbHNlLCJUdHkiOmZhbHNlLCJPcGVuU3RkaW4iOmZhbHNlLCJTdGRpbk9uY2UiOmZhbHNlLCJFbnYiOlsiUEFUSD0vdXNyL2xvY2FsL3NiaW46L3Vzci9sb2NhbC9iaW46L3Vzci9zYmluOi91c3IvYmluOi9zYmluOi9iaW4iXSwiQ21kIjpbIi9iaW4vc2giXSwiSW1hZ2UiOiJzaGEyNTY6ZWIyMDgwYzQ1NWU5NGMyMmFlMzViM2FlZjllMDc4YzQ5MmEwMDc5NTQxMmUwMjZlNGQ2YjQxZWY2NGJjN2RkOCIsIlZvbHVtZXMiOm51bGwsIldvcmtpbmdEaXIiOiIiLCJFbnRyeXBvaW50IjpudWxsLCJPbkJ1aWxkIjpudWxsLCJMYWJlbHMiOm51bGx9LCJjb250YWluZXIiOiJmZGI3ZTgwZTMzMzllOGQwNTk5MjgyZTYwNmM5MDdhYTU4ODFlZTRjNjY4YTY4MTM2MTE5ZTZkZmFjNmNlM2E0IiwiY29udGFpbmVyX2NvbmZpZyI6eyJIb3N0bmFtZSI6ImZkYjdlODBlMzMzOSIsIkRvbWFpbm5hbWUiOiIiLCJVc2VyIjoiIiwiQXR0YWNoU3RkaW4iOmZhbHNlLCJBdHRhY2hTdGRvdXQiOmZhbHNlLCJBdHRhY2hTdGRlcnIiOmZhbHNlLCJUdHkiOmZhbHNlLCJPcGVuU3RkaW4iOmZhbHNlLCJTdGRpbk9uY2UiOmZhbHNlLCJFbnYiOlsiUEFUSD0vdXNyL2xvY2FsL3NiaW46L3Vzci9sb2NhbC9iaW46L3Vzci9zYmluOi91c3IvYmluOi9zYmluOi9iaW4iXSwiQ21kIjpbIi9iaW4vc2giLCItYyIsIiMobm9wKSAiLCJDTUQgW1wiL2Jpbi9zaFwiXSJdLCJJbWFnZSI6InNoYTI1NjplYjIwODBjNDU1ZTk0YzIyYWUzNWIzYWVmOWUwNzhjNDkyYTAwNzk1NDEyZTAyNmU0ZDZiNDFlZjY0YmM3ZGQ4IiwiVm9sdW1lcyI6bnVsbCwiV29ya2luZ0RpciI6IiIsIkVudHJ5cG9pbnQiOm51bGwsIk9uQnVpbGQiOm51bGwsIkxhYmVscyI6e319LCJjcmVhdGVkIjoiMjAyMS0wNC0xNFQxOToyMDowNS4zMzgzOTc3NjFaIiwiZG9ja2VyX3ZlcnNpb24iOiIxOS4wMy4xMiIsImhpc3RvcnkiOlt7ImNyZWF0ZWQiOiIyMDIxLTA0LTE0VDE5OjIwOjA0Ljk4NzIxOTEyNFoiLCJjcmVhdGVkX2J5IjoiL2Jpbi9zaCAtYyAjKG5vcCkgQUREIGZpbGU6YzUzNzdlYWE5MjZiZjQxMmRkOGQ0YTA4YjBhMWYyMzk5Y2ZkNzA4NzQzNTMzYjBhYTAzYjUzZDE0Y2I0YmI0ZSBpbiAvICJ9LHsiY3JlYXRlZCI6IjIwMjEtMDQtMTRUMTk6MjA6MDUuMzM4Mzk3NzYxWiIsImNyZWF0ZWRfYnkiOiIvYmluL3NoIC1jICMobm9wKSAgQ01EIFtcIi9iaW4vc2hcIl0iLCJlbXB0eV9sYXllciI6dHJ1ZX1dLCJvcyI6ImxpbnV4Iiwicm9vdGZzIjp7InR5cGUiOiJsYXllcnMiLCJkaWZmX2lkcyI6WyJzaGEyNTY6OWZiM2FhMmY4YjgwMjNhNGJlYmJmOTJhYTU2N2NhZjg4ZTM4ZTk2OWFkYTlmMGFjMTI2NDNiMjg0NzM5MTYzNSJdfX0=", + "repoDigests": [ + "index.docker.io/library/alpine@sha256:451eee8bedcb2f029756dc3e9d73bab0e7943c1ac55cff3a4861c52a0fdd3e98" + ] + } + }`), + expectedSource: &Source{ + Type: "image", + Target: source.ImageMetadata{ + UserInput: "alpine:3.10", + ID: "sha256:e7b300aee9f9bf3433d32bc9305bfdd22183beb59d933b48d77ab56ba53a197a", + ManifestDigest: "sha256:e515aad2ed234a5072c4d2ef86a1cb77d5bfe4b11aa865d9214875734c4eeb3c", + MediaType: "application/vnd.docker.distribution.manifest.v2+json", + Tags: []string{}, + Size: 5576169, + Layers: []source.LayerMetadata{ + { + MediaType: "application/vnd.docker.image.rootfs.diff.tar.gzip", + Digest: "sha256:9fb3aa2f8b8023a4bebbf92aa567caf88e38e969ada9f0ac12643b2847391635", + Size: 5576169, + }, + }, + RawManifest: []byte(`{ + "schemaVersion": 2, + "mediaType": "application/vnd.docker.distribution.manifest.v2+json", + "config": { + "mediaType": "application/vnd.docker.container.image.v1+json", + "size": 1472, + "digest": "sha256:e7b300aee9f9bf3433d32bc9305bfdd22183beb59d933b48d77ab56ba53a197a" + }, + "layers": [ + { + "mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip", + "size": 2798338, + "digest": "sha256:396c31837116ac290458afcb928f68b6cc1c7bdd6963fc72f52f365a2a89c1b5" + } + ] +}`), + RawConfig: []byte(`{"architecture":"amd64","config":{"Hostname":"","Domainname":"","User":"","AttachStdin":false,"AttachStdout":false,"AttachStderr":false,"Tty":false,"OpenStdin":false,"StdinOnce":false,"Env":["PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"],"Cmd":["/bin/sh"],"Image":"sha256:eb2080c455e94c22ae35b3aef9e078c492a00795412e026e4d6b41ef64bc7dd8","Volumes":null,"WorkingDir":"","Entrypoint":null,"OnBuild":null,"Labels":null},"container":"fdb7e80e3339e8d0599282e606c907aa5881ee4c668a68136119e6dfac6ce3a4","container_config":{"Hostname":"fdb7e80e3339","Domainname":"","User":"","AttachStdin":false,"AttachStdout":false,"AttachStderr":false,"Tty":false,"OpenStdin":false,"StdinOnce":false,"Env":["PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"],"Cmd":["/bin/sh","-c","#(nop) ","CMD [\"/bin/sh\"]"],"Image":"sha256:eb2080c455e94c22ae35b3aef9e078c492a00795412e026e4d6b41ef64bc7dd8","Volumes":null,"WorkingDir":"","Entrypoint":null,"OnBuild":null,"Labels":{}},"created":"2021-04-14T19:20:05.338397761Z","docker_version":"19.03.12","history":[{"created":"2021-04-14T19:20:04.987219124Z","created_by":"/bin/sh -c #(nop) ADD file:c5377eaa926bf412dd8d4a08b0a1f2399cfd708743533b0aa03b53d14cb4bb4e in / "},{"created":"2021-04-14T19:20:05.338397761Z","created_by":"/bin/sh -c #(nop) CMD [\"/bin/sh\"]","empty_layer":true}],"os":"linux","rootfs":{"type":"layers","diff_ids":["sha256:9fb3aa2f8b8023a4bebbf92aa567caf88e38e969ada9f0ac12643b2847391635"]}}`), + RepoDigests: []string{ + "index.docker." + + "io/library/alpine@sha256:451eee8bedcb2f029756dc3e9d73bab0e7943c1ac55cff3a4861c52a0fdd3e98", + }, + }, + }, + errAssertion: assert.NoError, + }, + { + name: "file", + input: []byte(`{ + "type": "file", + "target":"/var/lib/foo/go.mod" + }`), + expectedSource: &Source{ + Type: "file", + Target: "/var/lib/foo/go.mod", + }, + errAssertion: assert.NoError, + }, + { + name: "unknown source type", + input: []byte(`{ + "type": "unknown-thing", + "target":"/var/lib/foo" + }`), + expectedSource: &Source{ + Type: "unknown-thing", + }, + errAssertion: assert.Error, + }, + } + + for _, testCase := range cases { + t.Run(testCase.name, func(t *testing.T) { + source := new(Source) + + err := json.Unmarshal(testCase.input, source) + + testCase.errAssertion(t, err) + if diff := cmp.Diff(testCase.expectedSource, source); diff != "" { + t.Errorf("unexpected result from Source unmarshaling (-want +got)\n%s", diff) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/Dockerfile b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..79cfa759e357be9628894dea6332a0e6a2c33bb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/Dockerfile @@ -0,0 +1,4 @@ +# Note: changes to this file will result in updating several test values. Consider making a new image fixture instead of editing this one. +FROM scratch +ADD file-1.txt /somefile-1.txt +ADD file-2.txt /somefile-2.txt diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/file-1.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..985d3408e98cb9f41c01376c698451fdef0e4b32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/file-1.txt @@ -0,0 +1 @@ +this file has contents \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/file-2.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..396d08bbc72f810ec6d057d1713a84a75d1cd542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/image-simple/file-2.txt @@ -0,0 +1 @@ +file-2 contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestDirectoryEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestDirectoryEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..19a8f5044f14b24e0296204596062ebb2bc9a3ff --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestDirectoryEncoder.golden @@ -0,0 +1,94 @@ +{ + "artifacts": [ + { + "id": "b85dbb4e6ece5082", + "name": "package-1", + "version": "1.0.1", + "type": "python", + "foundBy": "the-cataloger-1", + "locations": [ + { + "path": "/some/path/pkg1" + } + ], + "licenses": [ + "MIT" + ], + "language": "python", + "cpes": [ + "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*" + ], + "purl": "a-purl-2", + "metadataType": "PythonPackageMetadata", + "metadata": { + "name": "package-1", + "version": "1.0.1", + "license": "", + "author": "", + "authorEmail": "", + "platform": "", + "files": [ + { + "path": "/some/path/pkg1/dependencies/foo" + } + ], + "sitePackagesRootPath": "" + } + }, + { + "id": "ceda99598967ae8d", + "name": "package-2", + "version": "2.0.1", + "type": "deb", + "foundBy": "the-cataloger-2", + "locations": [ + { + "path": "/some/path/pkg1" + } + ], + "licenses": [], + "language": "", + "cpes": [ + "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*" + ], + "purl": "pkg:deb/debian/package-2@2.0.1", + "metadataType": "DpkgMetadata", + "metadata": { + "package": "package-2", + "source": "", + "version": "2.0.1", + "sourceVersion": "", + "architecture": "", + "maintainer": "", + "installedSize": 0, + "files": null + } + } + ], + "artifactRelationships": [], + "source": { + "type": "directory", + "target": "/some/path" + }, + "distro": { + "prettyName": "debian", + "name": "debian", + "id": "debian", + "idLike": [ + "like!" + ], + "version": "1.2.3", + "versionID": "1.2.3" + }, + "descriptor": { + "name": "syft", + "version": "v0.42.0-bogus", + "configuration": { + "config-key": "config-value" + } + }, + "schema": { + "version": "3.3.2", + "url": "https://raw.githubusercontent.com/anchore/syft/main/schema/json/schema-3.3.2.json" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestEncodeFullJSONDocument.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestEncodeFullJSONDocument.golden new file mode 100644 index 0000000000000000000000000000000000000000..2b474a2810db1218299fbb09699ea88b54b45ba6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestEncodeFullJSONDocument.golden @@ -0,0 +1,190 @@ +{ + "artifacts": [ + { + "id": "b3fa3ee64756b0c6", + "name": "package-1", + "version": "1.0.1", + "type": "python", + "foundBy": "the-cataloger-1", + "locations": [ + { + "path": "/a/place/a" + } + ], + "licenses": [ + "MIT" + ], + "language": "python", + "cpes": [ + "cpe:2.3:*:some:package:1:*:*:*:*:*:*:*" + ], + "purl": "a-purl-1", + "metadataType": "PythonPackageMetadata", + "metadata": { + "name": "package-1", + "version": "1.0.1", + "license": "", + "author": "", + "authorEmail": "", + "platform": "", + "sitePackagesRootPath": "" + } + }, + { + "id": "b324f4d9ee5413fe", + "name": "package-2", + "version": "2.0.1", + "type": "deb", + "foundBy": "the-cataloger-2", + "locations": [ + { + "path": "/b/place/b" + } + ], + "licenses": [], + "language": "", + "cpes": [ + "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*" + ], + "purl": "a-purl-2", + "metadataType": "DpkgMetadata", + "metadata": { + "package": "package-2", + "source": "", + "version": "2.0.1", + "sourceVersion": "", + "architecture": "", + "maintainer": "", + "installedSize": 0, + "files": [] + } + } + ], + "artifactRelationships": [ + { + "parent": "", + "child": "", + "type": "ownership-by-file-overlap", + "metadata": { + "file": "path" + } + } + ], + "files": [ + { + "id": "913b4592e2c2ebdf", + "location": { + "path": "/a/place" + }, + "metadata": { + "mode": 775, + "type": "directory", + "userID": 0, + "groupID": 0, + "mimeType": "" + } + }, + { + "id": "e7c88bd18e11b0b", + "location": { + "path": "/a/place/a" + }, + "metadata": { + "mode": 775, + "type": "regularFile", + "userID": 0, + "groupID": 0, + "mimeType": "" + }, + "contents": "the-contents", + "digests": [ + { + "algorithm": "sha256", + "value": "366a3f5653e34673b875891b021647440d0127c2ef041e3b1a22da2a7d4f3703" + } + ] + }, + { + "id": "5c3dc6885f48b5a1", + "location": { + "path": "/b" + }, + "metadata": { + "mode": 775, + "type": "symbolicLink", + "linkDestination": "/c", + "userID": 0, + "groupID": 0, + "mimeType": "" + } + }, + { + "id": "799d2f12da0bcec4", + "location": { + "path": "/b/place/b" + }, + "metadata": { + "mode": 644, + "type": "regularFile", + "userID": 1, + "groupID": 2, + "mimeType": "" + }, + "digests": [ + { + "algorithm": "sha256", + "value": "1b3722da2a7d90d033b87581a2a3f12021647445653e34666ef041e3b4f3707c" + } + ] + } + ], + "source": { + "type": "image", + "target": { + "userInput": "user-image-input", + "imageID": "sha256:c2b46b4eb06296933b7cf0722683964e9ecbd93265b9ef6ae9642e3952afbba0", + "manifestDigest": "sha256:2731251dc34951c0e50fcc643b4c5f74922dad1a5d98f302b504cf46cd5d9368", + "mediaType": "application/vnd.docker.distribution.manifest.v2+json", + "tags": [ + "stereoscope-fixture-image-simple:85066c51088bdd274f7a89e99e00490f666c49e72ffc955707cd6e18f0e22c5b" + ], + "imageSize": 38, + "layers": [ + { + "mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip", + "digest": "sha256:3de16c5b8659a2e8d888b8ded8427be7a5686a3c8c4e4dd30de20f362827285b", + "size": 22 + }, + { + "mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip", + "digest": "sha256:366a3f5653e34673b875891b021647440d0127c2ef041e3b1a22da2a7d4f3703", + "size": 16 + } + ], + "manifest": "ZXlKelkyaGxiV0ZXWlhKemFXOXVJam95TENKdFpXUnBZVlI1Y0dVaU9pSmguLi4=", + "config": "ZXlKaGNtTm9hWFJsWTNSMWNtVWlPaUpoYldRMk5DSXNJbU52Ym1acC4uLg==", + "repoDigests": [], + "architecture": "", + "os": "" + } + }, + "distro": { + "id": "redhat", + "idLike": [ + "rhel" + ], + "version": "7", + "versionID": "7" + }, + "descriptor": { + "name": "syft", + "version": "v0.42.0-bogus", + "configuration": { + "config-key": "config-value" + } + }, + "schema": { + "version": "3.3.2", + "url": "https://raw.githubusercontent.com/anchore/syft/main/schema/json/schema-3.3.2.json" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestImageEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestImageEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..ae948591c5ff8b424c283400a3ce4dc44c17ac2e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/TestImageEncoder.golden @@ -0,0 +1,117 @@ +{ + "artifacts": [ + { + "id": "2a46171f91c8d4bc", + "name": "package-1", + "version": "1.0.1", + "type": "python", + "foundBy": "the-cataloger-1", + "locations": [ + { + "path": "/somefile-1.txt", + "layerID": "sha256:7ef28e9c2d56471ee090b578a678bdf28c3b5a311ca7b2e28c2a4185e5bb34c0" + } + ], + "licenses": [ + "MIT" + ], + "language": "python", + "cpes": [ + "cpe:2.3:*:some:package:1:*:*:*:*:*:*:*" + ], + "purl": "a-purl-1", + "metadataType": "PythonPackageMetadata", + "metadata": { + "name": "package-1", + "version": "1.0.1", + "license": "", + "author": "", + "authorEmail": "", + "platform": "", + "sitePackagesRootPath": "" + } + }, + { + "id": "ae77680e9b1d087e", + "name": "package-2", + "version": "2.0.1", + "type": "deb", + "foundBy": "the-cataloger-2", + "locations": [ + { + "path": "/somefile-2.txt", + "layerID": "sha256:86da8aee621161bea2efaf27a2709ddab5e7d44e30ecdfda728b02c03a28fd98" + } + ], + "licenses": [], + "language": "", + "cpes": [ + "cpe:2.3:*:some:package:2:*:*:*:*:*:*:*" + ], + "purl": "pkg:deb/debian/package-2@2.0.1", + "metadataType": "DpkgMetadata", + "metadata": { + "package": "package-2", + "source": "", + "version": "2.0.1", + "sourceVersion": "", + "architecture": "", + "maintainer": "", + "installedSize": 0, + "files": null + } + } + ], + "artifactRelationships": [], + "source": { + "type": "image", + "target": { + "userInput": "user-image-input", + "imageID": "sha256:5dd5f5f4247e4e946f555f0de7681a631a5240b614e52717d0aed04808e8c65f", + "manifestDigest": "sha256:2731251dc34951c0e50fcc643b4c5f74922dad1a5d98f302b504cf46cd5d9368", + "mediaType": "application/vnd.docker.distribution.manifest.v2+json", + "tags": [ + "stereoscope-fixture-image-simple:85066c51088bdd274f7a89e99e00490f666c49e72ffc955707cd6e18f0e22c5b" + ], + "imageSize": 38, + "layers": [ + { + "mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip", + "digest": "sha256:7ef28e9c2d56471ee090b578a678bdf28c3b5a311ca7b2e28c2a4185e5bb34c0", + "size": 22 + }, + { + "mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip", + "digest": "sha256:86da8aee621161bea2efaf27a2709ddab5e7d44e30ecdfda728b02c03a28fd98", + "size": 16 + } + ], + "manifest": "eyJzY2hlbWFWZXJzaW9uIjoyLCJtZWRpYVR5cGUiOiJhcHBsaWNhdGlvbi92bmQuZG9ja2VyLmRpc3RyaWJ1dGlvbi5tYW5pZmVzdC52Mitqc29uIiwiY29uZmlnIjp7Im1lZGlhVHlwZSI6ImFwcGxpY2F0aW9uL3ZuZC5kb2NrZXIuY29udGFpbmVyLmltYWdlLnYxK2pzb24iLCJzaXplIjo2NzMsImRpZ2VzdCI6InNoYTI1Njo1ZGQ1ZjVmNDI0N2U0ZTk0NmY1NTVmMGRlNzY4MWE2MzFhNTI0MGI2MTRlNTI3MTdkMGFlZDA0ODA4ZThjNjVmIn0sImxheWVycyI6W3sibWVkaWFUeXBlIjoiYXBwbGljYXRpb24vdm5kLmRvY2tlci5pbWFnZS5yb290ZnMuZGlmZi50YXIuZ3ppcCIsInNpemUiOjIwNDgsImRpZ2VzdCI6InNoYTI1Njo3ZWYyOGU5YzJkNTY0NzFlZTA5MGI1NzhhNjc4YmRmMjhjM2I1YTMxMWNhN2IyZTI4YzJhNDE4NWU1YmIzNGMwIn0seyJtZWRpYVR5cGUiOiJhcHBsaWNhdGlvbi92bmQuZG9ja2VyLmltYWdlLnJvb3Rmcy5kaWZmLnRhci5nemlwIiwic2l6ZSI6MjA0OCwiZGlnZXN0Ijoic2hhMjU2Ojg2ZGE4YWVlNjIxMTYxYmVhMmVmYWYyN2EyNzA5ZGRhYjVlN2Q0NGUzMGVjZGZkYTcyOGIwMmMwM2EyOGZkOTgifV19", + "config": "eyJhcmNoaXRlY3R1cmUiOiJhbWQ2NCIsImNvbmZpZyI6eyJFbnYiOlsiUEFUSD0vdXNyL2xvY2FsL3NiaW46L3Vzci9sb2NhbC9iaW46L3Vzci9zYmluOi91c3IvYmluOi9zYmluOi9iaW4iXSwiV29ya2luZ0RpciI6Ii8iLCJPbkJ1aWxkIjpudWxsfSwiY3JlYXRlZCI6IjIwMjItMDYtMDJUMTQ6MzQ6MzQuNzE5MTM1MTc0WiIsImhpc3RvcnkiOlt7ImNyZWF0ZWQiOiIyMDIyLTA2LTAyVDE0OjM0OjM0LjY4NjkzMzI2M1oiLCJjcmVhdGVkX2J5IjoiQUREIGZpbGUtMS50eHQgL3NvbWVmaWxlLTEudHh0ICMgYnVpbGRraXQiLCJjb21tZW50IjoiYnVpbGRraXQuZG9ja2VyZmlsZS52MCJ9LHsiY3JlYXRlZCI6IjIwMjItMDYtMDJUMTQ6MzQ6MzQuNzE5MTM1MTc0WiIsImNyZWF0ZWRfYnkiOiJBREQgZmlsZS0yLnR4dCAvc29tZWZpbGUtMi50eHQgIyBidWlsZGtpdCIsImNvbW1lbnQiOiJidWlsZGtpdC5kb2NrZXJmaWxlLnYwIn1dLCJvcyI6ImxpbnV4Iiwicm9vdGZzIjp7InR5cGUiOiJsYXllcnMiLCJkaWZmX2lkcyI6WyJzaGEyNTY6N2VmMjhlOWMyZDU2NDcxZWUwOTBiNTc4YTY3OGJkZjI4YzNiNWEzMTFjYTdiMmUyOGMyYTQxODVlNWJiMzRjMCIsInNoYTI1Njo4NmRhOGFlZTYyMTE2MWJlYTJlZmFmMjdhMjcwOWRkYWI1ZTdkNDRlMzBlY2RmZGE3MjhiMDJjMDNhMjhmZDk4Il19fQ==", + "repoDigests": [], + "architecture": "", + "os": "" + } + }, + "distro": { + "prettyName": "debian", + "name": "debian", + "id": "debian", + "idLike": [ + "like!" + ], + "version": "1.2.3", + "versionID": "1.2.3" + }, + "descriptor": { + "name": "syft", + "version": "v0.42.0-bogus", + "configuration": { + "config-key": "config-value" + } + }, + "schema": { + "version": "3.3.2", + "url": "https://raw.githubusercontent.com/anchore/syft/main/schema/json/schema-3.3.2.json" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden new file mode 100644 index 0000000000000000000000000000000000000000..3cd33e2b8f5017eba3b30fd98d7a456c3e4515d7 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden differ diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_format_model.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_format_model.go new file mode 100644 index 0000000000000000000000000000000000000000..b97e2272505182992f563f5480c8ff0928766463 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_format_model.go @@ -0,0 +1,259 @@ +package syftjson + +import ( + "fmt" + "sort" + "strconv" + + "github.com/anchore/syft/syft/linux" + + "github.com/anchore/syft/syft/file" + + "github.com/anchore/syft/syft/artifact" + + "github.com/anchore/syft/syft/sbom" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/formats/syftjson/model" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +// ToFormatModel transforms the sbom import a format-specific model. +// note: this is needed for anchore import functionality +// TODO: unexport this when/if anchore import functionality is removed +func ToFormatModel(s sbom.SBOM) model.Document { + src, err := toSourceModel(s.Source) + if err != nil { + log.Warnf("unable to create syft-json source object: %+v", err) + } + + return model.Document{ + Artifacts: toPackageModels(s.Artifacts.PackageCatalog), + ArtifactRelationships: toRelationshipModel(s.Relationships), + Files: toFile(s), + Secrets: toSecrets(s.Artifacts.Secrets), + Source: src, + Distro: toLinuxReleaser(s.Artifacts.LinuxDistribution), + Descriptor: toDescriptor(s.Descriptor), + Schema: model.Schema{ + Version: internal.JSONSchemaVersion, + URL: fmt.Sprintf("https://raw.githubusercontent.com/anchore/syft/main/schema/json/schema-%s.json", internal.JSONSchemaVersion), + }, + } +} + +func toLinuxReleaser(d *linux.Release) model.LinuxRelease { + if d == nil { + return model.LinuxRelease{} + } + return model.LinuxRelease{ + PrettyName: d.PrettyName, + Name: d.Name, + ID: d.ID, + IDLike: d.IDLike, + Version: d.Version, + VersionID: d.VersionID, + VersionCodename: d.VersionCodename, + BuildID: d.BuildID, + ImageID: d.ImageID, + ImageVersion: d.ImageVersion, + Variant: d.Variant, + VariantID: d.VariantID, + HomeURL: d.HomeURL, + SupportURL: d.SupportURL, + BugReportURL: d.BugReportURL, + PrivacyPolicyURL: d.PrivacyPolicyURL, + CPEName: d.CPEName, + } +} + +func toDescriptor(d sbom.Descriptor) model.Descriptor { + return model.Descriptor{ + Name: d.Name, + Version: d.Version, + Configuration: d.Configuration, + } +} + +func toSecrets(data map[source.Coordinates][]file.SearchResult) []model.Secrets { + results := make([]model.Secrets, 0) + for coordinates, secrets := range data { + results = append(results, model.Secrets{ + Location: coordinates, + Secrets: secrets, + }) + } + + // sort by real path then virtual path to ensure the result is stable across multiple runs + sort.SliceStable(results, func(i, j int) bool { + return results[i].Location.RealPath < results[j].Location.RealPath + }) + return results +} + +func toFile(s sbom.SBOM) []model.File { + results := make([]model.File, 0) + artifacts := s.Artifacts + + for _, coordinates := range sbom.AllCoordinates(s) { + var metadata *source.FileMetadata + if metadataForLocation, exists := artifacts.FileMetadata[coordinates]; exists { + metadata = &metadataForLocation + } + + var digests []file.Digest + if digestsForLocation, exists := artifacts.FileDigests[coordinates]; exists { + digests = digestsForLocation + } + + var classifications []file.Classification + if classificationsForLocation, exists := artifacts.FileClassifications[coordinates]; exists { + classifications = classificationsForLocation + } + + var contents string + if contentsForLocation, exists := artifacts.FileContents[coordinates]; exists { + contents = contentsForLocation + } + + results = append(results, model.File{ + ID: string(coordinates.ID()), + Location: coordinates, + Metadata: toFileMetadataEntry(coordinates, metadata), + Digests: digests, + Classifications: classifications, + Contents: contents, + }) + } + + // sort by real path then virtual path to ensure the result is stable across multiple runs + sort.SliceStable(results, func(i, j int) bool { + return results[i].Location.RealPath < results[j].Location.RealPath + }) + return results +} + +func toFileMetadataEntry(coordinates source.Coordinates, metadata *source.FileMetadata) *model.FileMetadataEntry { + if metadata == nil { + return nil + } + + mode, err := strconv.Atoi(fmt.Sprintf("%o", metadata.Mode)) + if err != nil { + log.Warnf("invalid mode found in file catalog @ location=%+v mode=%q: %+v", coordinates, metadata.Mode, err) + mode = 0 + } + + return &model.FileMetadataEntry{ + Mode: mode, + Type: metadata.Type, + LinkDestination: metadata.LinkDestination, + UserID: metadata.UserID, + GroupID: metadata.GroupID, + MIMEType: metadata.MIMEType, + } +} + +func toPackageModels(catalog *pkg.Catalog) []model.Package { + artifacts := make([]model.Package, 0) + if catalog == nil { + return artifacts + } + for _, p := range catalog.Sorted() { + artifacts = append(artifacts, toPackageModel(p)) + } + return artifacts +} + +// toPackageModel crates a new Package from the given pkg.Package. +func toPackageModel(p pkg.Package) model.Package { + var cpes = make([]string, len(p.CPEs)) + for i, c := range p.CPEs { + cpes[i] = pkg.CPEString(c) + } + + var licenses = make([]string, 0) + if p.Licenses != nil { + licenses = p.Licenses + } + + locations := p.Locations.ToSlice() + var coordinates = make([]source.Coordinates, len(locations)) + for i, l := range locations { + coordinates[i] = l.Coordinates + } + + return model.Package{ + PackageBasicData: model.PackageBasicData{ + ID: string(p.ID()), + Name: p.Name, + Version: p.Version, + Type: p.Type, + FoundBy: p.FoundBy, + Locations: coordinates, + Licenses: licenses, + Language: p.Language, + CPEs: cpes, + PURL: p.PURL, + }, + PackageCustomData: model.PackageCustomData{ + MetadataType: p.MetadataType, + Metadata: p.Metadata, + }, + } +} + +func toRelationshipModel(relationships []artifact.Relationship) []model.Relationship { + result := make([]model.Relationship, len(relationships)) + for i, r := range relationships { + result[i] = model.Relationship{ + Parent: string(r.From.ID()), + Child: string(r.To.ID()), + Type: string(r.Type), + Metadata: r.Data, + } + } + sort.Slice(result, func(i, j int) bool { + if iParent, jParent := result[i].Parent, result[j].Parent; iParent != jParent { + return iParent < jParent + } + if iChild, jChild := result[i].Child, result[j].Child; iChild != jChild { + return iChild < jChild + } + return result[i].Type < result[j].Type + }) + return result +} + +// toSourceModel creates a new source object to be represented into JSON. +func toSourceModel(src source.Metadata) (model.Source, error) { + switch src.Scheme { + case source.ImageScheme: + metadata := src.ImageMetadata + // ensure that empty collections are not shown as null + if metadata.RepoDigests == nil { + metadata.RepoDigests = []string{} + } + if metadata.Tags == nil { + metadata.Tags = []string{} + } + return model.Source{ + Type: "image", + Target: metadata, + }, nil + case source.DirectoryScheme: + return model.Source{ + Type: "directory", + Target: src.Path, + }, nil + case source.FileScheme: + return model.Source{ + Type: "file", + Target: src.Path, + }, nil + default: + return model.Source{}, fmt.Errorf("unsupported source: %q", src.Scheme) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_format_model_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_format_model_test.go new file mode 100644 index 0000000000000000000000000000000000000000..18d67936dc007baf14c5e776fe6e2bf7f922f499 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_format_model_test.go @@ -0,0 +1,86 @@ +package syftjson + +import ( + "testing" + + "github.com/scylladb/go-set/strset" + + "github.com/anchore/syft/internal/formats/syftjson/model" + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func Test_toSourceModel(t *testing.T) { + allSchemes := strset.New() + for _, s := range source.AllSchemes { + allSchemes.Add(string(s)) + } + testedSchemes := strset.New() + + tests := []struct { + name string + src source.Metadata + expected model.Source + }{ + { + name: "directory", + src: source.Metadata{ + Scheme: source.DirectoryScheme, + Path: "some/path", + }, + expected: model.Source{ + Type: "directory", + Target: "some/path", + }, + }, + { + name: "file", + src: source.Metadata{ + Scheme: source.FileScheme, + Path: "some/path", + }, + expected: model.Source{ + Type: "file", + Target: "some/path", + }, + }, + { + name: "image", + src: source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: source.ImageMetadata{ + UserInput: "user-input", + ID: "id...", + ManifestDigest: "digest...", + MediaType: "type...", + }, + }, + expected: model.Source{ + Type: "image", + Target: source.ImageMetadata{ + UserInput: "user-input", + ID: "id...", + ManifestDigest: "digest...", + MediaType: "type...", + RepoDigests: []string{}, + Tags: []string{}, + }, + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + // track each scheme tested (passed or not) + testedSchemes.Add(string(test.src.Scheme)) + + // assert the model transformation is correct + actual, err := toSourceModel(test.src) + require.NoError(t, err) + assert.Equal(t, test.expected, actual) + }) + } + + // assert all possible schemes were under test + assert.ElementsMatch(t, allSchemes.List(), testedSchemes.List(), "not all source.Schemes are under test") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_syft_model.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_syft_model.go new file mode 100644 index 0000000000000000000000000000000000000000..992c724767f6755ff9df8ddfeee1a32e4f84c712 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_syft_model.go @@ -0,0 +1,196 @@ +package syftjson + +import ( + "github.com/anchore/syft/internal/formats/syftjson/model" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" + "github.com/google/go-cmp/cmp" +) + +func toSyftModel(doc model.Document) (*sbom.SBOM, error) { + idAliases := make(map[string]string) + + catalog := toSyftCatalog(doc.Artifacts, idAliases) + + return &sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: catalog, + LinuxDistribution: toSyftLinuxRelease(doc.Distro), + }, + Source: *toSyftSourceData(doc.Source), + Descriptor: toSyftDescriptor(doc.Descriptor), + Relationships: toSyftRelationships(&doc, catalog, doc.ArtifactRelationships, idAliases), + }, nil +} + +func toSyftLinuxRelease(d model.LinuxRelease) *linux.Release { + if cmp.Equal(d, model.LinuxRelease{}) { + return nil + } + return &linux.Release{ + PrettyName: d.PrettyName, + Name: d.Name, + ID: d.ID, + IDLike: d.IDLike, + Version: d.Version, + VersionID: d.VersionID, + VersionCodename: d.VersionCodename, + BuildID: d.BuildID, + ImageID: d.ImageID, + ImageVersion: d.ImageVersion, + Variant: d.Variant, + VariantID: d.VariantID, + HomeURL: d.HomeURL, + SupportURL: d.SupportURL, + BugReportURL: d.BugReportURL, + PrivacyPolicyURL: d.PrivacyPolicyURL, + CPEName: d.CPEName, + } +} + +func toSyftRelationships(doc *model.Document, catalog *pkg.Catalog, relationships []model.Relationship, idAliases map[string]string) []artifact.Relationship { + idMap := make(map[string]interface{}) + + for _, p := range catalog.Sorted() { + idMap[string(p.ID())] = p + locations := p.Locations.ToSlice() + for _, l := range locations { + idMap[string(l.Coordinates.ID())] = l.Coordinates + } + } + + for _, f := range doc.Files { + idMap[f.ID] = f.Location + } + + var out []artifact.Relationship + for _, r := range relationships { + syftRelationship := toSyftRelationship(idMap, r, idAliases) + if syftRelationship != nil { + out = append(out, *syftRelationship) + } + } + return out +} + +func toSyftRelationship(idMap map[string]interface{}, relationship model.Relationship, idAliases map[string]string) *artifact.Relationship { + id := func(id string) string { + aliased, ok := idAliases[id] + if ok { + return aliased + } + return id + } + from, ok := idMap[id(relationship.Parent)].(artifact.Identifiable) + if !ok { + log.Warnf("relationship mapping from key %s is not a valid artifact.Identifiable type: %+v", relationship.Parent, idMap[relationship.Parent]) + return nil + } + to, ok := idMap[id(relationship.Child)].(artifact.Identifiable) + if !ok { + log.Warnf("relationship mapping to key %s is not a valid artifact.Identifiable type: %+v", relationship.Child, idMap[relationship.Child]) + return nil + } + typ := artifact.RelationshipType(relationship.Type) + + switch typ { + case artifact.OwnershipByFileOverlapRelationship: + fallthrough + case artifact.ContainsRelationship: + default: + log.Warnf("unknown relationship type: %s", typ) + return nil + } + return &artifact.Relationship{ + From: from, + To: to, + Type: typ, + Data: relationship.Metadata, + } +} + +func toSyftDescriptor(d model.Descriptor) sbom.Descriptor { + return sbom.Descriptor{ + Name: d.Name, + Version: d.Version, + Configuration: d.Configuration, + } +} + +func toSyftSourceData(s model.Source) *source.Metadata { + switch s.Type { + case "directory": + return &source.Metadata{ + Scheme: source.DirectoryScheme, + Path: s.Target.(string), + } + case "file": + return &source.Metadata{ + Scheme: source.FileScheme, + Path: s.Target.(string), + } + case "image": + return &source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: s.Target.(source.ImageMetadata), + } + } + return nil +} + +func toSyftCatalog(pkgs []model.Package, idAliases map[string]string) *pkg.Catalog { + catalog := pkg.NewCatalog() + for _, p := range pkgs { + catalog.Add(toSyftPackage(p, idAliases)) + } + return catalog +} + +func toSyftPackage(p model.Package, idAliases map[string]string) pkg.Package { + var cpes []pkg.CPE + for _, c := range p.CPEs { + value, err := pkg.NewCPE(c) + if err != nil { + log.Warnf("excluding invalid CPE %q: %v", c, err) + continue + } + + cpes = append(cpes, value) + } + + var locations = make([]source.Location, len(p.Locations)) + for i, c := range p.Locations { + locations[i] = source.NewLocationFromCoordinates(c) + } + + out := pkg.Package{ + Name: p.Name, + Version: p.Version, + FoundBy: p.FoundBy, + Locations: source.NewLocationSet(locations...), + Licenses: p.Licenses, + Language: p.Language, + Type: p.Type, + CPEs: cpes, + PURL: p.PURL, + MetadataType: p.MetadataType, + Metadata: p.Metadata, + } + + // we don't know if this package ID is truly unique, however, we need to trust the user input in case there are + // external references to it. That is, we can't derive our own ID (using pkg.SetID()) since consumers won't + // be able to historically interact with data that references the IDs from the original SBOM document being decoded now. + out.OverrideID(artifact.ID(p.ID)) + + // this alias mapping is currently defunct, but could be useful in the future. + id := string(out.ID()) + if id != p.ID { + idAliases[p.ID] = id + } + + return out +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_syft_model_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_syft_model_test.go new file mode 100644 index 0000000000000000000000000000000000000000..277106b8e457cf2db4e0167099575522831ddd21 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/to_syft_model_test.go @@ -0,0 +1,125 @@ +package syftjson + +import ( + "testing" + + "github.com/anchore/syft/internal/formats/syftjson/model" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/source" + "github.com/scylladb/go-set/strset" + "github.com/stretchr/testify/assert" +) + +func Test_toSyftSourceData(t *testing.T) { + allSchemes := strset.New() + for _, s := range source.AllSchemes { + allSchemes.Add(string(s)) + } + testedSchemes := strset.New() + + tests := []struct { + name string + src model.Source + expected source.Metadata + }{ + { + name: "directory", + expected: source.Metadata{ + Scheme: source.DirectoryScheme, + Path: "some/path", + }, + src: model.Source{ + Type: "directory", + Target: "some/path", + }, + }, + { + name: "file", + expected: source.Metadata{ + Scheme: source.FileScheme, + Path: "some/path", + }, + src: model.Source{ + Type: "file", + Target: "some/path", + }, + }, + { + name: "image", + expected: source.Metadata{ + Scheme: source.ImageScheme, + ImageMetadata: source.ImageMetadata{ + UserInput: "user-input", + ID: "id...", + ManifestDigest: "digest...", + MediaType: "type...", + }, + }, + src: model.Source{ + Type: "image", + Target: source.ImageMetadata{ + UserInput: "user-input", + ID: "id...", + ManifestDigest: "digest...", + MediaType: "type...", + }, + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + // assert the model transformation is correct + actual := toSyftSourceData(test.src) + assert.Equal(t, test.expected, *actual) + + // track each scheme tested (passed or not) + testedSchemes.Add(string(test.expected.Scheme)) + }) + } + + // assert all possible schemes were under test + assert.ElementsMatch(t, allSchemes.List(), testedSchemes.List(), "not all source.Schemes are under test") +} + +func Test_idsHaveChanged(t *testing.T) { + s, err := toSyftModel(model.Document{ + Source: model.Source{ + Type: "file", + Target: "some/path", + }, + Artifacts: []model.Package{ + { + PackageBasicData: model.PackageBasicData{ + ID: "1", + Name: "pkg-1", + }, + }, + { + PackageBasicData: model.PackageBasicData{ + ID: "2", + Name: "pkg-2", + }, + }, + }, + ArtifactRelationships: []model.Relationship{ + { + Parent: "1", + Child: "2", + Type: string(artifact.ContainsRelationship), + }, + }, + }) + + assert.NoError(t, err) + assert.Len(t, s.Relationships, 1) + + r := s.Relationships[0] + + from := s.Artifacts.PackageCatalog.Package(r.From.ID()) + assert.NotNil(t, from) + assert.Equal(t, "pkg-1", from.Name) + + to := s.Artifacts.PackageCatalog.Package(r.To.ID()) + assert.NotNil(t, to) + assert.Equal(t, "pkg-2", to.Name) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/validator.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/validator.go new file mode 100644 index 0000000000000000000000000000000000000000..d359b60d940363fc461b34d67fbd3e5c51016b02 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/syftjson/validator.go @@ -0,0 +1,31 @@ +package syftjson + +import ( + "encoding/json" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/internal/formats/syftjson/model" +) + +func validator(reader io.Reader) error { + type Document struct { + Schema model.Schema `json:"schema"` + } + + dec := json.NewDecoder(reader) + + var doc Document + err := dec.Decode(&doc) + if err != nil { + return fmt.Errorf("unable to decode: %w", err) + } + + // note: we accept all schema versions + // TODO: add per-schema version parsing + if strings.Contains(doc.Schema.URL, "anchore/syft") { + return nil + } + return fmt.Errorf("could not extract syft schema") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/table/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/table/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..e651674c5c2327bde6d6128044e806c305e39138 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/table/encoder.go @@ -0,0 +1,79 @@ +package table + +import ( + "fmt" + "io" + "sort" + "strings" + + "github.com/anchore/syft/syft/sbom" + + "github.com/olekukonko/tablewriter" +) + +func encoder(output io.Writer, s sbom.SBOM) error { + var rows [][]string + + columns := []string{"Name", "Version", "Type"} + for _, p := range s.Artifacts.PackageCatalog.Sorted() { + row := []string{ + p.Name, + p.Version, + string(p.Type), + } + rows = append(rows, row) + } + + if len(rows) == 0 { + _, err := fmt.Fprintln(output, "No packages discovered") + return err + } + + // sort by name, version, then type + sort.SliceStable(rows, func(i, j int) bool { + for col := 0; col < len(columns); col++ { + if rows[i][col] != rows[j][col] { + return rows[i][col] < rows[j][col] + } + } + return false + }) + rows = removeDuplicateRows(rows) + + table := tablewriter.NewWriter(output) + + table.SetHeader(columns) + table.SetHeaderLine(false) + table.SetBorder(false) + table.SetAutoWrapText(false) + table.SetAutoFormatHeaders(true) + table.SetHeaderAlignment(tablewriter.ALIGN_LEFT) + table.SetAlignment(tablewriter.ALIGN_LEFT) + table.SetCenterSeparator("") + table.SetColumnSeparator("") + table.SetRowSeparator("") + table.SetTablePadding(" ") + table.SetNoWhiteSpace(true) + + table.AppendBulk(rows) + table.Render() + + return nil +} + +func removeDuplicateRows(items [][]string) [][]string { + seen := map[string][]string{} + var result [][]string + + for _, v := range items { + key := strings.Join(v, "|") + if seen[key] != nil { + // dup! + continue + } + + seen[key] = v + result = append(result, v) + } + return result +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/table/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/table/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..b2ba0236889463b9d58219e2631c882f7e64635f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/table/encoder_test.go @@ -0,0 +1,48 @@ +package table + +import ( + "flag" + "testing" + + "github.com/anchore/syft/internal/formats/common/testutils" + "github.com/go-test/deep" +) + +var updateTableGoldenFiles = flag.Bool("update-table", false, "update the *.golden files for table format") + +func TestTableEncoder(t *testing.T) { + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + testutils.DirectoryInput(t), + *updateTableGoldenFiles, + ) +} + +func TestRemoveDuplicateRows(t *testing.T) { + data := [][]string{ + {"1", "2", "3"}, + {"a", "b", "c"}, + {"1", "2", "3"}, + {"a", "b", "c"}, + {"1", "2", "3"}, + {"4", "5", "6"}, + {"1", "2", "1"}, + } + + expected := [][]string{ + {"1", "2", "3"}, + {"a", "b", "c"}, + {"4", "5", "6"}, + {"1", "2", "1"}, + } + + actual := removeDuplicateRows(data) + + if diffs := deep.Equal(expected, actual); len(diffs) > 0 { + t.Errorf("found diffs!") + for _, d := range diffs { + t.Errorf(" diff: %+v", d) + } + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/table/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/table/format.go new file mode 100644 index 0000000000000000000000000000000000000000..66e60e0ec5e744b1e89e593e7a86ce6d4ca7d523 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/table/format.go @@ -0,0 +1,16 @@ +package table + +import ( + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "syft-table" + +func Format() sbom.Format { + return sbom.NewFormat( + ID, + encoder, + nil, + nil, + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/table/test-fixtures/snapshot/TestTableEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/table/test-fixtures/snapshot/TestTableEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..2094e69e0e5acedca7e2a128a425d2aac9e6f763 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/table/test-fixtures/snapshot/TestTableEncoder.golden @@ -0,0 +1,3 @@ +NAME VERSION TYPE +package-1 1.0.1 python +package-2 2.0.1 deb diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/template/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..8ef95b73a7f4bef728e93ea1166a30aceb632a72 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/encoder.go @@ -0,0 +1,49 @@ +package template + +import ( + "errors" + "fmt" + "os" + "reflect" + "text/template" + + "github.com/Masterminds/sprig/v3" + "github.com/mitchellh/go-homedir" +) + +func makeTemplateExecutor(templateFilePath string) (*template.Template, error) { + if templateFilePath == "" { + return nil, errors.New("no template file: please provide a template path") + } + + expandedPathToTemplateFile, err := homedir.Expand(templateFilePath) + if err != nil { + return nil, fmt.Errorf("unable to expand path %s", templateFilePath) + } + + templateContents, err := os.ReadFile(expandedPathToTemplateFile) + if err != nil { + return nil, fmt.Errorf("unable to get template content: %w", err) + } + + templateName := expandedPathToTemplateFile + tmpl, err := template.New(templateName).Funcs(funcMap).Parse(string(templateContents)) + if err != nil { + return nil, fmt.Errorf("unable to parse template: %w", err) + } + + return tmpl, nil +} + +// These are custom functions available to template authors. +var funcMap = func() template.FuncMap { + f := sprig.HermeticTxtFuncMap() + f["getLastIndex"] = func(collection interface{}) int { + if v := reflect.ValueOf(collection); v.Kind() == reflect.Slice { + return v.Len() - 1 + } + + return 0 + } + return f +}() diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/template/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..950d4f91460c4895296fc071ea84896d7728ab13 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/encoder_test.go @@ -0,0 +1,29 @@ +package template + +import ( + "flag" + "testing" + + "github.com/anchore/syft/internal/formats/common/testutils" + "github.com/stretchr/testify/assert" +) + +var updateTmpl = flag.Bool("update-tmpl", false, "update the *.golden files for json encoders") + +func TestFormatWithOption(t *testing.T) { + f := OutputFormat{} + f.SetTemplatePath("test-fixtures/csv.template") + + testutils.AssertEncoderAgainstGoldenSnapshot(t, + f, + testutils.DirectoryInput(t), + *updateTmpl, + ) + +} + +func TestFormatWithoutOptions(t *testing.T) { + f := Format() + err := f.Encode(nil, testutils.DirectoryInput(t)) + assert.ErrorContains(t, err, "no template file: please provide a template path") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/template/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/format.go new file mode 100644 index 0000000000000000000000000000000000000000..4b8f28a5ed17399b1d0eaa33aa30467439d36fc0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/format.go @@ -0,0 +1,47 @@ +package template + +import ( + "io" + + "github.com/anchore/syft/internal/formats/syftjson" + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "template" + +func Format() sbom.Format { + return OutputFormat{} +} + +// implementation of sbom.Format interface +// to make use of format options +type OutputFormat struct { + templateFilePath string +} + +func (f OutputFormat) ID() sbom.FormatID { + return ID +} + +func (f OutputFormat) Decode(reader io.Reader) (*sbom.SBOM, error) { + return nil, sbom.ErrDecodingNotSupported +} + +func (f OutputFormat) Encode(output io.Writer, s sbom.SBOM) error { + tmpl, err := makeTemplateExecutor(f.templateFilePath) + if err != nil { + return err + } + + doc := syftjson.ToFormatModel(s) + return tmpl.Execute(output, doc) +} + +func (f OutputFormat) Validate(reader io.Reader) error { + return sbom.ErrValidationNotSupported +} + +// SetTemplatePath sets path for template file +func (f *OutputFormat) SetTemplatePath(filePath string) { + f.templateFilePath = filePath +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/template/test-fixtures/csv.template b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/test-fixtures/csv.template new file mode 100644 index 0000000000000000000000000000000000000000..8474271adb2946bce1063fa37ca4d440df2a8fa6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/test-fixtures/csv.template @@ -0,0 +1,4 @@ +"Package","Version Installed", "Found by" +{{- range .Artifacts}} +"{{.Name}}","{{.Version}}","{{.FoundBy}}" +{{- end}} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/template/test-fixtures/snapshot/TestFormatWithOption.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/test-fixtures/snapshot/TestFormatWithOption.golden new file mode 100644 index 0000000000000000000000000000000000000000..a7bc3b7d3ffb7f275a0a657e2505e60843ac2cf6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/template/test-fixtures/snapshot/TestFormatWithOption.golden @@ -0,0 +1,3 @@ +"Package","Version Installed", "Found by" +"package-1","1.0.1","the-cataloger-1" +"package-2","2.0.1","the-cataloger-2" \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/encoder.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/encoder.go new file mode 100644 index 0000000000000000000000000000000000000000..ee97abd4a2cf78f86de211c0d6c5cbed76bd3e9e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/encoder.go @@ -0,0 +1,54 @@ +package text + +import ( + "fmt" + "io" + "text/tabwriter" + + "github.com/anchore/syft/syft/sbom" + + "github.com/anchore/syft/syft/source" +) + +func encoder(output io.Writer, s sbom.SBOM) error { + // init the tabular writer + w := new(tabwriter.Writer) + w.Init(output, 0, 8, 0, '\t', tabwriter.AlignRight) + + switch s.Source.Scheme { + case source.DirectoryScheme, source.FileScheme: + fmt.Fprintf(w, "[Path: %s]\n", s.Source.Path) + case source.ImageScheme: + fmt.Fprintln(w, "[Image]") + + for idx, l := range s.Source.ImageMetadata.Layers { + fmt.Fprintln(w, " Layer:\t", idx) + fmt.Fprintln(w, " Digest:\t", l.Digest) + fmt.Fprintln(w, " Size:\t", l.Size) + fmt.Fprintln(w, " MediaType:\t", l.MediaType) + fmt.Fprintln(w) + w.Flush() + } + default: + return fmt.Errorf("unsupported source: %T", s.Source.Scheme) + } + + // populate artifacts... + rows := 0 + for _, p := range s.Artifacts.PackageCatalog.Sorted() { + fmt.Fprintf(w, "[%s]\n", p.Name) + fmt.Fprintln(w, " Version:\t", p.Version) + fmt.Fprintln(w, " Type:\t", string(p.Type)) + fmt.Fprintln(w, " Found by:\t", p.FoundBy) + fmt.Fprintln(w) + w.Flush() + rows++ + } + + if rows == 0 { + fmt.Fprintln(output, "No packages discovered") + return nil + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/encoder_test.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/encoder_test.go new file mode 100644 index 0000000000000000000000000000000000000000..7d4a4cd7094b5d77ed7301210c475de9fdaea6db --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/encoder_test.go @@ -0,0 +1,28 @@ +package text + +import ( + "flag" + "testing" + + "github.com/anchore/syft/internal/formats/common/testutils" +) + +var updateTextEncoderGoldenFiles = flag.Bool("update-text", false, "update the *.golden files for text encoder") + +func TestTextDirectoryEncoder(t *testing.T) { + testutils.AssertEncoderAgainstGoldenSnapshot(t, + Format(), + testutils.DirectoryInput(t), + *updateTextEncoderGoldenFiles, + ) +} + +func TestTextImageEncoder(t *testing.T) { + testImage := "image-simple" + testutils.AssertEncoderAgainstGoldenImageSnapshot(t, + Format(), + testutils.ImageInput(t, testImage, testutils.FromSnapshot()), + testImage, + *updateTextEncoderGoldenFiles, + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/format.go b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/format.go new file mode 100644 index 0000000000000000000000000000000000000000..e8e5e98b553b504a7a0cf06b4fb74a622d7dedca --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/format.go @@ -0,0 +1,16 @@ +package text + +import ( + "github.com/anchore/syft/syft/sbom" +) + +const ID sbom.FormatID = "syft-text" + +func Format() sbom.Format { + return sbom.NewFormat( + ID, + encoder, + nil, + nil, + ) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/Dockerfile b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..79cfa759e357be9628894dea6332a0e6a2c33bb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/Dockerfile @@ -0,0 +1,4 @@ +# Note: changes to this file will result in updating several test values. Consider making a new image fixture instead of editing this one. +FROM scratch +ADD file-1.txt /somefile-1.txt +ADD file-2.txt /somefile-2.txt diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/file-1.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..985d3408e98cb9f41c01376c698451fdef0e4b32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/file-1.txt @@ -0,0 +1 @@ +this file has contents \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/file-2.txt b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..396d08bbc72f810ec6d057d1713a84a75d1cd542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/image-simple/file-2.txt @@ -0,0 +1 @@ +file-2 contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/TestTextDirectoryEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/TestTextDirectoryEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..25881f2d952c243cf09155292180d99a78ec8ce2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/TestTextDirectoryEncoder.golden @@ -0,0 +1,11 @@ +[Path: /some/path] +[package-1] + Version: 1.0.1 + Type: python + Found by: the-cataloger-1 + +[package-2] + Version: 2.0.1 + Type: deb + Found by: the-cataloger-2 + diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/TestTextImageEncoder.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/TestTextImageEncoder.golden new file mode 100644 index 0000000000000000000000000000000000000000..4ab3a446e0c5be1796cf130fea6dfdadf7ed6e73 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/TestTextImageEncoder.golden @@ -0,0 +1,21 @@ +[Image] + Layer: 0 + Digest: sha256:fb6beecb75b39f4bb813dbf177e501edd5ddb3e69bb45cedeb78c676ee1b7a59 + Size: 22 + MediaType: application/vnd.docker.image.rootfs.diff.tar.gzip + + Layer: 1 + Digest: sha256:319b588ce64253a87b533c8ed01cf0025e0eac98e7b516e12532957e1244fdec + Size: 16 + MediaType: application/vnd.docker.image.rootfs.diff.tar.gzip + +[package-1] + Version: 1.0.1 + Type: python + Found by: the-cataloger-1 + +[package-2] + Version: 2.0.1 + Type: deb + Found by: the-cataloger-2 + diff --git a/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden new file mode 100644 index 0000000000000000000000000000000000000000..c1b1d2b797ecd34a5276a1aa2fb18c5b0a58c732 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/internal/formats/text/test-fixtures/snapshot/stereoscope-fixture-image-simple.golden differ diff --git a/ci/tools/openeuler-purl/syft-dev/internal/input.go b/ci/tools/openeuler-purl/syft-dev/internal/input.go new file mode 100644 index 0000000000000000000000000000000000000000..914c4212deb7839990fcb16c39e2f8e162b4add7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/input.go @@ -0,0 +1,26 @@ +package internal + +import ( + "fmt" + "os" +) + +// IsPipedInput returns true if there is no input device, which means the user **may** be providing input via a pipe. +func IsPipedInput() (bool, error) { + fi, err := os.Stdin.Stat() + if err != nil { + return false, fmt.Errorf("unable to determine if there is piped input: %w", err) + } + + // note: we should NOT use the absence of a character device here as the hint that there may be input expected + // on stdin, as running syft as a subprocess you would expect no character device to be present but input can + // be from either stdin or indicated by the CLI. Checking if stdin is a pipe is the most direct way to determine + // if there *may* be bytes that will show up on stdin that should be used for the analysis source. + return fi.Mode()&os.ModeNamedPipe != 0, nil +} + +// IsTerminal returns true if there is a terminal present. +func IsTerminal() bool { + stat, _ := os.Stdin.Stat() + return (stat.Mode() & os.ModeCharDevice) != 0 +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/log/log.go b/ci/tools/openeuler-purl/syft-dev/internal/log/log.go new file mode 100644 index 0000000000000000000000000000000000000000..0dd2199c62c6c99b7254e44d6bf5860e26e7e1a0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/log/log.go @@ -0,0 +1,49 @@ +/* +Package log contains the singleton object and helper functions for facilitating logging within the syft library. +*/ +package log + +import "github.com/anchore/syft/syft/logger" + +// Log is the singleton used to facilitate logging internally within syft +var Log logger.Logger = &nopLogger{} + +// Errorf takes a formatted template string and template arguments for the error logging level. +func Errorf(format string, args ...interface{}) { + Log.Errorf(format, args...) +} + +// Error logs the given arguments at the error logging level. +func Error(args ...interface{}) { + Log.Error(args...) +} + +// Warnf takes a formatted template string and template arguments for the warning logging level. +func Warnf(format string, args ...interface{}) { + Log.Warnf(format, args...) +} + +// Warn logs the given arguments at the warning logging level. +func Warn(args ...interface{}) { + Log.Warn(args...) +} + +// Infof takes a formatted template string and template arguments for the info logging level. +func Infof(format string, args ...interface{}) { + Log.Infof(format, args...) +} + +// Info logs the given arguments at the info logging level. +func Info(args ...interface{}) { + Log.Info(args...) +} + +// Debugf takes a formatted template string and template arguments for the debug logging level. +func Debugf(format string, args ...interface{}) { + Log.Debugf(format, args...) +} + +// Debug logs the given arguments at the debug logging level. +func Debug(args ...interface{}) { + Log.Debug(args...) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/log/nop.go b/ci/tools/openeuler-purl/syft-dev/internal/log/nop.go new file mode 100644 index 0000000000000000000000000000000000000000..ff20e4612cba5b953b02de45ee43f17d718d11df --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/log/nop.go @@ -0,0 +1,12 @@ +package log + +type nopLogger struct{} + +func (l *nopLogger) Errorf(format string, args ...interface{}) {} +func (l *nopLogger) Error(args ...interface{}) {} +func (l *nopLogger) Warnf(format string, args ...interface{}) {} +func (l *nopLogger) Warn(args ...interface{}) {} +func (l *nopLogger) Infof(format string, args ...interface{}) {} +func (l *nopLogger) Info(args ...interface{}) {} +func (l *nopLogger) Debugf(format string, args ...interface{}) {} +func (l *nopLogger) Debug(args ...interface{}) {} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/logger/doc.go b/ci/tools/openeuler-purl/syft-dev/internal/logger/doc.go new file mode 100644 index 0000000000000000000000000000000000000000..59647a80c8b62f1d320dfb0a6126098043a79fa7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/logger/doc.go @@ -0,0 +1,4 @@ +/* +Package logger contains implementations for the syft.logger.Logger interface. +*/ +package logger diff --git a/ci/tools/openeuler-purl/syft-dev/internal/logger/logrus.go b/ci/tools/openeuler-purl/syft-dev/internal/logger/logrus.go new file mode 100644 index 0000000000000000000000000000000000000000..37983e61c4a1c232f85180a7ee4cff6b5936b7c9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/logger/logrus.go @@ -0,0 +1,163 @@ +package logger + +import ( + "fmt" + "io" + "io/fs" + "os" + + "github.com/sirupsen/logrus" + prefixed "github.com/x-cray/logrus-prefixed-formatter" +) + +const defaultLogFilePermissions fs.FileMode = 0644 + +// LogrusConfig contains all configurable values for the Logrus logger +type LogrusConfig struct { + EnableConsole bool + EnableFile bool + Structured bool + Level logrus.Level + FileLocation string +} + +// LogrusLogger contains all runtime values for using Logrus with the configured output target and input configuration values. +type LogrusLogger struct { + Config LogrusConfig + Logger *logrus.Logger + Output io.Writer +} + +// LogrusNestedLogger is a wrapper for Logrus to enable nested logging configuration (loggers that always attach key-value pairs to all log entries) +type LogrusNestedLogger struct { + Logger *logrus.Entry +} + +// NewLogrusLogger creates a new LogrusLogger with the given configuration +func NewLogrusLogger(cfg LogrusConfig) *LogrusLogger { + appLogger := logrus.New() + + var output io.Writer + switch { + case cfg.EnableConsole && cfg.EnableFile: + logFile, err := os.OpenFile(cfg.FileLocation, os.O_WRONLY|os.O_CREATE, defaultLogFilePermissions) + if err != nil { + panic(fmt.Errorf("unable to setup log file: %w", err)) + } + output = io.MultiWriter(os.Stderr, logFile) + case cfg.EnableConsole: + output = os.Stderr + case cfg.EnableFile: + logFile, err := os.OpenFile(cfg.FileLocation, os.O_WRONLY|os.O_CREATE, defaultLogFilePermissions) + if err != nil { + panic(fmt.Errorf("unable to setup log file: %w", err)) + } + output = logFile + default: + output = io.Discard + } + + appLogger.SetOutput(output) + appLogger.SetLevel(cfg.Level) + + if cfg.Structured { + appLogger.SetFormatter(&logrus.JSONFormatter{ + TimestampFormat: "2006-01-02 15:04:05", + DisableTimestamp: false, + DisableHTMLEscape: false, + PrettyPrint: false, + }) + } else { + appLogger.SetFormatter(&prefixed.TextFormatter{ + TimestampFormat: "2006-01-02 15:04:05", + ForceColors: true, + ForceFormatting: true, + }) + } + + return &LogrusLogger{ + Config: cfg, + Logger: appLogger, + Output: output, + } +} + +// Debugf takes a formatted template string and template arguments for the debug logging level. +func (l *LogrusLogger) Debugf(format string, args ...interface{}) { + l.Logger.Debugf(format, args...) +} + +// Infof takes a formatted template string and template arguments for the info logging level. +func (l *LogrusLogger) Infof(format string, args ...interface{}) { + l.Logger.Infof(format, args...) +} + +// Warnf takes a formatted template string and template arguments for the warning logging level. +func (l *LogrusLogger) Warnf(format string, args ...interface{}) { + l.Logger.Warnf(format, args...) +} + +// Errorf takes a formatted template string and template arguments for the error logging level. +func (l *LogrusLogger) Errorf(format string, args ...interface{}) { + l.Logger.Errorf(format, args...) +} + +// Debug logs the given arguments at the debug logging level. +func (l *LogrusLogger) Debug(args ...interface{}) { + l.Logger.Debug(args...) +} + +// Info logs the given arguments at the info logging level. +func (l *LogrusLogger) Info(args ...interface{}) { + l.Logger.Info(args...) +} + +// Warn logs the given arguments at the warning logging level. +func (l *LogrusLogger) Warn(args ...interface{}) { + l.Logger.Warn(args...) +} + +// Error logs the given arguments at the error logging level. +func (l *LogrusLogger) Error(args ...interface{}) { + l.Logger.Error(args...) +} + +// Debugf takes a formatted template string and template arguments for the debug logging level. +func (l *LogrusNestedLogger) Debugf(format string, args ...interface{}) { + l.Logger.Debugf(format, args...) +} + +// Infof takes a formatted template string and template arguments for the info logging level. +func (l *LogrusNestedLogger) Infof(format string, args ...interface{}) { + l.Logger.Infof(format, args...) +} + +// Warnf takes a formatted template string and template arguments for the warning logging level. +func (l *LogrusNestedLogger) Warnf(format string, args ...interface{}) { + l.Logger.Warnf(format, args...) +} + +// Errorf takes a formatted template string and template arguments for the error logging level. +func (l *LogrusNestedLogger) Errorf(format string, args ...interface{}) { + l.Logger.Errorf(format, args...) +} + +// Debug logs the given arguments at the debug logging level. +func (l *LogrusNestedLogger) Debug(args ...interface{}) { + l.Logger.Debug(args...) +} + +// Info logs the given arguments at the info logging level. +func (l *LogrusNestedLogger) Info(args ...interface{}) { + l.Logger.Info(args...) +} + +// Warn logs the given arguments at the warning logging level. +func (l *LogrusNestedLogger) Warn(args ...interface{}) { + l.Logger.Warn(args...) +} + +// Error logs the given arguments at the error logging level. +func (l *LogrusNestedLogger) Error(args ...interface{}) { + l.Logger.Error(args...) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/mimetype_helper.go b/ci/tools/openeuler-purl/syft-dev/internal/mimetype_helper.go new file mode 100644 index 0000000000000000000000000000000000000000..3dbc360982f44a4be45d830589d41974d48735e8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/mimetype_helper.go @@ -0,0 +1,72 @@ +package internal + +import "github.com/scylladb/go-set/strset" + +var ( + ArchiveMIMETypeSet = strset.New( + // derived from https://en.wikipedia.org/wiki/List_of_archive_formats + []string{ + // archive only + "application/x-archive", + "application/x-cpio", + "application/x-shar", + "application/x-iso9660-image", + "application/x-sbx", + "application/x-tar", + // compression only + "application/x-bzip2", + "application/gzip", + "application/x-lzip", + "application/x-lzma", + "application/x-lzop", + "application/x-snappy-framed", + "application/x-xz", + "application/x-compress", + "application/zstd", + // archiving and compression + "application/x-7z-compressed", + "application/x-ace-compressed", + "application/x-astrotite-afa", + "application/x-alz-compressed", + "application/vnd.android.package-archive", + "application/x-freearc", + "application/x-arj", + "application/x-b1", + "application/vnd.ms-cab-compressed", + "application/x-cfs-compressed", + "application/x-dar", + "application/x-dgc-compressed", + "application/x-apple-diskimage", + "application/x-gca-compressed", + "application/java-archive", + "application/x-lzh", + "application/x-lzx", + "application/x-rar-compressed", + "application/x-stuffit", + "application/x-stuffitx", + "application/x-gtar", + "application/x-ms-wim", + "application/x-xar", + "application/zip", + "application/x-zoo", + }..., + ) + + ExecutableMIMETypeSet = strset.New( + []string{ + "application/x-executable", + "application/x-mach-binary", + "application/x-elf", + "application/x-sharedlib", + "application/vnd.microsoft.portable-executable", + }..., + ) +) + +func IsArchive(mimeType string) bool { + return ArchiveMIMETypeSet.Has(mimeType) +} + +func IsExecutable(mimeType string) bool { + return ExecutableMIMETypeSet.Has(mimeType) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/mimetype_helper_test.go b/ci/tools/openeuler-purl/syft-dev/internal/mimetype_helper_test.go new file mode 100644 index 0000000000000000000000000000000000000000..9a3f245e82fbdbc601ce0be577f0f6e7ec29d92b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/mimetype_helper_test.go @@ -0,0 +1,57 @@ +package internal + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func Test_IsArchive(t *testing.T) { + + tests := []struct { + name string + mimeType string + expected bool + }{ + { + name: "not an archive", + mimeType: "application/vnd.unknown", + expected: false, + }, + { + name: "archive", + mimeType: "application/x-rar-compressed", + expected: true, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, IsArchive(test.mimeType)) + }) + } +} + +func Test_IsExecutable(t *testing.T) { + + tests := []struct { + name string + mimeType string + expected bool + }{ + { + name: "not an executable", + mimeType: "application/vnd.unknown", + expected: false, + }, + { + name: "executable", + mimeType: "application/x-mach-binary", + expected: true, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, IsExecutable(test.mimeType)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/regex_helpers.go b/ci/tools/openeuler-purl/syft-dev/internal/regex_helpers.go new file mode 100644 index 0000000000000000000000000000000000000000..7130f21a89cf2bda69ac6b20d10c4490b0548708 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/regex_helpers.go @@ -0,0 +1,45 @@ +package internal + +import "regexp" + +// MatchNamedCaptureGroups takes a regular expression and string and returns all of the named capture group results in a map. +// This is only for the first match in the regex. Callers shouldn't be providing regexes with multiple capture groups with the same name. +func MatchNamedCaptureGroups(regEx *regexp.Regexp, content string) map[string]string { + // note: we are looking across all matches and stopping on the first non-empty match. Why? Take the following example: + // input: "cool something to match against" pattern: `((?Pmatch) (?Pagainst))?`. Since the pattern is + // encapsulated in an optional capture group, there will be results for each character, but the results will match + // on nothing. The only "true" match will be at the end ("match against"). + allMatches := regEx.FindAllStringSubmatch(content, -1) + var results map[string]string + for _, match := range allMatches { + // fill a candidate results map with named capture group results, accepting empty values, but not groups with + // no names + for nameIdx, name := range regEx.SubexpNames() { + if nameIdx > len(match) || len(name) == 0 { + continue + } + if results == nil { + results = make(map[string]string) + } + results[name] = match[nameIdx] + } + // note: since we are looking for the first best potential match we should stop when we find the first one + // with non-empty results. + if !isEmptyMap(results) { + break + } + } + return results +} + +func isEmptyMap(m map[string]string) bool { + if len(m) == 0 { + return true + } + for _, value := range m { + if value != "" { + return false + } + } + return true +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/regex_helpers_test.go b/ci/tools/openeuler-purl/syft-dev/internal/regex_helpers_test.go new file mode 100644 index 0000000000000000000000000000000000000000..1c48377530946856140290d7bb412252144d8ef3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/regex_helpers_test.go @@ -0,0 +1,70 @@ +package internal + +import ( + "regexp" + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestMatchCaptureGroups(t *testing.T) { + tests := []struct { + name string + input string + pattern string + expected map[string]string + }{ + { + name: "go-case", + input: "match this thing", + pattern: `(?Pmatch).*(?Pthing)`, + expected: map[string]string{ + "name": "match", + "version": "thing", + }, + }, + { + name: "only matches the first instance", + input: "match this thing batch another think", + pattern: `(?P[mb]atch).*?(?Pthin[gk])`, + expected: map[string]string{ + "name": "match", + "version": "thing", + }, + }, + { + name: "nested capture groups", + input: "cool something to match against", + pattern: `((?Pmatch) (?Pagainst))`, + expected: map[string]string{ + "name": "match", + "version": "against", + }, + }, + { + name: "nested optional capture groups", + input: "cool something to match against", + pattern: `((?Pmatch) (?Pagainst))?`, + expected: map[string]string{ + "name": "match", + "version": "against", + }, + }, + { + name: "nested optional capture groups with larger match", + input: "cool something to match against match never", + pattern: `.*?((?Pmatch) (?P(against|never)))?`, + expected: map[string]string{ + "name": "match", + "version": "against", + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := MatchNamedCaptureGroups(regexp.MustCompile(test.pattern), test.input) + assert.Equal(t, test.expected, actual) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/generate_license_list.go b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/generate_license_list.go new file mode 100644 index 0000000000000000000000000000000000000000..04ffb2bbf317e28ac7c7c3ca4461f0f870335bc8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/generate_license_list.go @@ -0,0 +1,160 @@ +package main + +import ( + "encoding/json" + "fmt" + "log" + "net/http" + "os" + "regexp" + "sort" + "strings" + "text/template" + "time" + + "github.com/scylladb/go-set/strset" +) + +// This program generates license_list.go. +const ( + source = "license_list.go" + url = "https://spdx.org/licenses/licenses.json" +) + +var tmp = template.Must(template.New("").Parse(`// Code generated by go generate; DO NOT EDIT. +// This file was generated by robots at {{ .Timestamp }} +// using data from {{ .URL }} +package spdxlicense + +const Version = {{ printf "%q" .Version }} + +var licenseIDs = map[string]string{ +{{- range $k, $v := .LicenseIDs }} + {{ printf "%q" $k }}: {{ printf "%q" $v }}, +{{- end }} +} +`)) + +var versionMatch = regexp.MustCompile(`-([0-9]+)\.?([0-9]+)?\.?([0-9]+)?\.?`) + +func main() { + if err := run(); err != nil { + fmt.Println(err.Error()) + os.Exit(1) + } +} + +func run() error { + resp, err := http.Get(url) + if err != nil { + return fmt.Errorf("unable to get licenses list: %+v", err) + } + + var result LicenseList + if err = json.NewDecoder(resp.Body).Decode(&result); err != nil { + return fmt.Errorf("unable to decode license list: %+v", err) + } + defer func() { + if err := resp.Body.Close(); err != nil { + log.Fatalf("unable to close body: %+v", err) + } + }() + + f, err := os.Create(source) + if err != nil { + return fmt.Errorf("unable to create %q: %+v", source, err) + } + defer func() { + if err := f.Close(); err != nil { + log.Fatalf("unable to close %q: %+v", source, err) + } + }() + + licenseIDs := processSPDXLicense(result) + + err = tmp.Execute(f, struct { + Timestamp time.Time + URL string + Version string + LicenseIDs map[string]string + }{ + Timestamp: time.Now(), + URL: url, + Version: result.Version, + LicenseIDs: licenseIDs, + }) + + if err != nil { + return fmt.Errorf("unable to generate template: %+v", err) + } + return nil +} + +// Parsing the provided SPDX license list necessitates a three pass approach. +// The first pass is only related to what SPDX considers the truth. We use license info to +// find replacements for deprecated licenses. +// The second pass attempts to generate known short/long version listings for each key. +// For info on some short name conventions see this document: +// https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/#license-short-name. +// The short long listing generation attempts to build all license permutations for a given key. +// The new keys are then also associated with their relative SPDX value. If a key has already been entered +// we know to ignore it since it came from the first pass which is considered the SPDX source of truth. +// We also sort the licenses for the second pass so that cases like `GPL-1` associate to `GPL-1.0` and not `GPL-1.1`. +// The third pass is for overwriting deprecated licenses with replacements, for example GPL-2.0+ is deprecated +// and now maps to GPL-2.0-or-later. +func processSPDXLicense(result LicenseList) map[string]string { + // first pass build map + var licenseIDs = make(map[string]string) + for _, l := range result.Licenses { + cleanID := strings.ToLower(l.ID) + if _, exists := licenseIDs[cleanID]; exists { + log.Fatalf("duplicate license ID found: %q", cleanID) + } + licenseIDs[cleanID] = l.ID + } + + // The order of variations/permutations of a license ID matters because of we how shuffle its digits, + // that is because the permutation code can generate the same value for two difference licenses, + // for example: The licenses `ABC-1.0` and `ABC-1.1` can both map to `ABC-1`, + // so we need to guarantee the order they are created to avoid mapping them wrongly. So we use a sorted list. + // To overwrite deprecated licenses during the first pass we would later on rely on map order, + // [which in go is not consistent by design](https://stackoverflow.com/a/55925880). + sort.Slice(result.Licenses, func(i, j int) bool { + return result.Licenses[i].ID < result.Licenses[j].ID + }) + + // second pass to build exceptions and replacements + replaced := strset.New() + for _, l := range result.Licenses { + var multipleID []string + cleanID := strings.ToLower(l.ID) + + var replacement *License + if l.Deprecated { + replacement = result.findReplacementLicense(l) + if replacement != nil { + licenseIDs[cleanID] = replacement.ID + } + } + + multipleID = append(multipleID, buildLicensePermutations(cleanID)...) + for _, id := range multipleID { + // don't make replacements for IDs that have already been replaced. Since we have a sorted license list + // the earliest replacement is correct (any future replacements are not. + // e.g. replace lgpl-2 with LGPL-2.1-only is wrong, but with LGPL-2.0-only is correct) + if replacement == nil || replaced.Has(id) { + if _, exists := licenseIDs[id]; !exists { + licenseIDs[id] = l.ID + } + } else { + // a useful debugging line during builds + log.Printf("replacing %s with %s\n", id, replacement.ID) + + licenseIDs[id] = replacement.ID + replaced.Add(id) + } + } + } + + return licenseIDs +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/generate_license_list_test.go b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/generate_license_list_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d730db1413ab491b20f417ebd9096b089b62754c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/generate_license_list_test.go @@ -0,0 +1,1128 @@ +package main + +import ( + "encoding/json" + "github.com/google/go-cmp/cmp" + "os" + "testing" + + "github.com/stretchr/testify/require" +) + +func TestReplaceDeprecatedLicenses(t *testing.T) { + results := LicenseList{ + Licenses: []License{ + license1, + license2, + license3, + license4, + license5, + license6, + }, + } + + expected := map[string]string{ + "abc-1": "ABC-1.0-Only", + "abc-1-only": "ABC-1.0-Only", + "abc-1.0": "ABC-1.0-Only", + "abc-1.0.0": "ABC-1.0-Only", + "abc-1.0-only": "ABC-1.0-Only", + "abc-1.0.0-only": "ABC-1.0-Only", + "abc-1+": "ABC-1.0-Or-later", + "abc-1.0+": "ABC-1.0-Or-later", + "abc-1.0.0+": "ABC-1.0-Or-later", + "abc-1-or-later": "ABC-1.0-Or-later", + "abc-1.0-or-later": "ABC-1.0-Or-later", + "abc-1.0.0-or-later": "ABC-1.0-Or-later", + "duh-1": "Duh-1.0", + "duh-1.0": "Duh-1.0", + "duh-1.0.0": "Duh-1.0", + "duh-1-duh": "Duh-1.0-duh", + "duh-1.0-duh": "Duh-1.0-duh", + "duh-1.0.0-duh": "Duh-1.0-duh", + } + + licenses := processSPDXLicense(results) + for k, v := range licenses { + e := expected[k] + require.Equal(t, e, v, k) + } +} + +func Test_processSPDXLicense(t *testing.T) { + tests := []struct { + fixture string + want map[string]string + }{ + { + fixture: "test-fixtures/licenses.json", + want: map[string]string{ + "0bsd": "0BSD", + "aal": "AAL", + "abstyles": "Abstyles", + "adobe-2006": "Adobe-2006", + "adobe-2006.0": "Adobe-2006", + "adobe-2006.0.0": "Adobe-2006", + "adobe-glyph": "Adobe-Glyph", + "adsl": "ADSL", + "afl-1": "AFL-1.1", + "afl-1.1": "AFL-1.1", + "afl-1.1.0": "AFL-1.1", + "afl-1.2": "AFL-1.2", + "afl-1.2.0": "AFL-1.2", + "afl-2": "AFL-2.0", + "afl-2.0": "AFL-2.0", + "afl-2.0.0": "AFL-2.0", + "afl-2.1": "AFL-2.1", + "afl-2.1.0": "AFL-2.1", + "afl-3": "AFL-3.0", + "afl-3.0": "AFL-3.0", + "afl-3.0.0": "AFL-3.0", + "afmparse": "Afmparse", + "agpl-1": "AGPL-1.0", + "agpl-1-only": "AGPL-1.0-only", + "agpl-1-or-later": "AGPL-1.0-or-later", + "agpl-1.0": "AGPL-1.0", + "agpl-1.0-only": "AGPL-1.0-only", + "agpl-1.0-or-later": "AGPL-1.0-or-later", + "agpl-1.0.0": "AGPL-1.0", + "agpl-1.0.0-only": "AGPL-1.0-only", + "agpl-1.0.0-or-later": "AGPL-1.0-or-later", + "agpl-3": "AGPL-3.0", + "agpl-3-only": "AGPL-3.0-only", + "agpl-3-or-later": "AGPL-3.0-or-later", + "agpl-3.0": "AGPL-3.0", + "agpl-3.0-only": "AGPL-3.0-only", + "agpl-3.0-or-later": "AGPL-3.0-or-later", + "agpl-3.0.0": "AGPL-3.0", + "agpl-3.0.0-only": "AGPL-3.0-only", + "agpl-3.0.0-or-later": "AGPL-3.0-or-later", + "aladdin": "Aladdin", + "amdplpa": "AMDPLPA", + "aml": "AML", + "ampas": "AMPAS", + "antlr-pd": "ANTLR-PD", + "antlr-pd-fallback": "ANTLR-PD-fallback", + "apache-1": "Apache-1.0", + "apache-1.0": "Apache-1.0", + "apache-1.0.0": "Apache-1.0", + "apache-1.1": "Apache-1.1", + "apache-1.1.0": "Apache-1.1", + "apache-2": "Apache-2.0", + "apache-2.0": "Apache-2.0", + "apache-2.0.0": "Apache-2.0", + "apafml": "APAFML", + "apl-1": "APL-1.0", + "apl-1.0": "APL-1.0", + "apl-1.0.0": "APL-1.0", + "app-s2p": "App-s2p", + "apsl-1": "APSL-1.0", + "apsl-1.0": "APSL-1.0", + "apsl-1.0.0": "APSL-1.0", + "apsl-1.1": "APSL-1.1", + "apsl-1.1.0": "APSL-1.1", + "apsl-1.2": "APSL-1.2", + "apsl-1.2.0": "APSL-1.2", + "apsl-2": "APSL-2.0", + "apsl-2.0": "APSL-2.0", + "apsl-2.0.0": "APSL-2.0", + "arphic-1999": "Arphic-1999", + "arphic-1999.0": "Arphic-1999", + "arphic-1999.0.0": "Arphic-1999", + "artistic-1": "Artistic-1.0", + "artistic-1-cl8": "Artistic-1.0-cl8", + "artistic-1-perl": "Artistic-1.0-Perl", + "artistic-1.0": "Artistic-1.0", + "artistic-1.0-cl8": "Artistic-1.0-cl8", + "artistic-1.0-perl": "Artistic-1.0-Perl", + "artistic-1.0.0": "Artistic-1.0", + "artistic-1.0.0-cl8": "Artistic-1.0-cl8", + "artistic-1.0.0-perl": "Artistic-1.0-Perl", + "artistic-2": "Artistic-2.0", + "artistic-2.0": "Artistic-2.0", + "artistic-2.0.0": "Artistic-2.0", + "baekmuk": "Baekmuk", + "bahyph": "Bahyph", + "barr": "Barr", + "beerware": "Beerware", + "bitstream-vera": "Bitstream-Vera", + "bittorrent-1": "BitTorrent-1.0", + "bittorrent-1.0": "BitTorrent-1.0", + "bittorrent-1.0.0": "BitTorrent-1.0", + "bittorrent-1.1": "BitTorrent-1.1", + "bittorrent-1.1.0": "BitTorrent-1.1", + "blessing": "blessing", + "blueoak-1": "BlueOak-1.0.0", + "blueoak-1.0": "BlueOak-1.0.0", + "blueoak-1.0.0": "BlueOak-1.0.0", + "borceux": "Borceux", + "bsd-1-clause": "BSD-1-Clause", + "bsd-1.0-clause": "BSD-1-Clause", + "bsd-1.0.0-clause": "BSD-1-Clause", + "bsd-2-clause": "BSD-2-Clause", + "bsd-2-clause-freebsd": "BSD-2-Clause-FreeBSD", + "bsd-2-clause-netbsd": "BSD-2-Clause-NetBSD", + "bsd-2-clause-patent": "BSD-2-Clause-Patent", + "bsd-2-clause-views": "BSD-2-Clause-Views", + "bsd-2.0-clause": "BSD-2-Clause", + "bsd-2.0-clause-freebsd": "BSD-2-Clause-FreeBSD", + "bsd-2.0-clause-netbsd": "BSD-2-Clause-NetBSD", + "bsd-2.0-clause-patent": "BSD-2-Clause-Patent", + "bsd-2.0-clause-views": "BSD-2-Clause-Views", + "bsd-2.0.0-clause": "BSD-2-Clause", + "bsd-2.0.0-clause-freebsd": "BSD-2-Clause-FreeBSD", + "bsd-2.0.0-clause-netbsd": "BSD-2-Clause-NetBSD", + "bsd-2.0.0-clause-patent": "BSD-2-Clause-Patent", + "bsd-2.0.0-clause-views": "BSD-2-Clause-Views", + "bsd-3-clause": "BSD-3-Clause", + "bsd-3-clause-attribution": "BSD-3-Clause-Attribution", + "bsd-3-clause-clear": "BSD-3-Clause-Clear", + "bsd-3-clause-lbnl": "BSD-3-Clause-LBNL", + "bsd-3-clause-modification": "BSD-3-Clause-Modification", + "bsd-3-clause-no-military-license": "BSD-3-Clause-No-Military-License", + "bsd-3-clause-no-nuclear-license": "BSD-3-Clause-No-Nuclear-License", + "bsd-3-clause-no-nuclear-license-2014": "BSD-3-Clause-No-Nuclear-License-2014", + "bsd-3-clause-no-nuclear-warranty": "BSD-3-Clause-No-Nuclear-Warranty", + "bsd-3-clause-open-mpi": "BSD-3-Clause-Open-MPI", + "bsd-3.0-clause": "BSD-3-Clause", + "bsd-3.0-clause-attribution": "BSD-3-Clause-Attribution", + "bsd-3.0-clause-clear": "BSD-3-Clause-Clear", + "bsd-3.0-clause-lbnl": "BSD-3-Clause-LBNL", + "bsd-3.0-clause-modification": "BSD-3-Clause-Modification", + "bsd-3.0-clause-no-military-license": "BSD-3-Clause-No-Military-License", + "bsd-3.0-clause-no-nuclear-license": "BSD-3-Clause-No-Nuclear-License", + "bsd-3.0-clause-no-nuclear-license-2014": "BSD-3-Clause-No-Nuclear-License-2014", + "bsd-3.0-clause-no-nuclear-warranty": "BSD-3-Clause-No-Nuclear-Warranty", + "bsd-3.0-clause-open-mpi": "BSD-3-Clause-Open-MPI", + "bsd-3.0.0-clause": "BSD-3-Clause", + "bsd-3.0.0-clause-attribution": "BSD-3-Clause-Attribution", + "bsd-3.0.0-clause-clear": "BSD-3-Clause-Clear", + "bsd-3.0.0-clause-lbnl": "BSD-3-Clause-LBNL", + "bsd-3.0.0-clause-modification": "BSD-3-Clause-Modification", + "bsd-3.0.0-clause-no-military-license": "BSD-3-Clause-No-Military-License", + "bsd-3.0.0-clause-no-nuclear-license": "BSD-3-Clause-No-Nuclear-License", + "bsd-3.0.0-clause-no-nuclear-license-2014": "BSD-3-Clause-No-Nuclear-License-2014", + "bsd-3.0.0-clause-no-nuclear-warranty": "BSD-3-Clause-No-Nuclear-Warranty", + "bsd-3.0.0-clause-open-mpi": "BSD-3-Clause-Open-MPI", + "bsd-4-clause": "BSD-4-Clause", + "bsd-4-clause-shortened": "BSD-4-Clause-Shortened", + "bsd-4-clause-uc": "BSD-4-Clause-UC", + "bsd-4.0-clause": "BSD-4-Clause", + "bsd-4.0-clause-shortened": "BSD-4-Clause-Shortened", + "bsd-4.0-clause-uc": "BSD-4-Clause-UC", + "bsd-4.0.0-clause": "BSD-4-Clause", + "bsd-4.0.0-clause-shortened": "BSD-4-Clause-Shortened", + "bsd-4.0.0-clause-uc": "BSD-4-Clause-UC", + "bsd-protection": "BSD-Protection", + "bsd-source-code": "BSD-Source-Code", + "bsl-1": "BSL-1.0", + "bsl-1.0": "BSL-1.0", + "bsl-1.0.0": "BSL-1.0", + "busl-1": "BUSL-1.1", + "busl-1.1": "BUSL-1.1", + "busl-1.1.0": "BUSL-1.1", + "bzip2-1": "bzip2-1.0.5", + "bzip2-1.0": "bzip2-1.0.5", + "bzip2-1.0.5": "bzip2-1.0.5", + "bzip2-1.0.6": "bzip2-1.0.6", + "c-uda-1": "C-UDA-1.0", + "c-uda-1.0": "C-UDA-1.0", + "c-uda-1.0.0": "C-UDA-1.0", + "cal-1": "CAL-1.0", + "cal-1-combined-work-exception": "CAL-1.0-Combined-Work-Exception", + "cal-1.0": "CAL-1.0", + "cal-1.0-combined-work-exception": "CAL-1.0-Combined-Work-Exception", + "cal-1.0.0": "CAL-1.0", + "cal-1.0.0-combined-work-exception": "CAL-1.0-Combined-Work-Exception", + "caldera": "Caldera", + "catosl-1": "CATOSL-1.1", + "catosl-1.1": "CATOSL-1.1", + "catosl-1.1.0": "CATOSL-1.1", + "cc-by-1": "CC-BY-1.0", + "cc-by-1.0": "CC-BY-1.0", + "cc-by-1.0.0": "CC-BY-1.0", + "cc-by-2": "CC-BY-2.0", + "cc-by-2-au": "CC-BY-2.5-AU", + "cc-by-2.0": "CC-BY-2.0", + "cc-by-2.0.0": "CC-BY-2.0", + "cc-by-2.5": "CC-BY-2.5", + "cc-by-2.5-au": "CC-BY-2.5-AU", + "cc-by-2.5.0": "CC-BY-2.5", + "cc-by-2.5.0-au": "CC-BY-2.5-AU", + "cc-by-3": "CC-BY-3.0", + "cc-by-3-at": "CC-BY-3.0-AT", + "cc-by-3-de": "CC-BY-3.0-DE", + "cc-by-3-nl": "CC-BY-3.0-NL", + "cc-by-3-us": "CC-BY-3.0-US", + "cc-by-3.0": "CC-BY-3.0", + "cc-by-3.0-at": "CC-BY-3.0-AT", + "cc-by-3.0-de": "CC-BY-3.0-DE", + "cc-by-3.0-nl": "CC-BY-3.0-NL", + "cc-by-3.0-us": "CC-BY-3.0-US", + "cc-by-3.0.0": "CC-BY-3.0", + "cc-by-3.0.0-at": "CC-BY-3.0-AT", + "cc-by-3.0.0-de": "CC-BY-3.0-DE", + "cc-by-3.0.0-nl": "CC-BY-3.0-NL", + "cc-by-3.0.0-us": "CC-BY-3.0-US", + "cc-by-4": "CC-BY-4.0", + "cc-by-4.0": "CC-BY-4.0", + "cc-by-4.0.0": "CC-BY-4.0", + "cc-by-nc-1": "CC-BY-NC-1.0", + "cc-by-nc-1.0": "CC-BY-NC-1.0", + "cc-by-nc-1.0.0": "CC-BY-NC-1.0", + "cc-by-nc-2": "CC-BY-NC-2.0", + "cc-by-nc-2.0": "CC-BY-NC-2.0", + "cc-by-nc-2.0.0": "CC-BY-NC-2.0", + "cc-by-nc-2.5": "CC-BY-NC-2.5", + "cc-by-nc-2.5.0": "CC-BY-NC-2.5", + "cc-by-nc-3": "CC-BY-NC-3.0", + "cc-by-nc-3-de": "CC-BY-NC-3.0-DE", + "cc-by-nc-3.0": "CC-BY-NC-3.0", + "cc-by-nc-3.0-de": "CC-BY-NC-3.0-DE", + "cc-by-nc-3.0.0": "CC-BY-NC-3.0", + "cc-by-nc-3.0.0-de": "CC-BY-NC-3.0-DE", + "cc-by-nc-4": "CC-BY-NC-4.0", + "cc-by-nc-4.0": "CC-BY-NC-4.0", + "cc-by-nc-4.0.0": "CC-BY-NC-4.0", + "cc-by-nc-nd-1": "CC-BY-NC-ND-1.0", + "cc-by-nc-nd-1.0": "CC-BY-NC-ND-1.0", + "cc-by-nc-nd-1.0.0": "CC-BY-NC-ND-1.0", + "cc-by-nc-nd-2": "CC-BY-NC-ND-2.0", + "cc-by-nc-nd-2.0": "CC-BY-NC-ND-2.0", + "cc-by-nc-nd-2.0.0": "CC-BY-NC-ND-2.0", + "cc-by-nc-nd-2.5": "CC-BY-NC-ND-2.5", + "cc-by-nc-nd-2.5.0": "CC-BY-NC-ND-2.5", + "cc-by-nc-nd-3": "CC-BY-NC-ND-3.0", + "cc-by-nc-nd-3-de": "CC-BY-NC-ND-3.0-DE", + "cc-by-nc-nd-3-igo": "CC-BY-NC-ND-3.0-IGO", + "cc-by-nc-nd-3.0": "CC-BY-NC-ND-3.0", + "cc-by-nc-nd-3.0-de": "CC-BY-NC-ND-3.0-DE", + "cc-by-nc-nd-3.0-igo": "CC-BY-NC-ND-3.0-IGO", + "cc-by-nc-nd-3.0.0": "CC-BY-NC-ND-3.0", + "cc-by-nc-nd-3.0.0-de": "CC-BY-NC-ND-3.0-DE", + "cc-by-nc-nd-3.0.0-igo": "CC-BY-NC-ND-3.0-IGO", + "cc-by-nc-nd-4": "CC-BY-NC-ND-4.0", + "cc-by-nc-nd-4.0": "CC-BY-NC-ND-4.0", + "cc-by-nc-nd-4.0.0": "CC-BY-NC-ND-4.0", + "cc-by-nc-sa-1": "CC-BY-NC-SA-1.0", + "cc-by-nc-sa-1.0": "CC-BY-NC-SA-1.0", + "cc-by-nc-sa-1.0.0": "CC-BY-NC-SA-1.0", + "cc-by-nc-sa-2": "CC-BY-NC-SA-2.0", + "cc-by-nc-sa-2-fr": "CC-BY-NC-SA-2.0-FR", + "cc-by-nc-sa-2-uk": "CC-BY-NC-SA-2.0-UK", + "cc-by-nc-sa-2.0": "CC-BY-NC-SA-2.0", + "cc-by-nc-sa-2.0-fr": "CC-BY-NC-SA-2.0-FR", + "cc-by-nc-sa-2.0-uk": "CC-BY-NC-SA-2.0-UK", + "cc-by-nc-sa-2.0.0": "CC-BY-NC-SA-2.0", + "cc-by-nc-sa-2.0.0-fr": "CC-BY-NC-SA-2.0-FR", + "cc-by-nc-sa-2.0.0-uk": "CC-BY-NC-SA-2.0-UK", + "cc-by-nc-sa-2.5": "CC-BY-NC-SA-2.5", + "cc-by-nc-sa-2.5.0": "CC-BY-NC-SA-2.5", + "cc-by-nc-sa-3": "CC-BY-NC-SA-3.0", + "cc-by-nc-sa-3-de": "CC-BY-NC-SA-3.0-DE", + "cc-by-nc-sa-3-igo": "CC-BY-NC-SA-3.0-IGO", + "cc-by-nc-sa-3.0": "CC-BY-NC-SA-3.0", + "cc-by-nc-sa-3.0-de": "CC-BY-NC-SA-3.0-DE", + "cc-by-nc-sa-3.0-igo": "CC-BY-NC-SA-3.0-IGO", + "cc-by-nc-sa-3.0.0": "CC-BY-NC-SA-3.0", + "cc-by-nc-sa-3.0.0-de": "CC-BY-NC-SA-3.0-DE", + "cc-by-nc-sa-3.0.0-igo": "CC-BY-NC-SA-3.0-IGO", + "cc-by-nc-sa-4": "CC-BY-NC-SA-4.0", + "cc-by-nc-sa-4.0": "CC-BY-NC-SA-4.0", + "cc-by-nc-sa-4.0.0": "CC-BY-NC-SA-4.0", + "cc-by-nd-1": "CC-BY-ND-1.0", + "cc-by-nd-1.0": "CC-BY-ND-1.0", + "cc-by-nd-1.0.0": "CC-BY-ND-1.0", + "cc-by-nd-2": "CC-BY-ND-2.0", + "cc-by-nd-2.0": "CC-BY-ND-2.0", + "cc-by-nd-2.0.0": "CC-BY-ND-2.0", + "cc-by-nd-2.5": "CC-BY-ND-2.5", + "cc-by-nd-2.5.0": "CC-BY-ND-2.5", + "cc-by-nd-3": "CC-BY-ND-3.0", + "cc-by-nd-3-de": "CC-BY-ND-3.0-DE", + "cc-by-nd-3.0": "CC-BY-ND-3.0", + "cc-by-nd-3.0-de": "CC-BY-ND-3.0-DE", + "cc-by-nd-3.0.0": "CC-BY-ND-3.0", + "cc-by-nd-3.0.0-de": "CC-BY-ND-3.0-DE", + "cc-by-nd-4": "CC-BY-ND-4.0", + "cc-by-nd-4.0": "CC-BY-ND-4.0", + "cc-by-nd-4.0.0": "CC-BY-ND-4.0", + "cc-by-sa-1": "CC-BY-SA-1.0", + "cc-by-sa-1.0": "CC-BY-SA-1.0", + "cc-by-sa-1.0.0": "CC-BY-SA-1.0", + "cc-by-sa-2": "CC-BY-SA-2.0", + "cc-by-sa-2-jp": "CC-BY-SA-2.1-JP", + "cc-by-sa-2-uk": "CC-BY-SA-2.0-UK", + "cc-by-sa-2.0": "CC-BY-SA-2.0", + "cc-by-sa-2.0-uk": "CC-BY-SA-2.0-UK", + "cc-by-sa-2.0.0": "CC-BY-SA-2.0", + "cc-by-sa-2.0.0-uk": "CC-BY-SA-2.0-UK", + "cc-by-sa-2.1-jp": "CC-BY-SA-2.1-JP", + "cc-by-sa-2.1.0-jp": "CC-BY-SA-2.1-JP", + "cc-by-sa-2.5": "CC-BY-SA-2.5", + "cc-by-sa-2.5.0": "CC-BY-SA-2.5", + "cc-by-sa-3": "CC-BY-SA-3.0", + "cc-by-sa-3-at": "CC-BY-SA-3.0-AT", + "cc-by-sa-3-de": "CC-BY-SA-3.0-DE", + "cc-by-sa-3.0": "CC-BY-SA-3.0", + "cc-by-sa-3.0-at": "CC-BY-SA-3.0-AT", + "cc-by-sa-3.0-de": "CC-BY-SA-3.0-DE", + "cc-by-sa-3.0.0": "CC-BY-SA-3.0", + "cc-by-sa-3.0.0-at": "CC-BY-SA-3.0-AT", + "cc-by-sa-3.0.0-de": "CC-BY-SA-3.0-DE", + "cc-by-sa-4": "CC-BY-SA-4.0", + "cc-by-sa-4.0": "CC-BY-SA-4.0", + "cc-by-sa-4.0.0": "CC-BY-SA-4.0", + "cc-pddc": "CC-PDDC", + "cc0-1": "CC0-1.0", + "cc0-1.0": "CC0-1.0", + "cc0-1.0.0": "CC0-1.0", + "cddl-1": "CDDL-1.0", + "cddl-1.0": "CDDL-1.0", + "cddl-1.0.0": "CDDL-1.0", + "cddl-1.1": "CDDL-1.1", + "cddl-1.1.0": "CDDL-1.1", + "cdl-1": "CDL-1.0", + "cdl-1.0": "CDL-1.0", + "cdl-1.0.0": "CDL-1.0", + "cdla-permissive-1": "CDLA-Permissive-1.0", + "cdla-permissive-1.0": "CDLA-Permissive-1.0", + "cdla-permissive-1.0.0": "CDLA-Permissive-1.0", + "cdla-permissive-2": "CDLA-Permissive-2.0", + "cdla-permissive-2.0": "CDLA-Permissive-2.0", + "cdla-permissive-2.0.0": "CDLA-Permissive-2.0", + "cdla-sharing-1": "CDLA-Sharing-1.0", + "cdla-sharing-1.0": "CDLA-Sharing-1.0", + "cdla-sharing-1.0.0": "CDLA-Sharing-1.0", + "cecill-1": "CECILL-1.0", + "cecill-1.0": "CECILL-1.0", + "cecill-1.0.0": "CECILL-1.0", + "cecill-1.1": "CECILL-1.1", + "cecill-1.1.0": "CECILL-1.1", + "cecill-2": "CECILL-2.0", + "cecill-2.0": "CECILL-2.0", + "cecill-2.0.0": "CECILL-2.0", + "cecill-2.1": "CECILL-2.1", + "cecill-2.1.0": "CECILL-2.1", + "cecill-b": "CECILL-B", + "cecill-c": "CECILL-C", + "cern-ohl-1": "CERN-OHL-1.1", + "cern-ohl-1.1": "CERN-OHL-1.1", + "cern-ohl-1.1.0": "CERN-OHL-1.1", + "cern-ohl-1.2": "CERN-OHL-1.2", + "cern-ohl-1.2.0": "CERN-OHL-1.2", + "cern-ohl-p-2": "CERN-OHL-P-2.0", + "cern-ohl-p-2.0": "CERN-OHL-P-2.0", + "cern-ohl-p-2.0.0": "CERN-OHL-P-2.0", + "cern-ohl-s-2": "CERN-OHL-S-2.0", + "cern-ohl-s-2.0": "CERN-OHL-S-2.0", + "cern-ohl-s-2.0.0": "CERN-OHL-S-2.0", + "cern-ohl-w-2": "CERN-OHL-W-2.0", + "cern-ohl-w-2.0": "CERN-OHL-W-2.0", + "cern-ohl-w-2.0.0": "CERN-OHL-W-2.0", + "clartistic": "ClArtistic", + "cnri-jython": "CNRI-Jython", + "cnri-python": "CNRI-Python", + "cnri-python-gpl-compatible": "CNRI-Python-GPL-Compatible", + "coil-1": "COIL-1.0", + "coil-1.0": "COIL-1.0", + "coil-1.0.0": "COIL-1.0", + "community-spec-1": "Community-Spec-1.0", + "community-spec-1.0": "Community-Spec-1.0", + "community-spec-1.0.0": "Community-Spec-1.0", + "condor-1": "Condor-1.1", + "condor-1.1": "Condor-1.1", + "condor-1.1.0": "Condor-1.1", + "copyleft-next-0.3": "copyleft-next-0.3.0", + "copyleft-next-0.3.0": "copyleft-next-0.3.0", + "copyleft-next-0.3.1": "copyleft-next-0.3.1", + "cpal-1": "CPAL-1.0", + "cpal-1.0": "CPAL-1.0", + "cpal-1.0.0": "CPAL-1.0", + "cpl-1": "CPL-1.0", + "cpl-1.0": "CPL-1.0", + "cpl-1.0.0": "CPL-1.0", + "cpol-1": "CPOL-1.02", + "cpol-1.02": "CPOL-1.02", + "cpol-1.02.0": "CPOL-1.02", + "crossword": "Crossword", + "crystalstacker": "CrystalStacker", + "cua-opl-1": "CUA-OPL-1.0", + "cua-opl-1.0": "CUA-OPL-1.0", + "cua-opl-1.0.0": "CUA-OPL-1.0", + "cube": "Cube", + "curl": "curl", + "d-fsl-1": "D-FSL-1.0", + "d-fsl-1.0": "D-FSL-1.0", + "d-fsl-1.0.0": "D-FSL-1.0", + "diffmark": "diffmark", + "dl-de-by-2": "DL-DE-BY-2.0", + "dl-de-by-2.0": "DL-DE-BY-2.0", + "dl-de-by-2.0.0": "DL-DE-BY-2.0", + "doc": "DOC", + "dotseqn": "Dotseqn", + "drl-1": "DRL-1.0", + "drl-1.0": "DRL-1.0", + "drl-1.0.0": "DRL-1.0", + "dsdp": "DSDP", + "dvipdfm": "dvipdfm", + "ecl-1": "ECL-1.0", + "ecl-1.0": "ECL-1.0", + "ecl-1.0.0": "ECL-1.0", + "ecl-2": "ECL-2.0", + "ecl-2.0": "ECL-2.0", + "ecl-2.0.0": "ECL-2.0", + "ecos-2": "eCos-2.0", + "ecos-2.0": "eCos-2.0", + "ecos-2.0.0": "eCos-2.0", + "efl-1": "EFL-1.0", + "efl-1.0": "EFL-1.0", + "efl-1.0.0": "EFL-1.0", + "efl-2": "EFL-2.0", + "efl-2.0": "EFL-2.0", + "efl-2.0.0": "EFL-2.0", + "egenix": "eGenix", + "elastic-2": "Elastic-2.0", + "elastic-2.0": "Elastic-2.0", + "elastic-2.0.0": "Elastic-2.0", + "entessa": "Entessa", + "epics": "EPICS", + "epl-1": "EPL-1.0", + "epl-1.0": "EPL-1.0", + "epl-1.0.0": "EPL-1.0", + "epl-2": "EPL-2.0", + "epl-2.0": "EPL-2.0", + "epl-2.0.0": "EPL-2.0", + "erlpl-1": "ErlPL-1.1", + "erlpl-1.1": "ErlPL-1.1", + "erlpl-1.1.0": "ErlPL-1.1", + "etalab-2": "etalab-2.0", + "etalab-2.0": "etalab-2.0", + "etalab-2.0.0": "etalab-2.0", + "eudatagrid": "EUDatagrid", + "eupl-1": "EUPL-1.0", + "eupl-1.0": "EUPL-1.0", + "eupl-1.0.0": "EUPL-1.0", + "eupl-1.1": "EUPL-1.1", + "eupl-1.1.0": "EUPL-1.1", + "eupl-1.2": "EUPL-1.2", + "eupl-1.2.0": "EUPL-1.2", + "eurosym": "Eurosym", + "fair": "Fair", + "fdk-aac": "FDK-AAC", + "frameworx-1": "Frameworx-1.0", + "frameworx-1.0": "Frameworx-1.0", + "frameworx-1.0.0": "Frameworx-1.0", + "freebsd-doc": "FreeBSD-DOC", + "freeimage": "FreeImage", + "fsfap": "FSFAP", + "fsful": "FSFUL", + "fsfullr": "FSFULLR", + "ftl": "FTL", + "gd": "GD", + "gfdl-1": "GFDL-1.1", + "gfdl-1-invariants-only": "GFDL-1.1-invariants-only", + "gfdl-1-invariants-or-later": "GFDL-1.1-invariants-or-later", + "gfdl-1-no-invariants-only": "GFDL-1.1-no-invariants-only", + "gfdl-1-no-invariants-or-later": "GFDL-1.1-no-invariants-or-later", + "gfdl-1-only": "GFDL-1.1-only", + "gfdl-1-or-later": "GFDL-1.1-or-later", + "gfdl-1.1": "GFDL-1.1", + "gfdl-1.1-invariants-only": "GFDL-1.1-invariants-only", + "gfdl-1.1-invariants-or-later": "GFDL-1.1-invariants-or-later", + "gfdl-1.1-no-invariants-only": "GFDL-1.1-no-invariants-only", + "gfdl-1.1-no-invariants-or-later": "GFDL-1.1-no-invariants-or-later", + "gfdl-1.1-only": "GFDL-1.1-only", + "gfdl-1.1-or-later": "GFDL-1.1-or-later", + "gfdl-1.1.0": "GFDL-1.1", + "gfdl-1.1.0-invariants-only": "GFDL-1.1-invariants-only", + "gfdl-1.1.0-invariants-or-later": "GFDL-1.1-invariants-or-later", + "gfdl-1.1.0-no-invariants-only": "GFDL-1.1-no-invariants-only", + "gfdl-1.1.0-no-invariants-or-later": "GFDL-1.1-no-invariants-or-later", + "gfdl-1.1.0-only": "GFDL-1.1-only", + "gfdl-1.1.0-or-later": "GFDL-1.1-or-later", + "gfdl-1.2": "GFDL-1.2", + "gfdl-1.2-invariants-only": "GFDL-1.2-invariants-only", + "gfdl-1.2-invariants-or-later": "GFDL-1.2-invariants-or-later", + "gfdl-1.2-no-invariants-only": "GFDL-1.2-no-invariants-only", + "gfdl-1.2-no-invariants-or-later": "GFDL-1.2-no-invariants-or-later", + "gfdl-1.2-only": "GFDL-1.2-only", + "gfdl-1.2-or-later": "GFDL-1.2-or-later", + "gfdl-1.2.0": "GFDL-1.2", + "gfdl-1.2.0-invariants-only": "GFDL-1.2-invariants-only", + "gfdl-1.2.0-invariants-or-later": "GFDL-1.2-invariants-or-later", + "gfdl-1.2.0-no-invariants-only": "GFDL-1.2-no-invariants-only", + "gfdl-1.2.0-no-invariants-or-later": "GFDL-1.2-no-invariants-or-later", + "gfdl-1.2.0-only": "GFDL-1.2-only", + "gfdl-1.2.0-or-later": "GFDL-1.2-or-later", + "gfdl-1.3": "GFDL-1.3", + "gfdl-1.3-invariants-only": "GFDL-1.3-invariants-only", + "gfdl-1.3-invariants-or-later": "GFDL-1.3-invariants-or-later", + "gfdl-1.3-no-invariants-only": "GFDL-1.3-no-invariants-only", + "gfdl-1.3-no-invariants-or-later": "GFDL-1.3-no-invariants-or-later", + "gfdl-1.3-only": "GFDL-1.3-only", + "gfdl-1.3-or-later": "GFDL-1.3-or-later", + "gfdl-1.3.0": "GFDL-1.3", + "gfdl-1.3.0-invariants-only": "GFDL-1.3-invariants-only", + "gfdl-1.3.0-invariants-or-later": "GFDL-1.3-invariants-or-later", + "gfdl-1.3.0-no-invariants-only": "GFDL-1.3-no-invariants-only", + "gfdl-1.3.0-no-invariants-or-later": "GFDL-1.3-no-invariants-or-later", + "gfdl-1.3.0-only": "GFDL-1.3-only", + "gfdl-1.3.0-or-later": "GFDL-1.3-or-later", + "giftware": "Giftware", + "gl2ps": "GL2PS", + "glide": "Glide", + "glulxe": "Glulxe", + "glwtpl": "GLWTPL", + "gnuplot": "gnuplot", + "gpl-1": "GPL-1.0-only", + "gpl-1+": "GPL-1.0-or-later", + "gpl-1-only": "GPL-1.0-only", + "gpl-1-or-later": "GPL-1.0-or-later", + "gpl-1.0": "GPL-1.0-only", + "gpl-1.0+": "GPL-1.0-or-later", + "gpl-1.0-only": "GPL-1.0-only", + "gpl-1.0-or-later": "GPL-1.0-or-later", + "gpl-1.0.0": "GPL-1.0-only", + "gpl-1.0.0+": "GPL-1.0-or-later", + "gpl-1.0.0-only": "GPL-1.0-only", + "gpl-1.0.0-or-later": "GPL-1.0-or-later", + "gpl-2": "GPL-2.0-only", + "gpl-2+": "GPL-2.0-or-later", + "gpl-2-only": "GPL-2.0-only", + "gpl-2-or-later": "GPL-2.0-or-later", + "gpl-2-with-autoconf-exception": "GPL-2.0-with-autoconf-exception", + "gpl-2-with-bison-exception": "GPL-2.0-with-bison-exception", + "gpl-2-with-classpath-exception": "GPL-2.0-with-classpath-exception", + "gpl-2-with-font-exception": "GPL-2.0-with-font-exception", + "gpl-2-with-gcc-exception": "GPL-2.0-with-GCC-exception", + "gpl-2.0": "GPL-2.0-only", + "gpl-2.0+": "GPL-2.0-or-later", + "gpl-2.0-only": "GPL-2.0-only", + "gpl-2.0-or-later": "GPL-2.0-or-later", + "gpl-2.0-with-autoconf-exception": "GPL-2.0-with-autoconf-exception", + "gpl-2.0-with-bison-exception": "GPL-2.0-with-bison-exception", + "gpl-2.0-with-classpath-exception": "GPL-2.0-with-classpath-exception", + "gpl-2.0-with-font-exception": "GPL-2.0-with-font-exception", + "gpl-2.0-with-gcc-exception": "GPL-2.0-with-GCC-exception", + "gpl-2.0.0": "GPL-2.0-only", + "gpl-2.0.0+": "GPL-2.0-or-later", + "gpl-2.0.0-only": "GPL-2.0-only", + "gpl-2.0.0-or-later": "GPL-2.0-or-later", + "gpl-2.0.0-with-autoconf-exception": "GPL-2.0-with-autoconf-exception", + "gpl-2.0.0-with-bison-exception": "GPL-2.0-with-bison-exception", + "gpl-2.0.0-with-classpath-exception": "GPL-2.0-with-classpath-exception", + "gpl-2.0.0-with-font-exception": "GPL-2.0-with-font-exception", + "gpl-2.0.0-with-gcc-exception": "GPL-2.0-with-GCC-exception", + "gpl-3": "GPL-3.0-only", + "gpl-3+": "GPL-3.0-or-later", + "gpl-3-only": "GPL-3.0-only", + "gpl-3-or-later": "GPL-3.0-or-later", + "gpl-3-with-autoconf-exception": "GPL-3.0-with-autoconf-exception", + "gpl-3-with-gcc-exception": "GPL-3.0-with-GCC-exception", + "gpl-3.0": "GPL-3.0-only", + "gpl-3.0+": "GPL-3.0-or-later", + "gpl-3.0-only": "GPL-3.0-only", + "gpl-3.0-or-later": "GPL-3.0-or-later", + "gpl-3.0-with-autoconf-exception": "GPL-3.0-with-autoconf-exception", + "gpl-3.0-with-gcc-exception": "GPL-3.0-with-GCC-exception", + "gpl-3.0.0": "GPL-3.0-only", + "gpl-3.0.0+": "GPL-3.0-or-later", + "gpl-3.0.0-only": "GPL-3.0-only", + "gpl-3.0.0-or-later": "GPL-3.0-or-later", + "gpl-3.0.0-with-autoconf-exception": "GPL-3.0-with-autoconf-exception", + "gpl-3.0.0-with-gcc-exception": "GPL-3.0-with-GCC-exception", + "gsoap-1.3.0b": "gSOAP-1.3b", + "gsoap-1.3b": "gSOAP-1.3b", + "gsoap-1b": "gSOAP-1.3b", + "haskellreport": "HaskellReport", + "hippocratic-2": "Hippocratic-2.1", + "hippocratic-2.1": "Hippocratic-2.1", + "hippocratic-2.1.0": "Hippocratic-2.1", + "hpnd": "HPND", + "hpnd-sell-variant": "HPND-sell-variant", + "htmltidy": "HTMLTIDY", + "ibm-pibs": "IBM-pibs", + "icu": "ICU", + "ijg": "IJG", + "imagemagick": "ImageMagick", + "imatix": "iMatix", + "imlib2": "Imlib2", + "info-zip": "Info-ZIP", + "intel": "Intel", + "intel-acpi": "Intel-ACPI", + "interbase-1": "Interbase-1.0", + "interbase-1.0": "Interbase-1.0", + "interbase-1.0.0": "Interbase-1.0", + "ipa": "IPA", + "ipl-1": "IPL-1.0", + "ipl-1.0": "IPL-1.0", + "ipl-1.0.0": "IPL-1.0", + "isc": "ISC", + "jam": "Jam", + "jasper-2": "JasPer-2.0", + "jasper-2.0": "JasPer-2.0", + "jasper-2.0.0": "JasPer-2.0", + "jpnic": "JPNIC", + "json": "JSON", + "kicad-libraries-exception": "KiCad-libraries-exception", + "lal-1": "LAL-1.2", + "lal-1.2": "LAL-1.2", + "lal-1.2.0": "LAL-1.2", + "lal-1.3": "LAL-1.3", + "lal-1.3.0": "LAL-1.3", + "latex2e": "Latex2e", + "leptonica": "Leptonica", + "lgpl-2": "LGPL-2.0-only", // This is an important line in testing! lgpl-2.1 would typically override this. + "lgpl-2+": "LGPL-2.0-or-later", + "lgpl-2-only": "LGPL-2.0-only", + "lgpl-2-or-later": "LGPL-2.0-or-later", + "lgpl-2.0": "LGPL-2.0-only", + "lgpl-2.0+": "LGPL-2.0-or-later", + "lgpl-2.0-only": "LGPL-2.0-only", + "lgpl-2.0-or-later": "LGPL-2.0-or-later", + "lgpl-2.0.0": "LGPL-2.0-only", + "lgpl-2.0.0+": "LGPL-2.0-or-later", + "lgpl-2.0.0-only": "LGPL-2.0-only", + "lgpl-2.0.0-or-later": "LGPL-2.0-or-later", + "lgpl-2.1": "LGPL-2.1-only", + "lgpl-2.1+": "LGPL-2.1+", + "lgpl-2.1-only": "LGPL-2.1-only", + "lgpl-2.1-or-later": "LGPL-2.1-or-later", + "lgpl-2.1.0": "LGPL-2.1-only", + "lgpl-2.1.0+": "LGPL-2.1+", + "lgpl-2.1.0-only": "LGPL-2.1-only", + "lgpl-2.1.0-or-later": "LGPL-2.1-or-later", + "lgpl-3": "LGPL-3.0-only", + "lgpl-3+": "LGPL-3.0-or-later", + "lgpl-3-only": "LGPL-3.0-only", + "lgpl-3-or-later": "LGPL-3.0-or-later", + "lgpl-3.0": "LGPL-3.0-only", + "lgpl-3.0+": "LGPL-3.0-or-later", + "lgpl-3.0-only": "LGPL-3.0-only", + "lgpl-3.0-or-later": "LGPL-3.0-or-later", + "lgpl-3.0.0": "LGPL-3.0-only", + "lgpl-3.0.0+": "LGPL-3.0-or-later", + "lgpl-3.0.0-only": "LGPL-3.0-only", + "lgpl-3.0.0-or-later": "LGPL-3.0-or-later", + "lgpllr": "LGPLLR", + "libpng": "Libpng", + "libpng-2": "libpng-2.0", + "libpng-2.0": "libpng-2.0", + "libpng-2.0.0": "libpng-2.0", + "libselinux-1": "libselinux-1.0", + "libselinux-1.0": "libselinux-1.0", + "libselinux-1.0.0": "libselinux-1.0", + "libtiff": "libtiff", + "liliq-p-1": "LiLiQ-P-1.1", + "liliq-p-1.1": "LiLiQ-P-1.1", + "liliq-p-1.1.0": "LiLiQ-P-1.1", + "liliq-r-1": "LiLiQ-R-1.1", + "liliq-r-1.1": "LiLiQ-R-1.1", + "liliq-r-1.1.0": "LiLiQ-R-1.1", + "liliq-rplus-1": "LiLiQ-Rplus-1.1", + "liliq-rplus-1.1": "LiLiQ-Rplus-1.1", + "liliq-rplus-1.1.0": "LiLiQ-Rplus-1.1", + "linux-man-pages-copyleft": "Linux-man-pages-copyleft", + "linux-openib": "Linux-OpenIB", + "lpl-1": "LPL-1.0", + "lpl-1.0": "LPL-1.0", + "lpl-1.0.0": "LPL-1.0", + "lpl-1.02": "LPL-1.02", + "lpl-1.02.0": "LPL-1.02", + "lppl-1": "LPPL-1.0", + "lppl-1.0": "LPPL-1.0", + "lppl-1.0.0": "LPPL-1.0", + "lppl-1.1": "LPPL-1.1", + "lppl-1.1.0": "LPPL-1.1", + "lppl-1.2": "LPPL-1.2", + "lppl-1.2.0": "LPPL-1.2", + "lppl-1.3.0a": "LPPL-1.3a", + "lppl-1.3.0c": "LPPL-1.3c", + "lppl-1.3a": "LPPL-1.3a", + "lppl-1.3c": "LPPL-1.3c", + "lppl-1a": "LPPL-1.3a", + "lppl-1c": "LPPL-1.3c", + "makeindex": "MakeIndex", + "miros": "MirOS", + "mit": "MIT", + "mit-0": "MIT-0", + "mit-advertising": "MIT-advertising", + "mit-cmu": "MIT-CMU", + "mit-enna": "MIT-enna", + "mit-feh": "MIT-feh", + "mit-modern-variant": "MIT-Modern-Variant", + "mit-open-group": "MIT-open-group", + "mitnfa": "MITNFA", + "motosoto": "Motosoto", + "mpich2": "mpich2", + "mpl-1": "MPL-1.0", + "mpl-1.0": "MPL-1.0", + "mpl-1.0.0": "MPL-1.0", + "mpl-1.1": "MPL-1.1", + "mpl-1.1.0": "MPL-1.1", + "mpl-2": "MPL-2.0", + "mpl-2-no-copyleft-exception": "MPL-2.0-no-copyleft-exception", + "mpl-2.0": "MPL-2.0", + "mpl-2.0-no-copyleft-exception": "MPL-2.0-no-copyleft-exception", + "mpl-2.0.0": "MPL-2.0", + "mpl-2.0.0-no-copyleft-exception": "MPL-2.0-no-copyleft-exception", + "mplus": "mplus", + "ms-pl": "MS-PL", + "ms-rl": "MS-RL", + "mtll": "MTLL", + "mulanpsl-1": "MulanPSL-1.0", + "mulanpsl-1.0": "MulanPSL-1.0", + "mulanpsl-1.0.0": "MulanPSL-1.0", + "mulanpsl-2": "MulanPSL-2.0", + "mulanpsl-2.0": "MulanPSL-2.0", + "mulanpsl-2.0.0": "MulanPSL-2.0", + "multics": "Multics", + "mup": "Mup", + "naist-2003": "NAIST-2003", + "naist-2003.0": "NAIST-2003", + "naist-2003.0.0": "NAIST-2003", + "nasa-1": "NASA-1.3", + "nasa-1.3": "NASA-1.3", + "nasa-1.3.0": "NASA-1.3", + "naumen": "Naumen", + "nbpl-1": "NBPL-1.0", + "nbpl-1.0": "NBPL-1.0", + "nbpl-1.0.0": "NBPL-1.0", + "ncgl-uk-2": "NCGL-UK-2.0", + "ncgl-uk-2.0": "NCGL-UK-2.0", + "ncgl-uk-2.0.0": "NCGL-UK-2.0", + "ncsa": "NCSA", + "net-snmp": "Net-SNMP", + "netcdf": "NetCDF", + "newsletr": "Newsletr", + "ngpl": "NGPL", + "nist-pd": "NIST-PD", + "nist-pd-fallback": "NIST-PD-fallback", + "nlod-1": "NLOD-1.0", + "nlod-1.0": "NLOD-1.0", + "nlod-1.0.0": "NLOD-1.0", + "nlod-2": "NLOD-2.0", + "nlod-2.0": "NLOD-2.0", + "nlod-2.0.0": "NLOD-2.0", + "nlpl": "NLPL", + "nokia": "Nokia", + "nosl": "NOSL", + "noweb": "Noweb", + "npl-1": "NPL-1.0", + "npl-1.0": "NPL-1.0", + "npl-1.0.0": "NPL-1.0", + "npl-1.1": "NPL-1.1", + "npl-1.1.0": "NPL-1.1", + "nposl-3": "NPOSL-3.0", + "nposl-3.0": "NPOSL-3.0", + "nposl-3.0.0": "NPOSL-3.0", + "nrl": "NRL", + "ntp": "NTP", + "ntp-0": "NTP-0", + "nunit": "Nunit", + "o-uda-1": "O-UDA-1.0", + "o-uda-1.0": "O-UDA-1.0", + "o-uda-1.0.0": "O-UDA-1.0", + "occt-pl": "OCCT-PL", + "oclc-2": "OCLC-2.0", + "oclc-2.0": "OCLC-2.0", + "oclc-2.0.0": "OCLC-2.0", + "odbl-1": "ODbL-1.0", + "odbl-1.0": "ODbL-1.0", + "odbl-1.0.0": "ODbL-1.0", + "odc-by-1": "ODC-By-1.0", + "odc-by-1.0": "ODC-By-1.0", + "odc-by-1.0.0": "ODC-By-1.0", + "ofl-1": "OFL-1.0", + "ofl-1-no-rfn": "OFL-1.0-no-RFN", + "ofl-1-rfn": "OFL-1.0-RFN", + "ofl-1.0": "OFL-1.0", + "ofl-1.0-no-rfn": "OFL-1.0-no-RFN", + "ofl-1.0-rfn": "OFL-1.0-RFN", + "ofl-1.0.0": "OFL-1.0", + "ofl-1.0.0-no-rfn": "OFL-1.0-no-RFN", + "ofl-1.0.0-rfn": "OFL-1.0-RFN", + "ofl-1.1": "OFL-1.1", + "ofl-1.1-no-rfn": "OFL-1.1-no-RFN", + "ofl-1.1-rfn": "OFL-1.1-RFN", + "ofl-1.1.0": "OFL-1.1", + "ofl-1.1.0-no-rfn": "OFL-1.1-no-RFN", + "ofl-1.1.0-rfn": "OFL-1.1-RFN", + "ogc-1": "OGC-1.0", + "ogc-1.0": "OGC-1.0", + "ogc-1.0.0": "OGC-1.0", + "ogdl-taiwan-1": "OGDL-Taiwan-1.0", + "ogdl-taiwan-1.0": "OGDL-Taiwan-1.0", + "ogdl-taiwan-1.0.0": "OGDL-Taiwan-1.0", + "ogl-canada-2": "OGL-Canada-2.0", + "ogl-canada-2.0": "OGL-Canada-2.0", + "ogl-canada-2.0.0": "OGL-Canada-2.0", + "ogl-uk-1": "OGL-UK-1.0", + "ogl-uk-1.0": "OGL-UK-1.0", + "ogl-uk-1.0.0": "OGL-UK-1.0", + "ogl-uk-2": "OGL-UK-2.0", + "ogl-uk-2.0": "OGL-UK-2.0", + "ogl-uk-2.0.0": "OGL-UK-2.0", + "ogl-uk-3": "OGL-UK-3.0", + "ogl-uk-3.0": "OGL-UK-3.0", + "ogl-uk-3.0.0": "OGL-UK-3.0", + "ogtsl": "OGTSL", + "oldap-1": "OLDAP-1.1", + "oldap-1.1": "OLDAP-1.1", + "oldap-1.1.0": "OLDAP-1.1", + "oldap-1.2": "OLDAP-1.2", + "oldap-1.2.0": "OLDAP-1.2", + "oldap-1.3": "OLDAP-1.3", + "oldap-1.3.0": "OLDAP-1.3", + "oldap-1.4": "OLDAP-1.4", + "oldap-1.4.0": "OLDAP-1.4", + "oldap-2": "OLDAP-2.0", + "oldap-2.0": "OLDAP-2.0", + "oldap-2.0.0": "OLDAP-2.0", + "oldap-2.0.1": "OLDAP-2.0.1", + "oldap-2.1": "OLDAP-2.1", + "oldap-2.1.0": "OLDAP-2.1", + "oldap-2.2": "OLDAP-2.2", + "oldap-2.2.0": "OLDAP-2.2", + "oldap-2.2.1": "OLDAP-2.2.1", + "oldap-2.2.2": "OLDAP-2.2.2", + "oldap-2.3": "OLDAP-2.3", + "oldap-2.3.0": "OLDAP-2.3", + "oldap-2.4": "OLDAP-2.4", + "oldap-2.4.0": "OLDAP-2.4", + "oldap-2.5": "OLDAP-2.5", + "oldap-2.5.0": "OLDAP-2.5", + "oldap-2.6": "OLDAP-2.6", + "oldap-2.6.0": "OLDAP-2.6", + "oldap-2.7": "OLDAP-2.7", + "oldap-2.7.0": "OLDAP-2.7", + "oldap-2.8": "OLDAP-2.8", + "oldap-2.8.0": "OLDAP-2.8", + "oml": "OML", + "openssl": "OpenSSL", + "opl-1": "OPL-1.0", + "opl-1.0": "OPL-1.0", + "opl-1.0.0": "OPL-1.0", + "opubl-1": "OPUBL-1.0", + "opubl-1.0": "OPUBL-1.0", + "opubl-1.0.0": "OPUBL-1.0", + "oset-pl-2": "OSET-PL-2.1", + "oset-pl-2.1": "OSET-PL-2.1", + "oset-pl-2.1.0": "OSET-PL-2.1", + "osl-1": "OSL-1.0", + "osl-1.0": "OSL-1.0", + "osl-1.0.0": "OSL-1.0", + "osl-1.1": "OSL-1.1", + "osl-1.1.0": "OSL-1.1", + "osl-2": "OSL-2.0", + "osl-2.0": "OSL-2.0", + "osl-2.0.0": "OSL-2.0", + "osl-2.1": "OSL-2.1", + "osl-2.1.0": "OSL-2.1", + "osl-3": "OSL-3.0", + "osl-3.0": "OSL-3.0", + "osl-3.0.0": "OSL-3.0", + "parity-6": "Parity-6.0.0", + "parity-6.0": "Parity-6.0.0", + "parity-6.0.0": "Parity-6.0.0", + "parity-7": "Parity-7.0.0", + "parity-7.0": "Parity-7.0.0", + "parity-7.0.0": "Parity-7.0.0", + "pddl-1": "PDDL-1.0", + "pddl-1.0": "PDDL-1.0", + "pddl-1.0.0": "PDDL-1.0", + "php-3": "PHP-3.0", + "php-3.0": "PHP-3.0", + "php-3.0.0": "PHP-3.0", + "php-3.01": "PHP-3.01", + "php-3.01.0": "PHP-3.01", + "plexus": "Plexus", + "polyform-noncommercial-1": "PolyForm-Noncommercial-1.0.0", + "polyform-noncommercial-1.0": "PolyForm-Noncommercial-1.0.0", + "polyform-noncommercial-1.0.0": "PolyForm-Noncommercial-1.0.0", + "polyform-small-business-1": "PolyForm-Small-Business-1.0.0", + "polyform-small-business-1.0": "PolyForm-Small-Business-1.0.0", + "polyform-small-business-1.0.0": "PolyForm-Small-Business-1.0.0", + "postgresql": "PostgreSQL", + "psf-2": "PSF-2.0", + "psf-2.0": "PSF-2.0", + "psf-2.0.0": "PSF-2.0", + "psfrag": "psfrag", + "psutils": "psutils", + "python-2": "Python-2.0", + "python-2.0": "Python-2.0", + "python-2.0.0": "Python-2.0", + "qhull": "Qhull", + "qpl-1": "QPL-1.0", + "qpl-1.0": "QPL-1.0", + "qpl-1.0.0": "QPL-1.0", + "rdisc": "Rdisc", + "rhecos-1": "RHeCos-1.1", + "rhecos-1.1": "RHeCos-1.1", + "rhecos-1.1.0": "RHeCos-1.1", + "rpl-1": "RPL-1.1", + "rpl-1.1": "RPL-1.1", + "rpl-1.1.0": "RPL-1.1", + "rpl-1.5": "RPL-1.5", + "rpl-1.5.0": "RPL-1.5", + "rpsl-1": "RPSL-1.0", + "rpsl-1.0": "RPSL-1.0", + "rpsl-1.0.0": "RPSL-1.0", + "rsa-md": "RSA-MD", + "rscpl": "RSCPL", + "ruby": "Ruby", + "sax-pd": "SAX-PD", + "saxpath": "Saxpath", + "scea": "SCEA", + "schemereport": "SchemeReport", + "sendmail": "Sendmail", + "sendmail-8": "Sendmail-8.23", + "sendmail-8.23": "Sendmail-8.23", + "sendmail-8.23.0": "Sendmail-8.23", + "sgi-b-1": "SGI-B-1.0", + "sgi-b-1.0": "SGI-B-1.0", + "sgi-b-1.0.0": "SGI-B-1.0", + "sgi-b-1.1": "SGI-B-1.1", + "sgi-b-1.1.0": "SGI-B-1.1", + "sgi-b-2": "SGI-B-2.0", + "sgi-b-2.0": "SGI-B-2.0", + "sgi-b-2.0.0": "SGI-B-2.0", + "shl-0.5": "SHL-0.5", + "shl-0.5.0": "SHL-0.5", + "shl-0.51": "SHL-0.51", + "shl-0.51.0": "SHL-0.51", + "simpl-2": "SimPL-2.0", + "simpl-2.0": "SimPL-2.0", + "simpl-2.0.0": "SimPL-2.0", + "sissl": "SISSL", + "sissl-1": "SISSL-1.2", + "sissl-1.2": "SISSL-1.2", + "sissl-1.2.0": "SISSL-1.2", + "sleepycat": "Sleepycat", + "smlnj": "SMLNJ", + "smppl": "SMPPL", + "snia": "SNIA", + "spencer-86": "Spencer-86", + "spencer-86.0": "Spencer-86", + "spencer-86.0.0": "Spencer-86", + "spencer-94": "Spencer-94", + "spencer-94.0": "Spencer-94", + "spencer-94.0.0": "Spencer-94", + "spencer-99": "Spencer-99", + "spencer-99.0": "Spencer-99", + "spencer-99.0.0": "Spencer-99", + "spl-1": "SPL-1.0", + "spl-1.0": "SPL-1.0", + "spl-1.0.0": "SPL-1.0", + "ssh-openssh": "SSH-OpenSSH", + "ssh-short": "SSH-short", + "sspl-1": "SSPL-1.0", + "sspl-1.0": "SSPL-1.0", + "sspl-1.0.0": "SSPL-1.0", + "standardml-nj": "StandardML-NJ", + "sugarcrm-1": "SugarCRM-1.1.3", + "sugarcrm-1.1": "SugarCRM-1.1.3", + "sugarcrm-1.1.3": "SugarCRM-1.1.3", + "swl": "SWL", + "tapr-ohl-1": "TAPR-OHL-1.0", + "tapr-ohl-1.0": "TAPR-OHL-1.0", + "tapr-ohl-1.0.0": "TAPR-OHL-1.0", + "tcl": "TCL", + "tcp-wrappers": "TCP-wrappers", + "tmate": "TMate", + "torque-1": "TORQUE-1.1", + "torque-1.1": "TORQUE-1.1", + "torque-1.1.0": "TORQUE-1.1", + "tosl": "TOSL", + "tu-berlin-1": "TU-Berlin-1.0", + "tu-berlin-1.0": "TU-Berlin-1.0", + "tu-berlin-1.0.0": "TU-Berlin-1.0", + "tu-berlin-2": "TU-Berlin-2.0", + "tu-berlin-2.0": "TU-Berlin-2.0", + "tu-berlin-2.0.0": "TU-Berlin-2.0", + "ucl-1": "UCL-1.0", + "ucl-1.0": "UCL-1.0", + "ucl-1.0.0": "UCL-1.0", + "unicode-dfs-2015": "Unicode-DFS-2015", + "unicode-dfs-2015.0": "Unicode-DFS-2015", + "unicode-dfs-2015.0.0": "Unicode-DFS-2015", + "unicode-dfs-2016": "Unicode-DFS-2016", + "unicode-dfs-2016.0": "Unicode-DFS-2016", + "unicode-dfs-2016.0.0": "Unicode-DFS-2016", + "unicode-tou": "Unicode-TOU", + "unlicense": "Unlicense", + "upl-1": "UPL-1.0", + "upl-1.0": "UPL-1.0", + "upl-1.0.0": "UPL-1.0", + "vim": "Vim", + "vostrom": "VOSTROM", + "vsl-1": "VSL-1.0", + "vsl-1.0": "VSL-1.0", + "vsl-1.0.0": "VSL-1.0", + "w3c": "W3C", + "w3c-19980720": "W3C-19980720", + "w3c-19980720.0": "W3C-19980720", + "w3c-19980720.0.0": "W3C-19980720", + "w3c-20150513": "W3C-20150513", + "w3c-20150513.0": "W3C-20150513", + "w3c-20150513.0.0": "W3C-20150513", + "watcom-1": "Watcom-1.0", + "watcom-1.0": "Watcom-1.0", + "watcom-1.0.0": "Watcom-1.0", + "wsuipa": "Wsuipa", + "wtfpl": "WTFPL", + "wxwindows": "wxWindows", + "x11": "X11", + "x11-distribute-modifications-variant": "X11-distribute-modifications-variant", + "xerox": "Xerox", + "xfree86-1": "XFree86-1.1", + "xfree86-1.1": "XFree86-1.1", + "xfree86-1.1.0": "XFree86-1.1", + "xinetd": "xinetd", + "xnet": "Xnet", + "xpp": "xpp", + "xskat": "XSkat", + "ypl-1": "YPL-1.0", + "ypl-1.0": "YPL-1.0", + "ypl-1.0.0": "YPL-1.0", + "ypl-1.1": "YPL-1.1", + "ypl-1.1.0": "YPL-1.1", + "zed": "Zed", + "zend-2": "Zend-2.0", + "zend-2.0": "Zend-2.0", + "zend-2.0.0": "Zend-2.0", + "zimbra-1": "Zimbra-1.3", + "zimbra-1.3": "Zimbra-1.3", + "zimbra-1.3.0": "Zimbra-1.3", + "zimbra-1.4": "Zimbra-1.4", + "zimbra-1.4.0": "Zimbra-1.4", + "zlib": "Zlib", + "zlib-acknowledgement": "zlib-acknowledgement", + "zpl-1": "ZPL-1.1", + "zpl-1.1": "ZPL-1.1", + "zpl-1.1.0": "ZPL-1.1", + "zpl-2": "ZPL-2.0", + "zpl-2.0": "ZPL-2.0", + "zpl-2.0.0": "ZPL-2.0", + "zpl-2.1": "ZPL-2.1", + "zpl-2.1.0": "ZPL-2.1", + }, + }, + } + for _, tt := range tests { + t.Run(tt.fixture, func(t *testing.T) { + f, err := os.Open(tt.fixture) + require.NoError(t, err) + + var list LicenseList + require.NoError(t, json.NewDecoder(f).Decode(&list)) + + d := cmp.Diff(tt.want, processSPDXLicense(list)) + if d != "" { + t.Log("differing license list:\n" + d) + t.Fail() + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/license.go b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/license.go new file mode 100644 index 0000000000000000000000000000000000000000..196b77bcecd728dfae5f19b3b6209270eba8cca7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/license.go @@ -0,0 +1,104 @@ +package main + +import ( + "strings" + + "github.com/scylladb/go-set/strset" +) + +type LicenseList struct { + Version string `json:"licenseListVersion"` + Licenses []License `json:"licenses"` +} + +type License struct { + ID string `json:"licenseId"` + Name string `json:"name"` + Text string `json:"licenseText"` + Deprecated bool `json:"isDeprecatedLicenseId"` + OSIApproved bool `json:"isOsiApproved"` + SeeAlso []string `json:"seeAlso"` +} + +func (l License) canReplace(other License) bool { + if l.Deprecated { + return false + } + + if l.Name != other.Name { + return false + } + + if l.OSIApproved != other.OSIApproved { + return false + } + + if len(l.SeeAlso) != len(other.SeeAlso) { + return false + } + + for i, sa := range l.SeeAlso { + if sa != other.SeeAlso[i] { + return false + } + } + + return l.ID != other.ID +} + +func (ll LicenseList) findReplacementLicense(deprecated License) *License { + for _, l := range ll.Licenses { + if l.canReplace(deprecated) { + return &l + } + } + + return nil +} + +func buildLicensePermutations(license string) (perms []string) { + lv := findLicenseVersion(license) + vp := versionPermutations(lv) + + version := strings.Join(lv, ".") + for _, p := range vp { + perms = append(perms, strings.Replace(license, version, p, 1)) + } + + return perms +} + +func findLicenseVersion(license string) (version []string) { + versionList := versionMatch.FindAllStringSubmatch(license, -1) + + if len(versionList) == 0 { + return version + } + + for i, v := range versionList[0] { + if v != "" && i != 0 { + version = append(version, v) + } + } + + return version +} + +func versionPermutations(version []string) []string { + ver := append([]string(nil), version...) + perms := strset.New() + for i := 1; i <= 3; i++ { + if len(ver) < i+1 { + ver = append(ver, "0") + } + + perm := strings.Join(ver[:i], ".") + badCount := strings.Count(perm, "0") + strings.Count(perm, ".") + + if badCount != len(perm) { + perms.Add(perm) + } + } + + return perms.List() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/license_test.go b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/license_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4796873ec6fa162ce3be83e971fe447eb8b2bd51 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/license_test.go @@ -0,0 +1,220 @@ +package main + +import ( + "github.com/stretchr/testify/assert" + "strings" + "testing" +) + +var ( + license1 = License{ + ID: "ABC-1.0+", + Name: "The ABC License 1.0", + Deprecated: true, + } + + license2 = License{ + ID: "ABC-1.0-Or-later", + Name: "The ABC License 1.0", + } + + license3 = License{ + ID: "ABC-1.0", + Name: "The ABC License 1.0 Only", + Deprecated: true, + } + + license4 = License{ + ID: "ABC-1.0-Only", + Name: "The ABC License 1.0 Only", + } + license5 = License{ + ID: "Duh-1.0", + Name: "The Duh License 1.0", + Deprecated: true, + } + license6 = License{ + ID: "Duh-1.0-duh", + Name: "The Duh License 1.0", + Deprecated: true, + } +) + +func TestLicense_canReplace(t *testing.T) { + tests := []struct { + l1, l2 License + expected bool + }{ + {license1, license2, false}, + {license2, license1, true}, + {license2, license3, false}, + {license3, license2, false}, + } + + for _, tt := range tests { + assert.Equal(t, tt.expected, tt.l1.canReplace(tt.l2)) + } +} + +func TestLicensePermutations(t *testing.T) { + var tests = []struct { + shortName string + permutations []string + }{ + { + "GPL-1-only", + []string{ + "GPL-1-only", + "GPL-1.0-only", + "GPL-1.0.0-only", + }, + }, + { + "GPL-2", + []string{ + "GPL-2", + "GPL-2.0", + "GPL-2.0.0", + }, + }, + { + "GPL-2.0+", + []string{ + "GPL-2+", + "GPL-2.0+", + "GPL-2.0.0+", + }, + }, + { + "GPL-3.0.0-or-later", + []string{ + "GPL-3-or-later", + "GPL-3.0-or-later", + "GPL-3.0.0-or-later", + }, + }, + { + "abc-1.1", + []string{ + "abc-1", + "abc-1.1", + "abc-1.1.0", + }, + }, + { + "oldap-2.0", + []string{ + "oldap-2", + "oldap-2.0", + "oldap-2.0.0", + }, + }, + } + + for _, test := range tests { + t.Run(test.shortName, func(t *testing.T) { + perms := buildLicensePermutations(test.shortName) + assert.ElementsMatch(t, test.permutations, perms) + }) + } +} + +func TestVersionPermutations(t *testing.T) { + var tests = []struct { + version []string + permutations []string + }{ + { + []string{"1", "0"}, + []string{"1", "1.0", "1.0.0"}, + }, + { + []string{"2"}, + []string{"2", "2.0", "2.0.0"}, + }, + { + []string{"2", "0"}, + []string{"2", "2.0", "2.0.0"}, + }, + + { + []string{"3", "0", "0"}, + []string{"3", "3.0", "3.0.0"}, + }, + { + []string{"0", "3"}, + []string{"0.3", "0.3.0"}, + }, + { + []string{"0", "0", "3"}, + []string{"0.0.3"}, + }, + } + + for _, test := range tests { + t.Run(strings.Join(test.version, "."), func(t *testing.T) { + got := versionPermutations(test.version) + assert.ElementsMatch(t, test.permutations, got) + }) + } +} + +func TestFindLicenseVersion(t *testing.T) { + var tests = []struct { + license string + version []string + }{ + { + "GPL-1.0-only", + []string{"1", "0"}, + }, + { + "GPL-2.0", + []string{"2", "0"}, + }, + { + "GPL-2.0.0", + []string{"2", "0", "0"}, + }, + { + "GPL-2", + []string{"2"}, + }, + { + "bzip2-1", + []string{"1"}, + }, + { + "php-3.01", + []string{"3", "01"}, + }, + { + "oldap-2.0", + []string{"2", "0"}, + }, + } + + for _, test := range tests { + t.Run(test.license, func(t *testing.T) { + got := findLicenseVersion(test.license) + assert.Equal(t, test.version, got) + }) + } +} + +func Test_findReplacementLicense(t *testing.T) { + tests := []struct { + l License + expected *License + licenses LicenseList + }{ + {license1, nil, LicenseList{}}, + {license1, nil, LicenseList{Licenses: []License{license3}}}, + {license1, &license2, LicenseList{Licenses: []License{license2, license3}}}, + {license1, &license2, LicenseList{Licenses: []License{license2, license3, license4, license5}}}, + } + + for _, tt := range tests { + assert.Equal(t, tt.expected, tt.licenses.findReplacementLicense(tt.l)) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/test-fixtures/licenses.json b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/test-fixtures/licenses.json new file mode 100644 index 0000000000000000000000000000000000000000..a8fba9c425a79f701e2c1f6a50b59bf0b79a5696 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/generate/test-fixtures/licenses.json @@ -0,0 +1,6155 @@ +{ + "licenseListVersion": "3.17", + "licenses": [ + { + "reference": "https://spdx.org/licenses/CC-BY-NC-ND-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-ND-2.0.json", + "referenceNumber": 0, + "name": "Creative Commons Attribution Non Commercial No Derivatives 2.0 Generic", + "licenseId": "CC-BY-NC-ND-2.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-nd/2.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SGI-B-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SGI-B-2.0.json", + "referenceNumber": 1, + "name": "SGI Free Software License B v2.0", + "licenseId": "SGI-B-2.0", + "seeAlso": [ + "http://oss.sgi.com/projects/FreeB/SGIFreeSWLicB.2.0.pdf" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LPPL-1.3c.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LPPL-1.3c.json", + "referenceNumber": 2, + "name": "LaTeX Project Public License v1.3c", + "licenseId": "LPPL-1.3c", + "seeAlso": [ + "http://www.latex-project.org/lppl/lppl-1-3c.txt", + "https://opensource.org/licenses/LPPL-1.3c" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/NIST-PD-fallback.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NIST-PD-fallback.json", + "referenceNumber": 3, + "name": "NIST Public Domain Notice with license fallback", + "licenseId": "NIST-PD-fallback", + "seeAlso": [ + "https://github.com/usnistgov/jsip/blob/59700e6926cbe96c5cdae897d9a7d2656b42abe3/LICENSE", + "https://github.com/usnistgov/fipy/blob/86aaa5c2ba2c6f1be19593c5986071cf6568cc34/LICENSE.rst" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/libtiff.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/libtiff.json", + "referenceNumber": 4, + "name": "libtiff License", + "licenseId": "libtiff", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/libtiff" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/XSkat.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/XSkat.json", + "referenceNumber": 5, + "name": "XSkat License", + "licenseId": "XSkat", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/XSkat_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/PDDL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/PDDL-1.0.json", + "referenceNumber": 6, + "name": "Open Data Commons Public Domain Dedication \u0026 License 1.0", + "licenseId": "PDDL-1.0", + "seeAlso": [ + "http://opendatacommons.org/licenses/pddl/1.0/", + "https://opendatacommons.org/licenses/pddl/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/KiCad-libraries-exception.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/KiCad-libraries-exception.json", + "referenceNumber": 7, + "name": "KiCad Libraries Exception", + "licenseId": "KiCad-libraries-exception", + "seeAlso": [ + "https://www.kicad.org/libraries/license/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-1.0.json", + "referenceNumber": 8, + "name": "Creative Commons Attribution Non Commercial Share Alike 1.0 Generic", + "licenseId": "CC-BY-NC-SA-1.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/1.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.1-no-invariants-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.1-no-invariants-only.json", + "referenceNumber": 9, + "name": "GNU Free Documentation License v1.1 only - no invariants", + "licenseId": "GFDL-1.1-no-invariants-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.1.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Xerox.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Xerox.json", + "referenceNumber": 10, + "name": "Xerox License", + "licenseId": "Xerox", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Xerox" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LPPL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LPPL-1.1.json", + "referenceNumber": 11, + "name": "LaTeX Project Public License v1.1", + "licenseId": "LPPL-1.1", + "seeAlso": [ + "http://www.latex-project.org/lppl/lppl-1-1.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/VOSTROM.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/VOSTROM.json", + "referenceNumber": 12, + "name": "VOSTROM Public License for Open Source", + "licenseId": "VOSTROM", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/VOSTROM" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/UCL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/UCL-1.0.json", + "referenceNumber": 13, + "name": "Upstream Compatibility License v1.0", + "licenseId": "UCL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/UCL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/ADSL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ADSL.json", + "referenceNumber": 14, + "name": "Amazon Digital Services License", + "licenseId": "ADSL", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/AmazonDigitalServicesLicense" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OSL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OSL-2.0.json", + "referenceNumber": 15, + "name": "Open Software License 2.0", + "licenseId": "OSL-2.0", + "seeAlso": [ + "http://web.archive.org/web/20041020171434/http://www.rosenlaw.com/osl2.0.html" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/AAL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AAL.json", + "referenceNumber": 16, + "name": "Attribution Assurance License", + "licenseId": "AAL", + "seeAlso": [ + "https://opensource.org/licenses/attribution" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/FDK-AAC.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/FDK-AAC.json", + "referenceNumber": 17, + "name": "Fraunhofer FDK AAC Codec Library", + "licenseId": "FDK-AAC", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/FDK-AAC", + "https://directory.fsf.org/wiki/License:Fdk" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/W3C-20150513.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/W3C-20150513.json", + "referenceNumber": 18, + "name": "W3C Software Notice and Document License (2015-05-13)", + "licenseId": "W3C-20150513", + "seeAlso": [ + "https://www.w3.org/Consortium/Legal/2015/copyright-software-and-document" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AFL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AFL-1.1.json", + "referenceNumber": 19, + "name": "Academic Free License v1.1", + "licenseId": "AFL-1.1", + "seeAlso": [ + "http://opensource.linux-mirror.org/licenses/afl-1.1.txt", + "http://wayback.archive.org/web/20021004124254/http://www.opensource.org/licenses/academic.php" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/W3C.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/W3C.json", + "referenceNumber": 20, + "name": "W3C Software Notice and License (2002-12-31)", + "licenseId": "W3C", + "seeAlso": [ + "http://www.w3.org/Consortium/Legal/2002/copyright-software-20021231.html", + "https://opensource.org/licenses/W3C" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Sleepycat.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Sleepycat.json", + "referenceNumber": 21, + "name": "Sleepycat License", + "licenseId": "Sleepycat", + "seeAlso": [ + "https://opensource.org/licenses/Sleepycat" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CECILL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CECILL-1.1.json", + "referenceNumber": 22, + "name": "CeCILL Free Software License Agreement v1.1", + "licenseId": "CECILL-1.1", + "seeAlso": [ + "http://www.cecill.info/licences/Licence_CeCILL_V1.1-US.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/mpich2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/mpich2.json", + "referenceNumber": 23, + "name": "mpich2 License", + "licenseId": "mpich2", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/MIT" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SISSL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SISSL.json", + "referenceNumber": 24, + "name": "Sun Industry Standards Source License v1.1", + "licenseId": "SISSL", + "seeAlso": [ + "http://www.openoffice.org/licenses/sissl_license.html", + "https://opensource.org/licenses/SISSL" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/NLOD-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NLOD-1.0.json", + "referenceNumber": 25, + "name": "Norwegian Licence for Open Government Data (NLOD) 1.0", + "licenseId": "NLOD-1.0", + "seeAlso": [ + "http://data.norge.no/nlod/en/1.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ANTLR-PD.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ANTLR-PD.json", + "referenceNumber": 26, + "name": "ANTLR Software Rights Notice", + "licenseId": "ANTLR-PD", + "seeAlso": [ + "http://www.antlr2.org/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GPL-3.0-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GPL-3.0-only.json", + "referenceNumber": 27, + "name": "GNU General Public License v3.0 only", + "licenseId": "GPL-3.0-only", + "seeAlso": [ + "https://www.gnu.org/licenses/gpl-3.0-standalone.html", + "https://opensource.org/licenses/GPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/gnuplot.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/gnuplot.json", + "referenceNumber": 28, + "name": "gnuplot License", + "licenseId": "gnuplot", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Gnuplot" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/NLOD-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NLOD-2.0.json", + "referenceNumber": 29, + "name": "Norwegian Licence for Open Government Data (NLOD) 2.0", + "licenseId": "NLOD-2.0", + "seeAlso": [ + "http://data.norge.no/nlod/en/2.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-Open-MPI.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-Open-MPI.json", + "referenceNumber": 30, + "name": "BSD 3-Clause Open MPI variant", + "licenseId": "BSD-3-Clause-Open-MPI", + "seeAlso": [ + "https://www.open-mpi.org/community/license.php", + "http://www.netlib.org/lapack/LICENSE.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LiLiQ-P-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LiLiQ-P-1.1.json", + "referenceNumber": 31, + "name": "Licence Libre du Québec – Permissive version 1.1", + "licenseId": "LiLiQ-P-1.1", + "seeAlso": [ + "https://forge.gouv.qc.ca/licence/fr/liliq-v1-1/", + "http://opensource.org/licenses/LiLiQ-P-1.1" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-Clear.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-Clear.json", + "referenceNumber": 32, + "name": "BSD 3-Clause Clear License", + "licenseId": "BSD-3-Clause-Clear", + "seeAlso": [ + "http://labs.metacarta.com/license-explanation.html#license" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/FSFUL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/FSFUL.json", + "referenceNumber": 33, + "name": "FSF Unlimited License", + "licenseId": "FSFUL", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/FSF_Unlimited_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-2.0-UK.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-2.0-UK.json", + "referenceNumber": 34, + "name": "Creative Commons Attribution Non Commercial Share Alike 2.0 England and Wales", + "licenseId": "CC-BY-NC-SA-2.0-UK", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/2.0/uk/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CERN-OHL-S-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CERN-OHL-S-2.0.json", + "referenceNumber": 35, + "name": "CERN Open Hardware Licence Version 2 - Strongly Reciprocal", + "licenseId": "CERN-OHL-S-2.0", + "seeAlso": [ + "https://www.ohwr.org/project/cernohl/wikis/Documents/CERN-OHL-version-2" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/Spencer-94.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Spencer-94.json", + "referenceNumber": 36, + "name": "Spencer License 94", + "licenseId": "Spencer-94", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Henry_Spencer_Reg-Ex_Library_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CERN-OHL-1.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CERN-OHL-1.2.json", + "referenceNumber": 37, + "name": "CERN Open Hardware Licence v1.2", + "licenseId": "CERN-OHL-1.2", + "seeAlso": [ + "https://www.ohwr.org/project/licenses/wikis/cern-ohl-v1.2" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.1-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.1-or-later.json", + "referenceNumber": 38, + "name": "GNU Free Documentation License v1.1 or later", + "licenseId": "GFDL-1.1-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.1.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/AGPL-1.0-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AGPL-1.0-or-later.json", + "referenceNumber": 39, + "name": "Affero General Public License v1.0 or later", + "licenseId": "AGPL-1.0-or-later", + "seeAlso": [ + "http://www.affero.org/oagpl.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Wsuipa.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Wsuipa.json", + "referenceNumber": 40, + "name": "Wsuipa License", + "licenseId": "Wsuipa", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Wsuipa" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AML.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AML.json", + "referenceNumber": 41, + "name": "Apple MIT License", + "licenseId": "AML", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Apple_MIT_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-2-Clause.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-2-Clause.json", + "referenceNumber": 42, + "name": "BSD 2-Clause \"Simplified\" License", + "licenseId": "BSD-2-Clause", + "seeAlso": [ + "https://opensource.org/licenses/BSD-2-Clause" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/DSDP.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/DSDP.json", + "referenceNumber": 43, + "name": "DSDP License", + "licenseId": "DSDP", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/DSDP" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-2.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-2.5.json", + "referenceNumber": 44, + "name": "Creative Commons Attribution 2.5 Generic", + "licenseId": "CC-BY-2.5", + "seeAlso": [ + "https://creativecommons.org/licenses/by/2.5/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MIT-CMU.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MIT-CMU.json", + "referenceNumber": 45, + "name": "CMU License", + "licenseId": "MIT-CMU", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing:MIT?rd\u003dLicensing/MIT#CMU_Style", + "https://github.com/python-pillow/Pillow/blob/fffb426092c8db24a5f4b6df243a8a3c01fb63cd/LICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Beerware.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Beerware.json", + "referenceNumber": 46, + "name": "Beerware License", + "licenseId": "Beerware", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Beerware", + "https://people.freebsd.org/~phk/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Sendmail.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Sendmail.json", + "referenceNumber": 47, + "name": "Sendmail License", + "licenseId": "Sendmail", + "seeAlso": [ + "http://www.sendmail.com/pdfs/open_source/sendmail_license.pdf", + "https://web.archive.org/web/20160322142305/https://www.sendmail.com/pdfs/open_source/sendmail_license.pdf" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/TU-Berlin-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/TU-Berlin-1.0.json", + "referenceNumber": 48, + "name": "Technische Universitaet Berlin License 1.0", + "licenseId": "TU-Berlin-1.0", + "seeAlso": [ + "https://github.com/swh/ladspa/blob/7bf6f3799fdba70fda297c2d8fd9f526803d9680/gsm/COPYRIGHT" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CNRI-Jython.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CNRI-Jython.json", + "referenceNumber": 49, + "name": "CNRI Jython License", + "licenseId": "CNRI-Jython", + "seeAlso": [ + "http://www.jython.org/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/mplus.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/mplus.json", + "referenceNumber": 50, + "name": "mplus Font License", + "licenseId": "mplus", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing:Mplus?rd\u003dLicensing/mplus" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CPOL-1.02.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CPOL-1.02.json", + "referenceNumber": 51, + "name": "Code Project Open License 1.02", + "licenseId": "CPOL-1.02", + "seeAlso": [ + "http://www.codeproject.com/info/cpol10.aspx" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-No-Nuclear-License-2014.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-No-Nuclear-License-2014.json", + "referenceNumber": 52, + "name": "BSD 3-Clause No Nuclear License 2014", + "licenseId": "BSD-3-Clause-No-Nuclear-License-2014", + "seeAlso": [ + "https://java.net/projects/javaeetutorial/pages/BerkeleyLicense" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ISC.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ISC.json", + "referenceNumber": 53, + "name": "ISC License", + "licenseId": "ISC", + "seeAlso": [ + "https://www.isc.org/licenses/", + "https://www.isc.org/downloads/software-support-policy/isc-license/", + "https://opensource.org/licenses/ISC" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-4.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-4.0.json", + "referenceNumber": 54, + "name": "Creative Commons Attribution Share Alike 4.0 International", + "licenseId": "CC-BY-SA-4.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/4.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Eurosym.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Eurosym.json", + "referenceNumber": 55, + "name": "Eurosym License", + "licenseId": "Eurosym", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Eurosym" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LGPL-3.0-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LGPL-3.0-only.json", + "referenceNumber": 56, + "name": "GNU Lesser General Public License v3.0 only", + "licenseId": "LGPL-3.0-only", + "seeAlso": [ + "https://www.gnu.org/licenses/lgpl-3.0-standalone.html", + "https://www.gnu.org/licenses/lgpl+gpl-3.0.txt", + "https://opensource.org/licenses/LGPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OLDAP-1.3.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-1.3.json", + "referenceNumber": 57, + "name": "Open LDAP Public License v1.3", + "licenseId": "OLDAP-1.3", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003de5f8117f0ce088d0bd7a8e18ddf37eaa40eb09b1" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.1-invariants-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.1-invariants-or-later.json", + "referenceNumber": 58, + "name": "GNU Free Documentation License v1.1 or later - invariants", + "licenseId": "GFDL-1.1-invariants-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.1.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Glulxe.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Glulxe.json", + "referenceNumber": 59, + "name": "Glulxe License", + "licenseId": "Glulxe", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Glulxe" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SimPL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SimPL-2.0.json", + "referenceNumber": 60, + "name": "Simple Public License 2.0", + "licenseId": "SimPL-2.0", + "seeAlso": [ + "https://opensource.org/licenses/SimPL-2.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CDLA-Permissive-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CDLA-Permissive-2.0.json", + "referenceNumber": 61, + "name": "Community Data License Agreement Permissive 2.0", + "licenseId": "CDLA-Permissive-2.0", + "seeAlso": [ + "https://cdla.dev/permissive-2-0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0-with-font-exception.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0-with-font-exception.json", + "referenceNumber": 62, + "name": "GNU General Public License v2.0 w/Font exception", + "licenseId": "GPL-2.0-with-font-exception", + "seeAlso": [ + "https://www.gnu.org/licenses/gpl-faq.html#FontException" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OGL-UK-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OGL-UK-2.0.json", + "referenceNumber": 63, + "name": "Open Government Licence v2.0", + "licenseId": "OGL-UK-2.0", + "seeAlso": [ + "http://www.nationalarchives.gov.uk/doc/open-government-licence/version/2/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-3.0-DE.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-3.0-DE.json", + "referenceNumber": 64, + "name": "Creative Commons Attribution Share Alike 3.0 Germany", + "licenseId": "CC-BY-SA-3.0-DE", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/3.0/de/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-ND-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-ND-1.0.json", + "referenceNumber": 65, + "name": "Creative Commons Attribution No Derivatives 1.0 Generic", + "licenseId": "CC-BY-ND-1.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nd/1.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.1.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.1.json", + "referenceNumber": 66, + "name": "GNU Free Documentation License v1.1", + "licenseId": "GFDL-1.1", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.1.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-4.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-4.0.json", + "referenceNumber": 67, + "name": "Creative Commons Attribution 4.0 International", + "licenseId": "CC-BY-4.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by/4.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OpenSSL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OpenSSL.json", + "referenceNumber": 68, + "name": "OpenSSL License", + "licenseId": "OpenSSL", + "seeAlso": [ + "http://www.openssl.org/source/license.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/TU-Berlin-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/TU-Berlin-2.0.json", + "referenceNumber": 69, + "name": "Technische Universitaet Berlin License 2.0", + "licenseId": "TU-Berlin-2.0", + "seeAlso": [ + "https://github.com/CorsixTH/deps/blob/fd339a9f526d1d9c9f01ccf39e438a015da50035/licences/libgsm.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/DOC.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/DOC.json", + "referenceNumber": 70, + "name": "DOC License", + "licenseId": "DOC", + "seeAlso": [ + "http://www.cs.wustl.edu/~schmidt/ACE-copying.html", + "https://www.dre.vanderbilt.edu/~schmidt/ACE-copying.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.2-no-invariants-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.2-no-invariants-or-later.json", + "referenceNumber": 71, + "name": "GNU Free Documentation License v1.2 or later - no invariants", + "licenseId": "GFDL-1.2-no-invariants-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.2.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/QPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/QPL-1.0.json", + "referenceNumber": 72, + "name": "Q Public License 1.0", + "licenseId": "QPL-1.0", + "seeAlso": [ + "http://doc.qt.nokia.com/3.3/license.html", + "https://opensource.org/licenses/QPL-1.0", + "https://doc.qt.io/archives/3.3/license.html" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.8.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.8.json", + "referenceNumber": 73, + "name": "Open LDAP Public License v2.8", + "licenseId": "OLDAP-2.8", + "seeAlso": [ + "http://www.openldap.org/software/release/license.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OML.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OML.json", + "referenceNumber": 74, + "name": "Open Market License", + "licenseId": "OML", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Open_Market_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.7.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.7.json", + "referenceNumber": 75, + "name": "Open LDAP Public License v2.7", + "licenseId": "OLDAP-2.7", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003d47c2415c1df81556eeb39be6cad458ef87c534a2" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/NIST-PD.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NIST-PD.json", + "referenceNumber": 76, + "name": "NIST Public Domain Notice", + "licenseId": "NIST-PD", + "seeAlso": [ + "https://github.com/tcheneau/simpleRPL/blob/e645e69e38dd4e3ccfeceb2db8cba05b7c2e0cd3/LICENSE.txt", + "https://github.com/tcheneau/Routing/blob/f09f46fcfe636107f22f2c98348188a65a135d98/README.md" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Bitstream-Vera.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Bitstream-Vera.json", + "referenceNumber": 77, + "name": "Bitstream Vera Font License", + "licenseId": "Bitstream-Vera", + "seeAlso": [ + "https://web.archive.org/web/20080207013128/http://www.gnome.org/fonts/", + "https://docubrain.com/sites/default/files/licenses/bitstream-vera.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.2-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.2-or-later.json", + "referenceNumber": 78, + "name": "GNU Free Documentation License v1.2 or later", + "licenseId": "GFDL-1.2-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.2.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OFL-1.1-RFN.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OFL-1.1-RFN.json", + "referenceNumber": 79, + "name": "SIL Open Font License 1.1 with Reserved Font Name", + "licenseId": "OFL-1.1-RFN", + "seeAlso": [ + "http://scripts.sil.org/cms/scripts/page.php?item_id\u003dOFL_web", + "https://opensource.org/licenses/OFL-1.1" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/Bahyph.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Bahyph.json", + "referenceNumber": 80, + "name": "Bahyph License", + "licenseId": "Bahyph", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Bahyph" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Barr.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Barr.json", + "referenceNumber": 81, + "name": "Barr License", + "licenseId": "Barr", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Barr" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/COIL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/COIL-1.0.json", + "referenceNumber": 82, + "name": "Copyfree Open Innovation License", + "licenseId": "COIL-1.0", + "seeAlso": [ + "https://coil.apotheon.org/plaintext/01.0.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.3.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.3.json", + "referenceNumber": 83, + "name": "GNU Free Documentation License v1.3", + "licenseId": "GFDL-1.3", + "seeAlso": [ + "https://www.gnu.org/licenses/fdl-1.3.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CECILL-B.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CECILL-B.json", + "referenceNumber": 84, + "name": "CeCILL-B Free Software License Agreement", + "licenseId": "CECILL-B", + "seeAlso": [ + "http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/JPNIC.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/JPNIC.json", + "referenceNumber": 85, + "name": "Japan Network Information Center License", + "licenseId": "JPNIC", + "seeAlso": [ + "https://gitlab.isc.org/isc-projects/bind9/blob/master/COPYRIGHT#L366" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Zed.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Zed.json", + "referenceNumber": 86, + "name": "Zed License", + "licenseId": "Zed", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Zed" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ICU.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ICU.json", + "referenceNumber": 87, + "name": "ICU License", + "licenseId": "ICU", + "seeAlso": [ + "http://source.icu-project.org/repos/icu/icu/trunk/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-2.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-2.5.json", + "referenceNumber": 88, + "name": "Creative Commons Attribution Non Commercial Share Alike 2.5 Generic", + "licenseId": "CC-BY-NC-SA-2.5", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/2.5/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-ND-3.0-DE.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-ND-3.0-DE.json", + "referenceNumber": 89, + "name": "Creative Commons Attribution No Derivatives 3.0 Germany", + "licenseId": "CC-BY-ND-3.0-DE", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nd/3.0/de/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/bzip2-1.0.5.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/bzip2-1.0.5.json", + "referenceNumber": 90, + "name": "bzip2 and libbzip2 License v1.0.5", + "licenseId": "bzip2-1.0.5", + "seeAlso": [ + "https://sourceware.org/bzip2/1.0.5/bzip2-manual-1.0.5.html", + "http://bzip.org/1.0.5/bzip2-manual-1.0.5.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SPL-1.0.json", + "referenceNumber": 91, + "name": "Sun Public License v1.0", + "licenseId": "SPL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/SPL-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/YPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/YPL-1.0.json", + "referenceNumber": 92, + "name": "Yahoo! Public License v1.0", + "licenseId": "YPL-1.0", + "seeAlso": [ + "http://www.zimbra.com/license/yahoo_public_license_1.0.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OSET-PL-2.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OSET-PL-2.1.json", + "referenceNumber": 93, + "name": "OSET Public License version 2.1", + "licenseId": "OSET-PL-2.1", + "seeAlso": [ + "http://www.osetfoundation.org/public-license", + "https://opensource.org/licenses/OPL-2.1" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/Noweb.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Noweb.json", + "referenceNumber": 94, + "name": "Noweb License", + "licenseId": "Noweb", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Noweb" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/RPSL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/RPSL-1.0.json", + "referenceNumber": 95, + "name": "RealNetworks Public Source License v1.0", + "licenseId": "RPSL-1.0", + "seeAlso": [ + "https://helixcommunity.org/content/rpsl", + "https://opensource.org/licenses/RPSL-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-LBNL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-LBNL.json", + "referenceNumber": 96, + "name": "Lawrence Berkeley National Labs BSD variant license", + "licenseId": "BSD-3-Clause-LBNL", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/LBNLBSD" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CDLA-Sharing-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CDLA-Sharing-1.0.json", + "referenceNumber": 97, + "name": "Community Data License Agreement Sharing 1.0", + "licenseId": "CDLA-Sharing-1.0", + "seeAlso": [ + "https://cdla.io/sharing-1-0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CECILL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CECILL-1.0.json", + "referenceNumber": 98, + "name": "CeCILL Free Software License Agreement v1.0", + "licenseId": "CECILL-1.0", + "seeAlso": [ + "http://www.cecill.info/licences/Licence_CeCILL_V1-fr.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AMPAS.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AMPAS.json", + "referenceNumber": 99, + "name": "Academy of Motion Picture Arts and Sciences BSD", + "licenseId": "AMPAS", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/BSD#AMPASBSD" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/APAFML.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/APAFML.json", + "referenceNumber": 100, + "name": "Adobe Postscript AFM License", + "licenseId": "APAFML", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/AdobePostscriptAFM" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-ND-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-ND-3.0.json", + "referenceNumber": 101, + "name": "Creative Commons Attribution No Derivatives 3.0 Unported", + "licenseId": "CC-BY-ND-3.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nd/3.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/D-FSL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/D-FSL-1.0.json", + "referenceNumber": 102, + "name": "Deutsche Freie Software Lizenz", + "licenseId": "D-FSL-1.0", + "seeAlso": [ + "http://www.dipp.nrw.de/d-fsl/lizenzen/", + "http://www.dipp.nrw.de/d-fsl/index_html/lizenzen/de/D-FSL-1_0_de.txt", + "http://www.dipp.nrw.de/d-fsl/index_html/lizenzen/en/D-FSL-1_0_en.txt", + "https://www.hbz-nrw.de/produkte/open-access/lizenzen/dfsl", + "https://www.hbz-nrw.de/produkte/open-access/lizenzen/dfsl/deutsche-freie-software-lizenz", + "https://www.hbz-nrw.de/produkte/open-access/lizenzen/dfsl/german-free-software-license", + "https://www.hbz-nrw.de/produkte/open-access/lizenzen/dfsl/D-FSL-1_0_de.txt/at_download/file", + "https://www.hbz-nrw.de/produkte/open-access/lizenzen/dfsl/D-FSL-1_0_en.txt/at_download/file" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-3.0.json", + "referenceNumber": 103, + "name": "Creative Commons Attribution Non Commercial 3.0 Unported", + "licenseId": "CC-BY-NC-3.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc/3.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/libpng-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/libpng-2.0.json", + "referenceNumber": 104, + "name": "PNG Reference Library version 2", + "licenseId": "libpng-2.0", + "seeAlso": [ + "http://www.libpng.org/pub/png/src/libpng-LICENSE.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/PolyForm-Noncommercial-1.0.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/PolyForm-Noncommercial-1.0.0.json", + "referenceNumber": 105, + "name": "PolyForm Noncommercial License 1.0.0", + "licenseId": "PolyForm-Noncommercial-1.0.0", + "seeAlso": [ + "https://polyformproject.org/licenses/noncommercial/1.0.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/dvipdfm.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/dvipdfm.json", + "referenceNumber": 106, + "name": "dvipdfm License", + "licenseId": "dvipdfm", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/dvipdfm" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.3-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.3-or-later.json", + "referenceNumber": 107, + "name": "GNU Free Documentation License v1.3 or later", + "licenseId": "GFDL-1.3-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/fdl-1.3.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OGTSL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OGTSL.json", + "referenceNumber": 108, + "name": "Open Group Test Suite License", + "licenseId": "OGTSL", + "seeAlso": [ + "http://www.opengroup.org/testing/downloads/The_Open_Group_TSL.txt", + "https://opensource.org/licenses/OGTSL" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/NPL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NPL-1.1.json", + "referenceNumber": 109, + "name": "Netscape Public License v1.1", + "licenseId": "NPL-1.1", + "seeAlso": [ + "http://www.mozilla.org/MPL/NPL/1.1/" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-3.0.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-3.0.json", + "referenceNumber": 110, + "name": "GNU General Public License v3.0 only", + "licenseId": "GPL-3.0", + "seeAlso": [ + "https://www.gnu.org/licenses/gpl-3.0-standalone.html", + "https://opensource.org/licenses/GPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CERN-OHL-P-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CERN-OHL-P-2.0.json", + "referenceNumber": 111, + "name": "CERN Open Hardware Licence Version 2 - Permissive", + "licenseId": "CERN-OHL-P-2.0", + "seeAlso": [ + "https://www.ohwr.org/project/cernohl/wikis/Documents/CERN-OHL-version-2" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/BlueOak-1.0.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BlueOak-1.0.0.json", + "referenceNumber": 112, + "name": "Blue Oak Model License 1.0.0", + "licenseId": "BlueOak-1.0.0", + "seeAlso": [ + "https://blueoakcouncil.org/license/1.0.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AGPL-3.0-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AGPL-3.0-or-later.json", + "referenceNumber": 113, + "name": "GNU Affero General Public License v3.0 or later", + "licenseId": "AGPL-3.0-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/agpl.txt", + "https://opensource.org/licenses/AGPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/blessing.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/blessing.json", + "referenceNumber": 114, + "name": "SQLite Blessing", + "licenseId": "blessing", + "seeAlso": [ + "https://www.sqlite.org/src/artifact/e33a4df7e32d742a?ln\u003d4-9", + "https://sqlite.org/src/artifact/df5091916dbb40e6" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ImageMagick.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ImageMagick.json", + "referenceNumber": 115, + "name": "ImageMagick License", + "licenseId": "ImageMagick", + "seeAlso": [ + "http://www.imagemagick.org/script/license.php" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/APSL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/APSL-2.0.json", + "referenceNumber": 116, + "name": "Apple Public Source License 2.0", + "licenseId": "APSL-2.0", + "seeAlso": [ + "http://www.opensource.apple.com/license/apsl/" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/MIT-advertising.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MIT-advertising.json", + "referenceNumber": 117, + "name": "Enlightenment License (e16)", + "licenseId": "MIT-advertising", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/MIT_With_Advertising" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/curl.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/curl.json", + "referenceNumber": 118, + "name": "curl License", + "licenseId": "curl", + "seeAlso": [ + "https://github.com/bagder/curl/blob/master/COPYING" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC0-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC0-1.0.json", + "referenceNumber": 119, + "name": "Creative Commons Zero v1.0 Universal", + "licenseId": "CC0-1.0", + "seeAlso": [ + "https://creativecommons.org/publicdomain/zero/1.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Zimbra-1.4.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Zimbra-1.4.json", + "referenceNumber": 120, + "name": "Zimbra Public License v1.4", + "licenseId": "Zimbra-1.4", + "seeAlso": [ + "http://www.zimbra.com/legal/zimbra-public-license-1-4" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SSPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SSPL-1.0.json", + "referenceNumber": 121, + "name": "Server Side Public License, v 1", + "licenseId": "SSPL-1.0", + "seeAlso": [ + "https://www.mongodb.com/licensing/server-side-public-license" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/psutils.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/psutils.json", + "referenceNumber": 122, + "name": "psutils License", + "licenseId": "psutils", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/psutils" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-2.0-UK.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-2.0-UK.json", + "referenceNumber": 123, + "name": "Creative Commons Attribution Share Alike 2.0 England and Wales", + "licenseId": "CC-BY-SA-2.0-UK", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/2.0/uk/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/PSF-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/PSF-2.0.json", + "referenceNumber": 124, + "name": "Python Software Foundation License 2.0", + "licenseId": "PSF-2.0", + "seeAlso": [ + "https://opensource.org/licenses/Python-2.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Net-SNMP.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Net-SNMP.json", + "referenceNumber": 125, + "name": "Net-SNMP License", + "licenseId": "Net-SNMP", + "seeAlso": [ + "http://net-snmp.sourceforge.net/about/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NAIST-2003.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NAIST-2003.json", + "referenceNumber": 126, + "name": "Nara Institute of Science and Technology License (2003)", + "licenseId": "NAIST-2003", + "seeAlso": [ + "https://enterprise.dejacode.com/licenses/public/naist-2003/#license-text", + "https://github.com/nodejs/node/blob/4a19cc8947b1bba2b2d27816ec3d0edf9b28e503/LICENSE#L343" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.2-invariants-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.2-invariants-or-later.json", + "referenceNumber": 127, + "name": "GNU Free Documentation License v1.2 or later - invariants", + "licenseId": "GFDL-1.2-invariants-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.2.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SGI-B-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SGI-B-1.0.json", + "referenceNumber": 128, + "name": "SGI Free Software License B v1.0", + "licenseId": "SGI-B-1.0", + "seeAlso": [ + "http://oss.sgi.com/projects/FreeB/SGIFreeSWLicB.1.0.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NBPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NBPL-1.0.json", + "referenceNumber": 129, + "name": "Net Boolean Public License v1", + "licenseId": "NBPL-1.0", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003d37b4b3f6cc4bf34e1d3dec61e69914b9819d8894" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.2-invariants-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.2-invariants-only.json", + "referenceNumber": 130, + "name": "GNU Free Documentation License v1.2 only - invariants", + "licenseId": "GFDL-1.2-invariants-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.2.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/W3C-19980720.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/W3C-19980720.json", + "referenceNumber": 131, + "name": "W3C Software Notice and License (1998-07-20)", + "licenseId": "W3C-19980720", + "seeAlso": [ + "http://www.w3.org/Consortium/Legal/copyright-software-19980720.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OFL-1.0-no-RFN.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OFL-1.0-no-RFN.json", + "referenceNumber": 132, + "name": "SIL Open Font License 1.0 with no Reserved Font Name", + "licenseId": "OFL-1.0-no-RFN", + "seeAlso": [ + "http://scripts.sil.org/cms/scripts/page.php?item_id\u003dOFL10_web" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NetCDF.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NetCDF.json", + "referenceNumber": 133, + "name": "NetCDF license", + "licenseId": "NetCDF", + "seeAlso": [ + "http://www.unidata.ucar.edu/software/netcdf/copyright.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/TMate.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/TMate.json", + "referenceNumber": 134, + "name": "TMate Open Source License", + "licenseId": "TMate", + "seeAlso": [ + "http://svnkit.com/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NOSL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NOSL.json", + "referenceNumber": 135, + "name": "Netizen Open Source License", + "licenseId": "NOSL", + "seeAlso": [ + "http://bits.netizen.com.au/licenses/NOSL/nosl.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CNRI-Python-GPL-Compatible.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CNRI-Python-GPL-Compatible.json", + "referenceNumber": 136, + "name": "CNRI Python Open Source GPL Compatible License Agreement", + "licenseId": "CNRI-Python-GPL-Compatible", + "seeAlso": [ + "http://www.python.org/download/releases/1.6.1/download_win/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-1-Clause.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-1-Clause.json", + "referenceNumber": 137, + "name": "BSD 1-Clause License", + "licenseId": "BSD-1-Clause", + "seeAlso": [ + "https://svnweb.freebsd.org/base/head/include/ifaddrs.h?revision\u003d326823" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-3.0-DE.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-3.0-DE.json", + "referenceNumber": 138, + "name": "Creative Commons Attribution Non Commercial Share Alike 3.0 Germany", + "licenseId": "CC-BY-NC-SA-3.0-DE", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/3.0/de/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-Modification.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-Modification.json", + "referenceNumber": 139, + "name": "BSD 3-Clause Modification", + "licenseId": "BSD-3-Clause-Modification", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing:BSD#Modification_Variant" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GLWTPL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GLWTPL.json", + "referenceNumber": 140, + "name": "Good Luck With That Public License", + "licenseId": "GLWTPL", + "seeAlso": [ + "https://github.com/me-shaon/GLWTPL/commit/da5f6bc734095efbacb442c0b31e33a65b9d6e85" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.3-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.3-only.json", + "referenceNumber": 141, + "name": "GNU Free Documentation License v1.3 only", + "licenseId": "GFDL-1.3-only", + "seeAlso": [ + "https://www.gnu.org/licenses/fdl-1.3.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.2.json", + "referenceNumber": 142, + "name": "Open LDAP Public License v2.2", + "licenseId": "OLDAP-2.2", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003d470b0c18ec67621c85881b2733057fecf4a1acc3" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-ND-4.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-ND-4.0.json", + "referenceNumber": 143, + "name": "Creative Commons Attribution No Derivatives 4.0 International", + "licenseId": "CC-BY-ND-4.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nd/4.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-ND-3.0-DE.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-ND-3.0-DE.json", + "referenceNumber": 144, + "name": "Creative Commons Attribution Non Commercial No Derivatives 3.0 Germany", + "licenseId": "CC-BY-NC-ND-3.0-DE", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-nd/3.0/de/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/EUPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EUPL-1.0.json", + "referenceNumber": 145, + "name": "European Union Public License 1.0", + "licenseId": "EUPL-1.0", + "seeAlso": [ + "http://ec.europa.eu/idabc/en/document/7330.html", + "http://ec.europa.eu/idabc/servlets/Doc027f.pdf?id\u003d31096" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Linux-OpenIB.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Linux-OpenIB.json", + "referenceNumber": 146, + "name": "Linux Kernel Variant of OpenIB.org license", + "licenseId": "Linux-OpenIB", + "seeAlso": [ + "https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/drivers/infiniband/core/sa.h" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LGPL-2.0-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LGPL-2.0-or-later.json", + "referenceNumber": 147, + "name": "GNU Library General Public License v2 or later", + "licenseId": "LGPL-2.0-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/lgpl-2.0-standalone.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OSL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OSL-1.1.json", + "referenceNumber": 148, + "name": "Open Software License 1.1", + "licenseId": "OSL-1.1", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/OSL1.1" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Spencer-86.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Spencer-86.json", + "referenceNumber": 149, + "name": "Spencer License 86", + "licenseId": "Spencer-86", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Henry_Spencer_Reg-Ex_Library_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LGPL-2.0.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/LGPL-2.0.json", + "referenceNumber": 150, + "name": "GNU Library General Public License v2 only", + "licenseId": "LGPL-2.0", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/lgpl-2.0-standalone.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CC-PDDC.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-PDDC.json", + "referenceNumber": 151, + "name": "Creative Commons Public Domain Dedication and Certification", + "licenseId": "CC-PDDC", + "seeAlso": [ + "https://creativecommons.org/licenses/publicdomain/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-ND-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-ND-3.0.json", + "referenceNumber": 152, + "name": "Creative Commons Attribution Non Commercial No Derivatives 3.0 Unported", + "licenseId": "CC-BY-NC-ND-3.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-nd/3.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CDL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CDL-1.0.json", + "referenceNumber": 153, + "name": "Common Documentation License 1.0", + "licenseId": "CDL-1.0", + "seeAlso": [ + "http://www.opensource.apple.com/cdl/", + "https://fedoraproject.org/wiki/Licensing/Common_Documentation_License", + "https://www.gnu.org/licenses/license-list.html#ACDL" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Elastic-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Elastic-2.0.json", + "referenceNumber": 154, + "name": "Elastic License 2.0", + "licenseId": "Elastic-2.0", + "seeAlso": [ + "https://www.elastic.co/licensing/elastic-license", + "https://github.com/elastic/elasticsearch/blob/master/licenses/ELASTIC-LICENSE-2.0.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-2.0.json", + "referenceNumber": 155, + "name": "Creative Commons Attribution 2.0 Generic", + "licenseId": "CC-BY-2.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by/2.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-No-Military-License.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-No-Military-License.json", + "referenceNumber": 156, + "name": "BSD 3-Clause No Military License", + "licenseId": "BSD-3-Clause-No-Military-License", + "seeAlso": [ + "https://gitlab.syncad.com/hive/dhive/-/blob/master/LICENSE", + "https://github.com/greymass/swift-eosio/blob/master/LICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/IJG.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/IJG.json", + "referenceNumber": 157, + "name": "Independent JPEG Group License", + "licenseId": "IJG", + "seeAlso": [ + "http://dev.w3.org/cvsweb/Amaya/libjpeg/Attic/README?rev\u003d1.2" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LPPL-1.3a.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LPPL-1.3a.json", + "referenceNumber": 158, + "name": "LaTeX Project Public License v1.3a", + "licenseId": "LPPL-1.3a", + "seeAlso": [ + "http://www.latex-project.org/lppl/lppl-1-3a.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/SAX-PD.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SAX-PD.json", + "referenceNumber": 159, + "name": "Sax Public Domain Notice", + "licenseId": "SAX-PD", + "seeAlso": [ + "http://www.saxproject.org/copying.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BitTorrent-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BitTorrent-1.0.json", + "referenceNumber": 160, + "name": "BitTorrent Open Source License v1.0", + "licenseId": "BitTorrent-1.0", + "seeAlso": [ + "http://sources.gentoo.org/cgi-bin/viewvc.cgi/gentoo-x86/licenses/BitTorrent?r1\u003d1.1\u0026r2\u003d1.1.1.1\u0026diff_format\u003ds" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.0.json", + "referenceNumber": 161, + "name": "Open LDAP Public License v2.0 (or possibly 2.0A and 2.0B)", + "licenseId": "OLDAP-2.0", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003dcbf50f4e1185a21abd4c0a54d3f4341fe28f36ea" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Giftware.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Giftware.json", + "referenceNumber": 162, + "name": "Giftware License", + "licenseId": "Giftware", + "seeAlso": [ + "http://liballeg.org/license.html#allegro-4-the-giftware-license" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/C-UDA-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/C-UDA-1.0.json", + "referenceNumber": 163, + "name": "Computational Use of Data Agreement v1.0", + "licenseId": "C-UDA-1.0", + "seeAlso": [ + "https://github.com/microsoft/Computational-Use-of-Data-Agreement/blob/master/C-UDA-1.0.md", + "https://cdla.dev/computational-use-of-data-agreement-v1-0/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LGPL-2.0+.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/LGPL-2.0+.json", + "referenceNumber": 164, + "name": "GNU Library General Public License v2 or later", + "licenseId": "LGPL-2.0+", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/lgpl-2.0-standalone.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/Rdisc.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Rdisc.json", + "referenceNumber": 165, + "name": "Rdisc License", + "licenseId": "Rdisc", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Rdisc_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0-with-classpath-exception.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0-with-classpath-exception.json", + "referenceNumber": 166, + "name": "GNU General Public License v2.0 w/Classpath exception", + "licenseId": "GPL-2.0-with-classpath-exception", + "seeAlso": [ + "https://www.gnu.org/software/classpath/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-3.0-US.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-3.0-US.json", + "referenceNumber": 167, + "name": "Creative Commons Attribution 3.0 United States", + "licenseId": "CC-BY-3.0-US", + "seeAlso": [ + "https://creativecommons.org/licenses/by/3.0/us/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CDDL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CDDL-1.0.json", + "referenceNumber": 168, + "name": "Common Development and Distribution License 1.0", + "licenseId": "CDDL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/cddl1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Xnet.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Xnet.json", + "referenceNumber": 169, + "name": "X.Net License", + "licenseId": "Xnet", + "seeAlso": [ + "https://opensource.org/licenses/Xnet" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CPL-1.0.json", + "referenceNumber": 170, + "name": "Common Public License 1.0", + "licenseId": "CPL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/CPL-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LGPL-3.0-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LGPL-3.0-or-later.json", + "referenceNumber": 171, + "name": "GNU Lesser General Public License v3.0 or later", + "licenseId": "LGPL-3.0-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/lgpl-3.0-standalone.html", + "https://www.gnu.org/licenses/lgpl+gpl-3.0.txt", + "https://opensource.org/licenses/LGPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/NASA-1.3.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NASA-1.3.json", + "referenceNumber": 172, + "name": "NASA Open Source Agreement 1.3", + "licenseId": "NASA-1.3", + "seeAlso": [ + "http://ti.arc.nasa.gov/opensource/nosa/", + "https://opensource.org/licenses/NASA-1.3" + ], + "isOsiApproved": true, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/BUSL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BUSL-1.1.json", + "referenceNumber": 173, + "name": "Business Source License 1.1", + "licenseId": "BUSL-1.1", + "seeAlso": [ + "https://mariadb.com/bsl11/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/etalab-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/etalab-2.0.json", + "referenceNumber": 174, + "name": "Etalab Open License 2.0", + "licenseId": "etalab-2.0", + "seeAlso": [ + "https://github.com/DISIC/politique-de-contribution-open-source/blob/master/LICENSE.pdf", + "https://raw.githubusercontent.com/DISIC/politique-de-contribution-open-source/master/LICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MIT-open-group.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MIT-open-group.json", + "referenceNumber": 175, + "name": "MIT Open Group variant", + "licenseId": "MIT-open-group", + "seeAlso": [ + "https://gitlab.freedesktop.org/xorg/app/iceauth/-/blob/master/COPYING", + "https://gitlab.freedesktop.org/xorg/app/xvinfo/-/blob/master/COPYING", + "https://gitlab.freedesktop.org/xorg/app/xsetroot/-/blob/master/COPYING", + "https://gitlab.freedesktop.org/xorg/app/xauth/-/blob/master/COPYING" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OLDAP-1.4.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-1.4.json", + "referenceNumber": 176, + "name": "Open LDAP Public License v1.4", + "licenseId": "OLDAP-1.4", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003dc9f95c2f3f2ffb5e0ae55fe7388af75547660941" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.1-invariants-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.1-invariants-only.json", + "referenceNumber": 177, + "name": "GNU Free Documentation License v1.1 only - invariants", + "licenseId": "GFDL-1.1-invariants-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.1.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/RPL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/RPL-1.1.json", + "referenceNumber": 178, + "name": "Reciprocal Public License 1.1", + "licenseId": "RPL-1.1", + "seeAlso": [ + "https://opensource.org/licenses/RPL-1.1" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-ND-2.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-ND-2.5.json", + "referenceNumber": 179, + "name": "Creative Commons Attribution Non Commercial No Derivatives 2.5 Generic", + "licenseId": "CC-BY-NC-ND-2.5", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-nd/2.5/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/FSFULLR.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/FSFULLR.json", + "referenceNumber": 180, + "name": "FSF Unlimited License (with License Retention)", + "licenseId": "FSFULLR", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/FSF_Unlimited_License#License_Retention_Variant" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Saxpath.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Saxpath.json", + "referenceNumber": 181, + "name": "Saxpath License", + "licenseId": "Saxpath", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Saxpath_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NTP-0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NTP-0.json", + "referenceNumber": 182, + "name": "NTP No Attribution", + "licenseId": "NTP-0", + "seeAlso": [ + "https://github.com/tytso/e2fsprogs/blob/master/lib/et/et_name.c" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SISSL-1.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SISSL-1.2.json", + "referenceNumber": 183, + "name": "Sun Industry Standards Source License v1.2", + "licenseId": "SISSL-1.2", + "seeAlso": [ + "http://gridscheduler.sourceforge.net/Gridengine_SISSL_license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GPL-3.0-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GPL-3.0-or-later.json", + "referenceNumber": 184, + "name": "GNU General Public License v3.0 or later", + "licenseId": "GPL-3.0-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/gpl-3.0-standalone.html", + "https://opensource.org/licenses/GPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Apache-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Apache-1.1.json", + "referenceNumber": 185, + "name": "Apache License 1.1", + "licenseId": "Apache-1.1", + "seeAlso": [ + "http://apache.org/licenses/LICENSE-1.1", + "https://opensource.org/licenses/Apache-1.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-2.1-JP.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-2.1-JP.json", + "referenceNumber": 186, + "name": "Creative Commons Attribution Share Alike 2.1 Japan", + "licenseId": "CC-BY-SA-2.1-JP", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/2.1/jp/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AGPL-3.0-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AGPL-3.0-only.json", + "referenceNumber": 187, + "name": "GNU Affero General Public License v3.0 only", + "licenseId": "AGPL-3.0-only", + "seeAlso": [ + "https://www.gnu.org/licenses/agpl.txt", + "https://opensource.org/licenses/AGPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0-with-autoconf-exception.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0-with-autoconf-exception.json", + "referenceNumber": 188, + "name": "GNU General Public License v2.0 w/Autoconf exception", + "licenseId": "GPL-2.0-with-autoconf-exception", + "seeAlso": [ + "http://ac-archive.sourceforge.net/doc/copyright.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Artistic-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Artistic-2.0.json", + "referenceNumber": 189, + "name": "Artistic License 2.0", + "licenseId": "Artistic-2.0", + "seeAlso": [ + "http://www.perlfoundation.org/artistic_license_2_0", + "https://www.perlfoundation.org/artistic-license-20.html", + "https://opensource.org/licenses/artistic-license-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/App-s2p.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/App-s2p.json", + "referenceNumber": 190, + "name": "App::s2p License", + "licenseId": "App-s2p", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/App-s2p" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Unicode-DFS-2015.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Unicode-DFS-2015.json", + "referenceNumber": 191, + "name": "Unicode License Agreement - Data Files and Software (2015)", + "licenseId": "Unicode-DFS-2015", + "seeAlso": [ + "https://web.archive.org/web/20151224134844/http://unicode.org/copyright.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/diffmark.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/diffmark.json", + "referenceNumber": 192, + "name": "diffmark license", + "licenseId": "diffmark", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/diffmark" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SNIA.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SNIA.json", + "referenceNumber": 193, + "name": "SNIA Public License 1.1", + "licenseId": "SNIA", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/SNIA_Public_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-2.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-2.5.json", + "referenceNumber": 194, + "name": "Creative Commons Attribution Share Alike 2.5 Generic", + "licenseId": "CC-BY-SA-2.5", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/2.5/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Linux-man-pages-copyleft.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Linux-man-pages-copyleft.json", + "referenceNumber": 195, + "name": "Linux man-pages Copyleft", + "licenseId": "Linux-man-pages-copyleft", + "seeAlso": [ + "https://www.kernel.org/doc/man-pages/licenses.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/HPND-sell-variant.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/HPND-sell-variant.json", + "referenceNumber": 196, + "name": "Historical Permission Notice and Disclaimer - sell variant", + "licenseId": "HPND-sell-variant", + "seeAlso": [ + "https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/net/sunrpc/auth_gss/gss_generic_token.c?h\u003dv4.19" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ZPL-2.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ZPL-2.1.json", + "referenceNumber": 197, + "name": "Zope Public License 2.1", + "licenseId": "ZPL-2.1", + "seeAlso": [ + "http://old.zope.org/Resources/ZPL/" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/BSD-4-Clause-UC.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-4-Clause-UC.json", + "referenceNumber": 198, + "name": "BSD-4-Clause (University of California-Specific)", + "licenseId": "BSD-4-Clause-UC", + "seeAlso": [ + "http://www.freebsd.org/copyright/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LAL-1.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LAL-1.2.json", + "referenceNumber": 199, + "name": "Licence Art Libre 1.2", + "licenseId": "LAL-1.2", + "seeAlso": [ + "http://artlibre.org/licence/lal/licence-art-libre-12/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AGPL-1.0-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AGPL-1.0-only.json", + "referenceNumber": 200, + "name": "Affero General Public License v1.0 only", + "licenseId": "AGPL-1.0-only", + "seeAlso": [ + "http://www.affero.org/oagpl.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MIT-enna.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MIT-enna.json", + "referenceNumber": 201, + "name": "enna License", + "licenseId": "MIT-enna", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/MIT#enna" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Condor-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Condor-1.1.json", + "referenceNumber": 202, + "name": "Condor Public License v1.1", + "licenseId": "Condor-1.1", + "seeAlso": [ + "http://research.cs.wisc.edu/condor/license.html#condor", + "http://web.archive.org/web/20111123062036/http://research.cs.wisc.edu/condor/license.html#condor" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Naumen.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Naumen.json", + "referenceNumber": 203, + "name": "Naumen Public License", + "licenseId": "Naumen", + "seeAlso": [ + "https://opensource.org/licenses/Naumen" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.3-no-invariants-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.3-no-invariants-or-later.json", + "referenceNumber": 204, + "name": "GNU Free Documentation License v1.3 or later - no invariants", + "licenseId": "GFDL-1.3-no-invariants-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/fdl-1.3.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/RPL-1.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/RPL-1.5.json", + "referenceNumber": 205, + "name": "Reciprocal Public License 1.5", + "licenseId": "RPL-1.5", + "seeAlso": [ + "https://opensource.org/licenses/RPL-1.5" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/PolyForm-Small-Business-1.0.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/PolyForm-Small-Business-1.0.0.json", + "referenceNumber": 206, + "name": "PolyForm Small Business License 1.0.0", + "licenseId": "PolyForm-Small-Business-1.0.0", + "seeAlso": [ + "https://polyformproject.org/licenses/small-business/1.0.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/EFL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EFL-1.0.json", + "referenceNumber": 207, + "name": "Eiffel Forum License v1.0", + "licenseId": "EFL-1.0", + "seeAlso": [ + "http://www.eiffel-nice.org/license/forum.txt", + "https://opensource.org/licenses/EFL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/MirOS.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MirOS.json", + "referenceNumber": 208, + "name": "The MirOS Licence", + "licenseId": "MirOS", + "seeAlso": [ + "https://opensource.org/licenses/MirOS" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-2.5-AU.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-2.5-AU.json", + "referenceNumber": 209, + "name": "Creative Commons Attribution 2.5 Australia", + "licenseId": "CC-BY-2.5-AU", + "seeAlso": [ + "https://creativecommons.org/licenses/by/2.5/au/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Afmparse.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Afmparse.json", + "referenceNumber": 210, + "name": "Afmparse License", + "licenseId": "Afmparse", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Afmparse" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MPL-2.0-no-copyleft-exception.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MPL-2.0-no-copyleft-exception.json", + "referenceNumber": 211, + "name": "Mozilla Public License 2.0 (no copyleft exception)", + "licenseId": "MPL-2.0-no-copyleft-exception", + "seeAlso": [ + "https://www.mozilla.org/MPL/2.0/", + "https://opensource.org/licenses/MPL-2.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/LiLiQ-Rplus-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LiLiQ-Rplus-1.1.json", + "referenceNumber": 212, + "name": "Licence Libre du Québec – Réciprocité forte version 1.1", + "licenseId": "LiLiQ-Rplus-1.1", + "seeAlso": [ + "https://www.forge.gouv.qc.ca/participez/licence-logicielle/licence-libre-du-quebec-liliq-en-francais/licence-libre-du-quebec-reciprocite-forte-liliq-r-v1-1/", + "http://opensource.org/licenses/LiLiQ-Rplus-1.1" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/AFL-1.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AFL-1.2.json", + "referenceNumber": 213, + "name": "Academic Free License v1.2", + "licenseId": "AFL-1.2", + "seeAlso": [ + "http://opensource.linux-mirror.org/licenses/afl-1.2.txt", + "http://wayback.archive.org/web/20021204204652/http://www.opensource.org/licenses/academic.php" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OSL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OSL-1.0.json", + "referenceNumber": 214, + "name": "Open Software License 1.0", + "licenseId": "OSL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/OSL-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-1.0-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GPL-1.0-only.json", + "referenceNumber": 215, + "name": "GNU General Public License v1.0 only", + "licenseId": "GPL-1.0-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/gpl-1.0-standalone.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/APSL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/APSL-1.0.json", + "referenceNumber": 216, + "name": "Apple Public Source License 1.0", + "licenseId": "APSL-1.0", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Apple_Public_Source_License_1.0" + ], + "isOsiApproved": true, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/OGL-Canada-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OGL-Canada-2.0.json", + "referenceNumber": 217, + "name": "Open Government Licence - Canada", + "licenseId": "OGL-Canada-2.0", + "seeAlso": [ + "https://open.canada.ca/en/open-government-licence-canada" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CPAL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CPAL-1.0.json", + "referenceNumber": 218, + "name": "Common Public Attribution License 1.0", + "licenseId": "CPAL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/CPAL-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Latex2e.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Latex2e.json", + "referenceNumber": 219, + "name": "Latex2e License", + "licenseId": "Latex2e", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Latex2e" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Zend-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Zend-2.0.json", + "referenceNumber": 220, + "name": "Zend License v2.0", + "licenseId": "Zend-2.0", + "seeAlso": [ + "https://web.archive.org/web/20130517195954/http://www.zend.com/license/2_00.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Unlicense.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Unlicense.json", + "referenceNumber": 221, + "name": "The Unlicense", + "licenseId": "Unlicense", + "seeAlso": [ + "https://unlicense.org/" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/xpp.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/xpp.json", + "referenceNumber": 222, + "name": "XPP License", + "licenseId": "xpp", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/xpp" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-1.0.json", + "referenceNumber": 223, + "name": "Creative Commons Attribution Non Commercial 1.0 Generic", + "licenseId": "CC-BY-NC-1.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc/1.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/GPL-3.0-with-autoconf-exception.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-3.0-with-autoconf-exception.json", + "referenceNumber": 224, + "name": "GNU General Public License v3.0 w/Autoconf exception", + "licenseId": "GPL-3.0-with-autoconf-exception", + "seeAlso": [ + "https://www.gnu.org/licenses/autoconf-exception-3.0.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-3.0.json", + "referenceNumber": 225, + "name": "Creative Commons Attribution Non Commercial Share Alike 3.0 Unported", + "licenseId": "CC-BY-NC-SA-3.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/3.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/TCP-wrappers.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/TCP-wrappers.json", + "referenceNumber": 226, + "name": "TCP Wrappers License", + "licenseId": "TCP-wrappers", + "seeAlso": [ + "http://rc.quest.com/topics/openssh/license.php#tcpwrappers" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SCEA.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SCEA.json", + "referenceNumber": 227, + "name": "SCEA Shared Source License", + "licenseId": "SCEA", + "seeAlso": [ + "http://research.scea.com/scea_shared_source_license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SSH-short.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SSH-short.json", + "referenceNumber": 228, + "name": "SSH short notice", + "licenseId": "SSH-short", + "seeAlso": [ + "https://github.com/openssh/openssh-portable/blob/1b11ea7c58cd5c59838b5fa574cd456d6047b2d4/pathnames.h", + "http://web.mit.edu/kolya/.f/root/athena.mit.edu/sipb.mit.edu/project/openssh/OldFiles/src/openssh-2.9.9p2/ssh-add.1", + "https://joinup.ec.europa.eu/svn/lesoll/trunk/italc/lib/src/dsa_key.cpp" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-3.0-NL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-3.0-NL.json", + "referenceNumber": 229, + "name": "Creative Commons Attribution 3.0 Netherlands", + "licenseId": "CC-BY-3.0-NL", + "seeAlso": [ + "https://creativecommons.org/licenses/by/3.0/nl/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SchemeReport.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SchemeReport.json", + "referenceNumber": 230, + "name": "Scheme Language Report License", + "licenseId": "SchemeReport", + "seeAlso": [], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-3.0.json", + "referenceNumber": 231, + "name": "Creative Commons Attribution 3.0 Unported", + "licenseId": "CC-BY-3.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by/3.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MPL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MPL-2.0.json", + "referenceNumber": 232, + "name": "Mozilla Public License 2.0", + "licenseId": "MPL-2.0", + "seeAlso": [ + "https://www.mozilla.org/MPL/2.0/", + "https://opensource.org/licenses/MPL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Unicode-TOU.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Unicode-TOU.json", + "referenceNumber": 233, + "name": "Unicode Terms of Use", + "licenseId": "Unicode-TOU", + "seeAlso": [ + "http://www.unicode.org/copyright.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-ND-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-ND-1.0.json", + "referenceNumber": 234, + "name": "Creative Commons Attribution Non Commercial No Derivatives 1.0 Generic", + "licenseId": "CC-BY-NC-ND-1.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nd-nc/1.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Entessa.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Entessa.json", + "referenceNumber": 235, + "name": "Entessa Public License v1.0", + "licenseId": "Entessa", + "seeAlso": [ + "https://opensource.org/licenses/Entessa" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-No-Nuclear-License.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-No-Nuclear-License.json", + "referenceNumber": 236, + "name": "BSD 3-Clause No Nuclear License", + "licenseId": "BSD-3-Clause-No-Nuclear-License", + "seeAlso": [ + "http://download.oracle.com/otn-pub/java/licenses/bsd.txt?AuthParam\u003d1467140197_43d516ce1776bd08a58235a7785be1cc" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SWL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SWL.json", + "referenceNumber": 237, + "name": "Scheme Widget Library (SWL) Software License Agreement", + "licenseId": "SWL", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/SWL" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.2-no-invariants-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.2-no-invariants-only.json", + "referenceNumber": 238, + "name": "GNU Free Documentation License v1.2 only - no invariants", + "licenseId": "GFDL-1.2-no-invariants-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.2.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Parity-7.0.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Parity-7.0.0.json", + "referenceNumber": 239, + "name": "The Parity Public License 7.0.0", + "licenseId": "Parity-7.0.0", + "seeAlso": [ + "https://paritylicense.com/versions/7.0.0.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.2.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.2.1.json", + "referenceNumber": 240, + "name": "Open LDAP Public License v2.2.1", + "licenseId": "OLDAP-2.2.1", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003d4bc786f34b50aa301be6f5600f58a980070f481e" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SGI-B-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SGI-B-1.1.json", + "referenceNumber": 241, + "name": "SGI Free Software License B v1.1", + "licenseId": "SGI-B-1.1", + "seeAlso": [ + "http://oss.sgi.com/projects/FreeB/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/FTL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/FTL.json", + "referenceNumber": 242, + "name": "Freetype Project License", + "licenseId": "FTL", + "seeAlso": [ + "http://freetype.fis.uniroma2.it/FTL.TXT", + "http://git.savannah.gnu.org/cgit/freetype/freetype2.git/tree/docs/FTL.TXT", + "http://gitlab.freedesktop.org/freetype/freetype/-/raw/master/docs/FTL.TXT" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.4.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.4.json", + "referenceNumber": 243, + "name": "Open LDAP Public License v2.4", + "licenseId": "OLDAP-2.4", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003dcd1284c4a91a8a380d904eee68d1583f989ed386" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-4.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-4.0.json", + "referenceNumber": 244, + "name": "Creative Commons Attribution Non Commercial 4.0 International", + "licenseId": "CC-BY-NC-4.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc/4.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/bzip2-1.0.6.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/bzip2-1.0.6.json", + "referenceNumber": 245, + "name": "bzip2 and libbzip2 License v1.0.6", + "licenseId": "bzip2-1.0.6", + "seeAlso": [ + "https://sourceware.org/git/?p\u003dbzip2.git;a\u003dblob;f\u003dLICENSE;hb\u003dbzip2-1.0.6", + "http://bzip.org/1.0.5/bzip2-manual-1.0.5.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/copyleft-next-0.3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/copyleft-next-0.3.0.json", + "referenceNumber": 246, + "name": "copyleft-next 0.3.0", + "licenseId": "copyleft-next-0.3.0", + "seeAlso": [ + "https://github.com/copyleft-next/copyleft-next/blob/master/Releases/copyleft-next-0.3.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MakeIndex.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MakeIndex.json", + "referenceNumber": 247, + "name": "MakeIndex License", + "licenseId": "MakeIndex", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/MakeIndex" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NRL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NRL.json", + "referenceNumber": 248, + "name": "NRL License", + "licenseId": "NRL", + "seeAlso": [ + "http://web.mit.edu/network/isakmp/nrllicense.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.3-invariants-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.3-invariants-or-later.json", + "referenceNumber": 249, + "name": "GNU Free Documentation License v1.3 or later - invariants", + "licenseId": "GFDL-1.3-invariants-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/fdl-1.3.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-2.0.json", + "referenceNumber": 250, + "name": "Creative Commons Attribution Non Commercial 2.0 Generic", + "licenseId": "CC-BY-NC-2.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc/2.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/SugarCRM-1.1.3.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SugarCRM-1.1.3.json", + "referenceNumber": 251, + "name": "SugarCRM Public License v1.1.3", + "licenseId": "SugarCRM-1.1.3", + "seeAlso": [ + "http://www.sugarcrm.com/crm/SPL" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AFL-2.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AFL-2.1.json", + "referenceNumber": 252, + "name": "Academic Free License v2.1", + "licenseId": "AFL-2.1", + "seeAlso": [ + "http://opensource.linux-mirror.org/licenses/afl-2.1.txt" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0-only.json", + "referenceNumber": 253, + "name": "GNU General Public License v2.0 only", + "licenseId": "GPL-2.0-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html", + "https://opensource.org/licenses/GPL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.3-invariants-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.3-invariants-only.json", + "referenceNumber": 254, + "name": "GNU Free Documentation License v1.3 only - invariants", + "licenseId": "GFDL-1.3-invariants-only", + "seeAlso": [ + "https://www.gnu.org/licenses/fdl-1.3.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/TORQUE-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/TORQUE-1.1.json", + "referenceNumber": 255, + "name": "TORQUE v2.5+ Software License v1.1", + "licenseId": "TORQUE-1.1", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/TORQUEv1.1" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Ruby.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Ruby.json", + "referenceNumber": 256, + "name": "Ruby License", + "licenseId": "Ruby", + "seeAlso": [ + "http://www.ruby-lang.org/en/LICENSE.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/X11.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/X11.json", + "referenceNumber": 257, + "name": "X11 License", + "licenseId": "X11", + "seeAlso": [ + "http://www.xfree86.org/3.3.6/COPYRIGHT2.html#3" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Borceux.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Borceux.json", + "referenceNumber": 258, + "name": "Borceux license", + "licenseId": "Borceux", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Borceux" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Libpng.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Libpng.json", + "referenceNumber": 259, + "name": "libpng License", + "licenseId": "Libpng", + "seeAlso": [ + "http://www.libpng.org/pub/png/src/libpng-LICENSE.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/X11-distribute-modifications-variant.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/X11-distribute-modifications-variant.json", + "referenceNumber": 260, + "name": "X11 License Distribution Modification Variant", + "licenseId": "X11-distribute-modifications-variant", + "seeAlso": [ + "https://github.com/mirror/ncurses/blob/master/COPYING" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Frameworx-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Frameworx-1.0.json", + "referenceNumber": 261, + "name": "Frameworx Open License 1.0", + "licenseId": "Frameworx-1.0", + "seeAlso": [ + "https://opensource.org/licenses/Frameworx-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/NCGL-UK-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NCGL-UK-2.0.json", + "referenceNumber": 262, + "name": "Non-Commercial Government Licence", + "licenseId": "NCGL-UK-2.0", + "seeAlso": [ + "http://www.nationalarchives.gov.uk/doc/non-commercial-government-licence/version/2/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CECILL-2.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CECILL-2.1.json", + "referenceNumber": 263, + "name": "CeCILL Free Software License Agreement v2.1", + "licenseId": "CECILL-2.1", + "seeAlso": [ + "http://www.cecill.info/licences/Licence_CeCILL_V2.1-en.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-3.0-AT.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-3.0-AT.json", + "referenceNumber": 264, + "name": "Creative Commons Attribution 3.0 Austria", + "licenseId": "CC-BY-3.0-AT", + "seeAlso": [ + "https://creativecommons.org/licenses/by/3.0/at/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CNRI-Python.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CNRI-Python.json", + "referenceNumber": 265, + "name": "CNRI Python License", + "licenseId": "CNRI-Python", + "seeAlso": [ + "https://opensource.org/licenses/CNRI-Python" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/NCSA.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NCSA.json", + "referenceNumber": 266, + "name": "University of Illinois/NCSA Open Source License", + "licenseId": "NCSA", + "seeAlso": [ + "http://otm.illinois.edu/uiuc_openSource", + "https://opensource.org/licenses/NCSA" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/gSOAP-1.3b.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/gSOAP-1.3b.json", + "referenceNumber": 267, + "name": "gSOAP Public License v1.3b", + "licenseId": "gSOAP-1.3b", + "seeAlso": [ + "http://www.cs.fsu.edu/~engelen/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/EUPL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EUPL-1.1.json", + "referenceNumber": 268, + "name": "European Union Public License 1.1", + "licenseId": "EUPL-1.1", + "seeAlso": [ + "https://joinup.ec.europa.eu/software/page/eupl/licence-eupl", + "https://joinup.ec.europa.eu/sites/default/files/custom-page/attachment/eupl1.1.-licence-en_0.pdf", + "https://opensource.org/licenses/EUPL-1.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/AMDPLPA.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AMDPLPA.json", + "referenceNumber": 269, + "name": "AMD\u0027s plpa_map.c License", + "licenseId": "AMDPLPA", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/AMD_plpa_map_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Imlib2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Imlib2.json", + "referenceNumber": 270, + "name": "Imlib2 License", + "licenseId": "Imlib2", + "seeAlso": [ + "http://trac.enlightenment.org/e/browser/trunk/imlib2/COPYING", + "https://git.enlightenment.org/legacy/imlib2.git/tree/COPYING" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CDDL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CDDL-1.1.json", + "referenceNumber": 271, + "name": "Common Development and Distribution License 1.1", + "licenseId": "CDDL-1.1", + "seeAlso": [ + "http://glassfish.java.net/public/CDDL+GPL_1_1.html", + "https://javaee.github.io/glassfish/LICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/WTFPL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/WTFPL.json", + "referenceNumber": 272, + "name": "Do What The F*ck You Want To Public License", + "licenseId": "WTFPL", + "seeAlso": [ + "http://www.wtfpl.net/about/", + "http://sam.zoy.org/wtfpl/COPYING" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LPL-1.0.json", + "referenceNumber": 273, + "name": "Lucent Public License Version 1.0", + "licenseId": "LPL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/LPL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/EPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EPL-1.0.json", + "referenceNumber": 274, + "name": "Eclipse Public License 1.0", + "licenseId": "EPL-1.0", + "seeAlso": [ + "http://www.eclipse.org/legal/epl-v10.html", + "https://opensource.org/licenses/EPL-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-Attribution.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-Attribution.json", + "referenceNumber": 275, + "name": "BSD with attribution", + "licenseId": "BSD-3-Clause-Attribution", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/BSD_with_Attribution" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OSL-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OSL-3.0.json", + "referenceNumber": 276, + "name": "Open Software License 3.0", + "licenseId": "OSL-3.0", + "seeAlso": [ + "https://web.archive.org/web/20120101081418/http://rosenlaw.com:80/OSL3.0.htm", + "https://opensource.org/licenses/OSL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/RHeCos-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/RHeCos-1.1.json", + "referenceNumber": 277, + "name": "Red Hat eCos Public License v1.1", + "licenseId": "RHeCos-1.1", + "seeAlso": [ + "http://ecos.sourceware.org/old-license.html" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/PHP-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/PHP-3.0.json", + "referenceNumber": 278, + "name": "PHP License v3.0", + "licenseId": "PHP-3.0", + "seeAlso": [ + "http://www.php.net/license/3_0.txt", + "https://opensource.org/licenses/PHP-3.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/BSD-Protection.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-Protection.json", + "referenceNumber": 279, + "name": "BSD Protection License", + "licenseId": "BSD-Protection", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/BSD_Protection_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-3.0-DE.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-3.0-DE.json", + "referenceNumber": 280, + "name": "Creative Commons Attribution Non Commercial 3.0 Germany", + "licenseId": "CC-BY-NC-3.0-DE", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc/3.0/de/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/APL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/APL-1.0.json", + "referenceNumber": 281, + "name": "Adaptive Public License 1.0", + "licenseId": "APL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/APL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/EUDatagrid.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EUDatagrid.json", + "referenceNumber": 282, + "name": "EU DataGrid Software License", + "licenseId": "EUDatagrid", + "seeAlso": [ + "http://eu-datagrid.web.cern.ch/eu-datagrid/license.html", + "https://opensource.org/licenses/EUDatagrid" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-1.0.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-1.0.json", + "referenceNumber": 283, + "name": "GNU General Public License v1.0 only", + "licenseId": "GPL-1.0", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/gpl-1.0-standalone.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SHL-0.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SHL-0.5.json", + "referenceNumber": 284, + "name": "Solderpad Hardware License v0.5", + "licenseId": "SHL-0.5", + "seeAlso": [ + "https://solderpad.org/licenses/SHL-0.5/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-2.0.json", + "referenceNumber": 285, + "name": "Creative Commons Attribution Share Alike 2.0 Generic", + "licenseId": "CC-BY-SA-2.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/2.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-3.0-AT.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-3.0-AT.json", + "referenceNumber": 286, + "name": "Creative Commons Attribution Share Alike 3.0 Austria", + "licenseId": "CC-BY-SA-3.0-AT", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/3.0/at/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-3.0-IGO.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-3.0-IGO.json", + "referenceNumber": 287, + "name": "Creative Commons Attribution Non Commercial Share Alike 3.0 IGO", + "licenseId": "CC-BY-NC-SA-3.0-IGO", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/3.0/igo/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Adobe-2006.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Adobe-2006.json", + "referenceNumber": 288, + "name": "Adobe Systems Incorporated Source Code License Agreement", + "licenseId": "Adobe-2006", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/AdobeLicense" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Newsletr.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Newsletr.json", + "referenceNumber": 289, + "name": "Newsletr License", + "licenseId": "Newsletr", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Newsletr" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Nunit.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/Nunit.json", + "referenceNumber": 290, + "name": "Nunit License", + "licenseId": "Nunit", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Nunit" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Multics.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Multics.json", + "referenceNumber": 291, + "name": "Multics License", + "licenseId": "Multics", + "seeAlso": [ + "https://opensource.org/licenses/Multics" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OGL-UK-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OGL-UK-1.0.json", + "referenceNumber": 292, + "name": "Open Government Licence v1.0", + "licenseId": "OGL-UK-1.0", + "seeAlso": [ + "http://www.nationalarchives.gov.uk/doc/open-government-licence/version/1/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Vim.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Vim.json", + "referenceNumber": 293, + "name": "Vim License", + "licenseId": "Vim", + "seeAlso": [ + "http://vimdoc.sourceforge.net/htmldoc/uganda.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/eCos-2.0.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/eCos-2.0.json", + "referenceNumber": 294, + "name": "eCos license version 2.0", + "licenseId": "eCos-2.0", + "seeAlso": [ + "https://www.gnu.org/licenses/ecos-license.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Zimbra-1.3.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Zimbra-1.3.json", + "referenceNumber": 295, + "name": "Zimbra Public License v1.3", + "licenseId": "Zimbra-1.3", + "seeAlso": [ + "http://web.archive.org/web/20100302225219/http://www.zimbra.com/license/zimbra-public-license-1-3.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/eGenix.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/eGenix.json", + "referenceNumber": 296, + "name": "eGenix.com Public License 1.1.0", + "licenseId": "eGenix", + "seeAlso": [ + "http://www.egenix.com/products/eGenix.com-Public-License-1.1.0.pdf", + "https://fedoraproject.org/wiki/Licensing/eGenix.com_Public_License_1.1.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/IBM-pibs.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/IBM-pibs.json", + "referenceNumber": 297, + "name": "IBM PowerPC Initialization and Boot Software", + "licenseId": "IBM-pibs", + "seeAlso": [ + "http://git.denx.de/?p\u003du-boot.git;a\u003dblob;f\u003darch/powerpc/cpu/ppc4xx/miiphy.c;h\u003d297155fdafa064b955e53e9832de93bfb0cfb85b;hb\u003d9fab4bf4cc077c21e43941866f3f2c196f28670d" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BitTorrent-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BitTorrent-1.1.json", + "referenceNumber": 298, + "name": "BitTorrent Open Source License v1.1", + "licenseId": "BitTorrent-1.1", + "seeAlso": [ + "http://directory.fsf.org/wiki/License:BitTorrentOSL1.1" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OFL-1.1-no-RFN.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OFL-1.1-no-RFN.json", + "referenceNumber": 299, + "name": "SIL Open Font License 1.1 with no Reserved Font Name", + "licenseId": "OFL-1.1-no-RFN", + "seeAlso": [ + "http://scripts.sil.org/cms/scripts/page.php?item_id\u003dOFL_web", + "https://opensource.org/licenses/OFL-1.1" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/psfrag.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/psfrag.json", + "referenceNumber": 300, + "name": "psfrag License", + "licenseId": "psfrag", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/psfrag" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-ND-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-ND-2.0.json", + "referenceNumber": 301, + "name": "Creative Commons Attribution No Derivatives 2.0 Generic", + "licenseId": "CC-BY-ND-2.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nd/2.0/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/SHL-0.51.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SHL-0.51.json", + "referenceNumber": 302, + "name": "Solderpad Hardware License, Version 0.51", + "licenseId": "SHL-0.51", + "seeAlso": [ + "https://solderpad.org/licenses/SHL-0.51/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/FreeBSD-DOC.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/FreeBSD-DOC.json", + "referenceNumber": 303, + "name": "FreeBSD Documentation License", + "licenseId": "FreeBSD-DOC", + "seeAlso": [ + "https://www.freebsd.org/copyright/freebsd-doc-license/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Python-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Python-2.0.json", + "referenceNumber": 304, + "name": "Python License 2.0", + "licenseId": "Python-2.0", + "seeAlso": [ + "https://opensource.org/licenses/Python-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Mup.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Mup.json", + "referenceNumber": 305, + "name": "Mup License", + "licenseId": "Mup", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Mup" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-4-Clause-Shortened.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-4-Clause-Shortened.json", + "referenceNumber": 306, + "name": "BSD 4 Clause Shortened", + "licenseId": "BSD-4-Clause-Shortened", + "seeAlso": [ + "https://metadata.ftp-master.debian.org/changelogs//main/a/arpwatch/arpwatch_2.1a15-7_copyright" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-4.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-4.0.json", + "referenceNumber": 307, + "name": "Creative Commons Attribution Non Commercial Share Alike 4.0 International", + "licenseId": "CC-BY-NC-SA-4.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/4.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/HPND.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/HPND.json", + "referenceNumber": 308, + "name": "Historical Permission Notice and Disclaimer", + "licenseId": "HPND", + "seeAlso": [ + "https://opensource.org/licenses/HPND" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.6.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.6.json", + "referenceNumber": 309, + "name": "Open LDAP Public License v2.6", + "licenseId": "OLDAP-2.6", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003d1cae062821881f41b73012ba816434897abf4205" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MPL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MPL-1.1.json", + "referenceNumber": 310, + "name": "Mozilla Public License 1.1", + "licenseId": "MPL-1.1", + "seeAlso": [ + "http://www.mozilla.org/MPL/MPL-1.1.html", + "https://opensource.org/licenses/MPL-1.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0-with-GCC-exception.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0-with-GCC-exception.json", + "referenceNumber": 311, + "name": "GNU General Public License v2.0 w/GCC Runtime Library exception", + "licenseId": "GPL-2.0-with-GCC-exception", + "seeAlso": [ + "https://gcc.gnu.org/git/?p\u003dgcc.git;a\u003dblob;f\u003dgcc/libgcc1.c;h\u003d762f5143fc6eed57b6797c82710f3538aa52b40b;hb\u003dcb143a3ce4fb417c68f5fa2691a1b1b1053dfba9#l10" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/HaskellReport.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/HaskellReport.json", + "referenceNumber": 312, + "name": "Haskell Language Report License", + "licenseId": "HaskellReport", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Haskell_Language_Report_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ECL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ECL-1.0.json", + "referenceNumber": 313, + "name": "Educational Community License v1.0", + "licenseId": "ECL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/ECL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/LGPL-2.1-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LGPL-2.1-or-later.json", + "referenceNumber": 314, + "name": "GNU Lesser General Public License v2.1 or later", + "licenseId": "LGPL-2.1-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/lgpl-2.1-standalone.html", + "https://opensource.org/licenses/LGPL-2.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OFL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OFL-1.0.json", + "referenceNumber": 315, + "name": "SIL Open Font License 1.0", + "licenseId": "OFL-1.0", + "seeAlso": [ + "http://scripts.sil.org/cms/scripts/page.php?item_id\u003dOFL10_web" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/APSL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/APSL-1.1.json", + "referenceNumber": 316, + "name": "Apple Public Source License 1.1", + "licenseId": "APSL-1.1", + "seeAlso": [ + "http://www.opensource.apple.com/source/IOSerialFamily/IOSerialFamily-7/APPLE_LICENSE" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/MITNFA.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MITNFA.json", + "referenceNumber": 317, + "name": "MIT +no-false-attribs license", + "licenseId": "MITNFA", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/MITNFA" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CECILL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CECILL-2.0.json", + "referenceNumber": 318, + "name": "CeCILL Free Software License Agreement v2.0", + "licenseId": "CECILL-2.0", + "seeAlso": [ + "http://www.cecill.info/licences/Licence_CeCILL_V2-en.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Crossword.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Crossword.json", + "referenceNumber": 319, + "name": "Crossword License", + "licenseId": "Crossword", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Crossword" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Aladdin.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Aladdin.json", + "referenceNumber": 320, + "name": "Aladdin Free Public License", + "licenseId": "Aladdin", + "seeAlso": [ + "http://pages.cs.wisc.edu/~ghost/doc/AFPL/6.01/Public.htm" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/Baekmuk.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Baekmuk.json", + "referenceNumber": 321, + "name": "Baekmuk License", + "licenseId": "Baekmuk", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing:Baekmuk?rd\u003dLicensing/Baekmuk" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/XFree86-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/XFree86-1.1.json", + "referenceNumber": 322, + "name": "XFree86 License 1.1", + "licenseId": "XFree86-1.1", + "seeAlso": [ + "http://www.xfree86.org/current/LICENSE4.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-1.0-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GPL-1.0-or-later.json", + "referenceNumber": 323, + "name": "GNU General Public License v1.0 or later", + "licenseId": "GPL-1.0-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/gpl-1.0-standalone.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CERN-OHL-W-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CERN-OHL-W-2.0.json", + "referenceNumber": 324, + "name": "CERN Open Hardware Licence Version 2 - Weakly Reciprocal", + "licenseId": "CERN-OHL-W-2.0", + "seeAlso": [ + "https://www.ohwr.org/project/cernohl/wikis/Documents/CERN-OHL-version-2" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-1.0.json", + "referenceNumber": 325, + "name": "Creative Commons Attribution Share Alike 1.0 Generic", + "licenseId": "CC-BY-SA-1.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/1.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NTP.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NTP.json", + "referenceNumber": 326, + "name": "NTP License", + "licenseId": "NTP", + "seeAlso": [ + "https://opensource.org/licenses/NTP" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/PHP-3.01.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/PHP-3.01.json", + "referenceNumber": 327, + "name": "PHP License v3.01", + "licenseId": "PHP-3.01", + "seeAlso": [ + "http://www.php.net/license/3_01.txt" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OCLC-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OCLC-2.0.json", + "referenceNumber": 328, + "name": "OCLC Research Public License 2.0", + "licenseId": "OCLC-2.0", + "seeAlso": [ + "http://www.oclc.org/research/activities/software/license/v2final.htm", + "https://opensource.org/licenses/OCLC-2.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-3.0-DE.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-3.0-DE.json", + "referenceNumber": 329, + "name": "Creative Commons Attribution 3.0 Germany", + "licenseId": "CC-BY-3.0-DE", + "seeAlso": [ + "https://creativecommons.org/licenses/by/3.0/de/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-2.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-2.5.json", + "referenceNumber": 330, + "name": "Creative Commons Attribution Non Commercial 2.5 Generic", + "licenseId": "CC-BY-NC-2.5", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc/2.5/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/Zlib.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Zlib.json", + "referenceNumber": 331, + "name": "zlib License", + "licenseId": "Zlib", + "seeAlso": [ + "http://www.zlib.net/zlib_license.html", + "https://opensource.org/licenses/Zlib" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CATOSL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CATOSL-1.1.json", + "referenceNumber": 332, + "name": "Computer Associates Trusted Open Source License 1.1", + "licenseId": "CATOSL-1.1", + "seeAlso": [ + "https://opensource.org/licenses/CATOSL-1.1" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/LGPL-3.0+.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/LGPL-3.0+.json", + "referenceNumber": 333, + "name": "GNU Lesser General Public License v3.0 or later", + "licenseId": "LGPL-3.0+", + "seeAlso": [ + "https://www.gnu.org/licenses/lgpl-3.0-standalone.html", + "https://www.gnu.org/licenses/lgpl+gpl-3.0.txt", + "https://opensource.org/licenses/LGPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CAL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CAL-1.0.json", + "referenceNumber": 334, + "name": "Cryptographic Autonomy License 1.0", + "licenseId": "CAL-1.0", + "seeAlso": [ + "http://cryptographicautonomylicense.com/license-text.html", + "https://opensource.org/licenses/CAL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/NPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NPL-1.0.json", + "referenceNumber": 335, + "name": "Netscape Public License v1.0", + "licenseId": "NPL-1.0", + "seeAlso": [ + "http://www.mozilla.org/MPL/NPL/1.0/" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/SMLNJ.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SMLNJ.json", + "referenceNumber": 336, + "name": "Standard ML of New Jersey License", + "licenseId": "SMLNJ", + "seeAlso": [ + "https://www.smlnj.org/license.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0+.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0+.json", + "referenceNumber": 337, + "name": "GNU General Public License v2.0 or later", + "licenseId": "GPL-2.0+", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html", + "https://opensource.org/licenses/GPL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.5.json", + "referenceNumber": 338, + "name": "Open LDAP Public License v2.5", + "licenseId": "OLDAP-2.5", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003d6852b9d90022e8593c98205413380536b1b5a7cf" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/JasPer-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/JasPer-2.0.json", + "referenceNumber": 339, + "name": "JasPer License", + "licenseId": "JasPer-2.0", + "seeAlso": [ + "http://www.ece.uvic.ca/~mdadams/jasper/LICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0-or-later.json", + "referenceNumber": 340, + "name": "GNU General Public License v2.0 or later", + "licenseId": "GPL-2.0-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html", + "https://opensource.org/licenses/GPL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/BSD-2-Clause-Patent.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-2-Clause-Patent.json", + "referenceNumber": 341, + "name": "BSD-2-Clause Plus Patent License", + "licenseId": "BSD-2-Clause-Patent", + "seeAlso": [ + "https://opensource.org/licenses/BSDplusPatent" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/MS-RL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MS-RL.json", + "referenceNumber": 342, + "name": "Microsoft Reciprocal License", + "licenseId": "MS-RL", + "seeAlso": [ + "http://www.microsoft.com/opensource/licenses.mspx", + "https://opensource.org/licenses/MS-RL" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CUA-OPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CUA-OPL-1.0.json", + "referenceNumber": 343, + "name": "CUA Office Public License v1.0", + "licenseId": "CUA-OPL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/CUA-OPL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/IPA.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/IPA.json", + "referenceNumber": 344, + "name": "IPA Font License", + "licenseId": "IPA", + "seeAlso": [ + "https://opensource.org/licenses/IPA" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/NLPL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NLPL.json", + "referenceNumber": 345, + "name": "No Limit Public License", + "licenseId": "NLPL", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/NLPL" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/O-UDA-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/O-UDA-1.0.json", + "referenceNumber": 346, + "name": "Open Use of Data Agreement v1.0", + "licenseId": "O-UDA-1.0", + "seeAlso": [ + "https://github.com/microsoft/Open-Use-of-Data-Agreement/blob/v1.0/O-UDA-1.0.md", + "https://cdla.dev/open-use-of-data-agreement-v1-0/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MIT-Modern-Variant.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MIT-Modern-Variant.json", + "referenceNumber": 347, + "name": "MIT License Modern Variant", + "licenseId": "MIT-Modern-Variant", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing:MIT#Modern_Variants", + "https://ptolemy.berkeley.edu/copyright.htm", + "https://pirlwww.lpl.arizona.edu/resources/guide/software/PerlTk/Tixlic.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OLDAP-1.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-1.2.json", + "referenceNumber": 348, + "name": "Open LDAP Public License v1.2", + "licenseId": "OLDAP-1.2", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003d42b0383c50c299977b5893ee695cf4e486fb0dc7" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-2-Clause-FreeBSD.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/BSD-2-Clause-FreeBSD.json", + "referenceNumber": 349, + "name": "BSD 2-Clause FreeBSD License", + "licenseId": "BSD-2-Clause-FreeBSD", + "seeAlso": [ + "http://www.freebsd.org/copyright/freebsd-license.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Info-ZIP.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Info-ZIP.json", + "referenceNumber": 350, + "name": "Info-ZIP License", + "licenseId": "Info-ZIP", + "seeAlso": [ + "http://www.info-zip.org/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-2.0-FR.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-2.0-FR.json", + "referenceNumber": 351, + "name": "Creative Commons Attribution-NonCommercial-ShareAlike 2.0 France", + "licenseId": "CC-BY-NC-SA-2.0-FR", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/2.0/fr/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/0BSD.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/0BSD.json", + "referenceNumber": 352, + "name": "BSD Zero Clause License", + "licenseId": "0BSD", + "seeAlso": [ + "http://landley.net/toybox/license.html", + "https://opensource.org/licenses/0BSD" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/Unicode-DFS-2016.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Unicode-DFS-2016.json", + "referenceNumber": 353, + "name": "Unicode License Agreement - Data Files and Software (2016)", + "licenseId": "Unicode-DFS-2016", + "seeAlso": [ + "http://www.unicode.org/copyright.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OFL-1.0-RFN.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OFL-1.0-RFN.json", + "referenceNumber": 354, + "name": "SIL Open Font License 1.0 with Reserved Font Name", + "licenseId": "OFL-1.0-RFN", + "seeAlso": [ + "http://scripts.sil.org/cms/scripts/page.php?item_id\u003dOFL10_web" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Intel.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Intel.json", + "referenceNumber": 355, + "name": "Intel Open Source License", + "licenseId": "Intel", + "seeAlso": [ + "https://opensource.org/licenses/Intel" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/AFL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AFL-2.0.json", + "referenceNumber": 356, + "name": "Academic Free License v2.0", + "licenseId": "AFL-2.0", + "seeAlso": [ + "http://wayback.archive.org/web/20060924134533/http://www.opensource.org/licenses/afl-2.0.txt" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GL2PS.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GL2PS.json", + "referenceNumber": 357, + "name": "GL2PS License", + "licenseId": "GL2PS", + "seeAlso": [ + "http://www.geuz.org/gl2ps/COPYING.GL2PS" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/TAPR-OHL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/TAPR-OHL-1.0.json", + "referenceNumber": 358, + "name": "TAPR Open Hardware License v1.0", + "licenseId": "TAPR-OHL-1.0", + "seeAlso": [ + "https://www.tapr.org/OHL" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Apache-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Apache-1.0.json", + "referenceNumber": 359, + "name": "Apache License 1.0", + "licenseId": "Apache-1.0", + "seeAlso": [ + "http://www.apache.org/licenses/LICENSE-1.0" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/MTLL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MTLL.json", + "referenceNumber": 360, + "name": "Matrix Template Library License", + "licenseId": "MTLL", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Matrix_Template_Library_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Motosoto.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Motosoto.json", + "referenceNumber": 361, + "name": "Motosoto License", + "licenseId": "Motosoto", + "seeAlso": [ + "https://opensource.org/licenses/Motosoto" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/RSA-MD.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/RSA-MD.json", + "referenceNumber": 362, + "name": "RSA Message-Digest License", + "licenseId": "RSA-MD", + "seeAlso": [ + "http://www.faqs.org/rfcs/rfc1321.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Community-Spec-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Community-Spec-1.0.json", + "referenceNumber": 363, + "name": "Community Specification License 1.0", + "licenseId": "Community-Spec-1.0", + "seeAlso": [ + "https://github.com/CommunitySpecification/1.0/blob/master/1._Community_Specification_License-v1.md" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ODC-By-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ODC-By-1.0.json", + "referenceNumber": 364, + "name": "Open Data Commons Attribution License v1.0", + "licenseId": "ODC-By-1.0", + "seeAlso": [ + "https://opendatacommons.org/licenses/by/1.0/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/zlib-acknowledgement.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/zlib-acknowledgement.json", + "referenceNumber": 365, + "name": "zlib/libpng License with Acknowledgement", + "licenseId": "zlib-acknowledgement", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/ZlibWithAcknowledgement" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/DL-DE-BY-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/DL-DE-BY-2.0.json", + "referenceNumber": 366, + "name": "Data licence Germany – attribution – version 2.0", + "licenseId": "DL-DE-BY-2.0", + "seeAlso": [ + "https://www.govdata.de/dl-de/by-2-0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/VSL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/VSL-1.0.json", + "referenceNumber": 367, + "name": "Vovida Software License v1.0", + "licenseId": "VSL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/VSL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/LiLiQ-R-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LiLiQ-R-1.1.json", + "referenceNumber": 368, + "name": "Licence Libre du Québec – Réciprocité version 1.1", + "licenseId": "LiLiQ-R-1.1", + "seeAlso": [ + "https://www.forge.gouv.qc.ca/participez/licence-logicielle/licence-libre-du-quebec-liliq-en-francais/licence-libre-du-quebec-reciprocite-liliq-r-v1-1/", + "http://opensource.org/licenses/LiLiQ-R-1.1" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OPL-1.0.json", + "referenceNumber": 369, + "name": "Open Public License v1.0", + "licenseId": "OPL-1.0", + "seeAlso": [ + "http://old.koalateam.com/jackaroo/OPL_1_0.TXT", + "https://fedoraproject.org/wiki/Licensing/Open_Public_License" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/GPL-3.0+.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-3.0+.json", + "referenceNumber": 370, + "name": "GNU General Public License v3.0 or later", + "licenseId": "GPL-3.0+", + "seeAlso": [ + "https://www.gnu.org/licenses/gpl-3.0-standalone.html", + "https://opensource.org/licenses/GPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/MulanPSL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MulanPSL-2.0.json", + "referenceNumber": 371, + "name": "Mulan Permissive Software License, Version 2", + "licenseId": "MulanPSL-2.0", + "seeAlso": [ + "https://license.coscl.org.cn/MulanPSL2/" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/APSL-1.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/APSL-1.2.json", + "referenceNumber": 372, + "name": "Apple Public Source License 1.2", + "licenseId": "APSL-1.2", + "seeAlso": [ + "http://www.samurajdata.se/opensource/mirror/licenses/apsl.php" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OGDL-Taiwan-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OGDL-Taiwan-1.0.json", + "referenceNumber": 373, + "name": "Taiwan Open Government Data License, version 1.0", + "licenseId": "OGDL-Taiwan-1.0", + "seeAlso": [ + "https://data.gov.tw/license" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/RSCPL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/RSCPL.json", + "referenceNumber": 374, + "name": "Ricoh Source Code Public License", + "licenseId": "RSCPL", + "seeAlso": [ + "http://wayback.archive.org/web/20060715140826/http://www.risource.org/RPL/RPL-1.0A.shtml", + "https://opensource.org/licenses/RSCPL" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OGC-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OGC-1.0.json", + "referenceNumber": 375, + "name": "OGC Software License, Version 1.0", + "licenseId": "OGC-1.0", + "seeAlso": [ + "https://www.ogc.org/ogc/software/1.0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/EFL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EFL-2.0.json", + "referenceNumber": 376, + "name": "Eiffel Forum License v2.0", + "licenseId": "EFL-2.0", + "seeAlso": [ + "http://www.eiffel-nice.org/license/eiffel-forum-license-2.html", + "https://opensource.org/licenses/EFL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CAL-1.0-Combined-Work-Exception.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CAL-1.0-Combined-Work-Exception.json", + "referenceNumber": 377, + "name": "Cryptographic Autonomy License 1.0 (Combined Work Exception)", + "licenseId": "CAL-1.0-Combined-Work-Exception", + "seeAlso": [ + "http://cryptographicautonomylicense.com/license-text.html", + "https://opensource.org/licenses/CAL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/MS-PL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MS-PL.json", + "referenceNumber": 378, + "name": "Microsoft Public License", + "licenseId": "MS-PL", + "seeAlso": [ + "http://www.microsoft.com/opensource/licenses.mspx", + "https://opensource.org/licenses/MS-PL" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Plexus.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Plexus.json", + "referenceNumber": 379, + "name": "Plexus Classworlds License", + "licenseId": "Plexus", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Plexus_Classworlds_License" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Sendmail-8.23.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Sendmail-8.23.json", + "referenceNumber": 380, + "name": "Sendmail License 8.23", + "licenseId": "Sendmail-8.23", + "seeAlso": [ + "https://www.proofpoint.com/sites/default/files/sendmail-license.pdf", + "https://web.archive.org/web/20181003101040/https://www.proofpoint.com/sites/default/files/sendmail-license.pdf" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Cube.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Cube.json", + "referenceNumber": 381, + "name": "Cube License", + "licenseId": "Cube", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Cube" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/JSON.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/JSON.json", + "referenceNumber": 382, + "name": "JSON License", + "licenseId": "JSON", + "seeAlso": [ + "http://www.json.org/license.html" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/EUPL-1.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EUPL-1.2.json", + "referenceNumber": 383, + "name": "European Union Public License 1.2", + "licenseId": "EUPL-1.2", + "seeAlso": [ + "https://joinup.ec.europa.eu/page/eupl-text-11-12", + "https://joinup.ec.europa.eu/sites/default/files/custom-page/attachment/eupl_v1.2_en.pdf", + "https://joinup.ec.europa.eu/sites/default/files/custom-page/attachment/2020-03/EUPL-1.2%20EN.txt", + "https://joinup.ec.europa.eu/sites/default/files/inline-files/EUPL%20v1_2%20EN(1).txt", + "http://eur-lex.europa.eu/legal-content/EN/TXT/HTML/?uri\u003dCELEX:32017D0863", + "https://opensource.org/licenses/EUPL-1.2" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Adobe-Glyph.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Adobe-Glyph.json", + "referenceNumber": 384, + "name": "Adobe Glyph List License", + "licenseId": "Adobe-Glyph", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/MIT#AdobeGlyph" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/FreeImage.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/FreeImage.json", + "referenceNumber": 385, + "name": "FreeImage Public License v1.0", + "licenseId": "FreeImage", + "seeAlso": [ + "http://freeimage.sourceforge.net/freeimage-license.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Watcom-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Watcom-1.0.json", + "referenceNumber": 386, + "name": "Sybase Open Watcom Public License 1.0", + "licenseId": "Watcom-1.0", + "seeAlso": [ + "https://opensource.org/licenses/Watcom-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/Jam.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Jam.json", + "referenceNumber": 387, + "name": "Jam License", + "licenseId": "Jam", + "seeAlso": [ + "https://www.boost.org/doc/libs/1_35_0/doc/html/jam.html", + "https://web.archive.org/web/20160330173339/https://swarm.workshop.perforce.com/files/guest/perforce_software/jam/src/README" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/Hippocratic-2.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Hippocratic-2.1.json", + "referenceNumber": 388, + "name": "Hippocratic License 2.1", + "licenseId": "Hippocratic-2.1", + "seeAlso": [ + "https://firstdonoharm.dev/version/2/1/license.html", + "https://github.com/EthicalSource/hippocratic-license/blob/58c0e646d64ff6fbee275bfe2b9492f914e3ab2a/LICENSE.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.0.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.0.1.json", + "referenceNumber": 389, + "name": "Open LDAP Public License v2.0.1", + "licenseId": "OLDAP-2.0.1", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003db6d68acd14e51ca3aab4428bf26522aa74873f0e" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-SA-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-SA-2.0.json", + "referenceNumber": 390, + "name": "Creative Commons Attribution Non Commercial Share Alike 2.0 Generic", + "licenseId": "CC-BY-NC-SA-2.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-sa/2.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Nokia.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Nokia.json", + "referenceNumber": 391, + "name": "Nokia Open Source License", + "licenseId": "Nokia", + "seeAlso": [ + "https://opensource.org/licenses/nokia" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OCCT-PL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OCCT-PL.json", + "referenceNumber": 392, + "name": "Open CASCADE Technology Public License", + "licenseId": "OCCT-PL", + "seeAlso": [ + "http://www.opencascade.com/content/occt-public-license" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ErlPL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ErlPL-1.1.json", + "referenceNumber": 393, + "name": "Erlang Public License v1.1", + "licenseId": "ErlPL-1.1", + "seeAlso": [ + "http://www.erlang.org/EPLICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/TOSL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/TOSL.json", + "referenceNumber": 394, + "name": "Trusster Open Source License", + "licenseId": "TOSL", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/TOSL" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OSL-2.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OSL-2.1.json", + "referenceNumber": 395, + "name": "Open Software License 2.1", + "licenseId": "OSL-2.1", + "seeAlso": [ + "http://web.archive.org/web/20050212003940/http://www.rosenlaw.com/osl21.htm", + "https://opensource.org/licenses/OSL-2.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/ClArtistic.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ClArtistic.json", + "referenceNumber": 396, + "name": "Clarified Artistic License", + "licenseId": "ClArtistic", + "seeAlso": [ + "http://gianluca.dellavedova.org/2011/01/03/clarified-artistic-license/", + "http://www.ncftp.com/ncftp/doc/LICENSE.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/xinetd.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/xinetd.json", + "referenceNumber": 397, + "name": "xinetd License", + "licenseId": "xinetd", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Xinetd_License" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-3.0-with-GCC-exception.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-3.0-with-GCC-exception.json", + "referenceNumber": 398, + "name": "GNU General Public License v3.0 w/GCC Runtime Library exception", + "licenseId": "GPL-3.0-with-GCC-exception", + "seeAlso": [ + "https://www.gnu.org/licenses/gcc-exception-3.1.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/ODbL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ODbL-1.0.json", + "referenceNumber": 399, + "name": "Open Data Commons Open Database License v1.0", + "licenseId": "ODbL-1.0", + "seeAlso": [ + "http://www.opendatacommons.org/licenses/odbl/1.0/", + "https://opendatacommons.org/licenses/odbl/1-0/" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/MIT.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MIT.json", + "referenceNumber": 400, + "name": "MIT License", + "licenseId": "MIT", + "seeAlso": [ + "https://opensource.org/licenses/MIT" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LGPL-2.1+.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/LGPL-2.1+.json", + "referenceNumber": 401, + "name": "GNU Library General Public License v2.1 or later", + "licenseId": "LGPL-2.1+", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/lgpl-2.1-standalone.html", + "https://opensource.org/licenses/LGPL-2.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LGPL-2.1-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LGPL-2.1-only.json", + "referenceNumber": 402, + "name": "GNU Lesser General Public License v2.1 only", + "licenseId": "LGPL-2.1-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/lgpl-2.1-standalone.html", + "https://opensource.org/licenses/LGPL-2.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CrystalStacker.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CrystalStacker.json", + "referenceNumber": 403, + "name": "CrystalStacker License", + "licenseId": "CrystalStacker", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing:CrystalStacker?rd\u003dLicensing/CrystalStacker" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ECL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ECL-2.0.json", + "referenceNumber": 404, + "name": "Educational Community License v2.0", + "licenseId": "ECL-2.0", + "seeAlso": [ + "https://opensource.org/licenses/ECL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LPPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LPPL-1.0.json", + "referenceNumber": 405, + "name": "LaTeX Project Public License v1.0", + "licenseId": "LPPL-1.0", + "seeAlso": [ + "http://www.latex-project.org/lppl/lppl-1-0.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/iMatix.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/iMatix.json", + "referenceNumber": 406, + "name": "iMatix Standard Function Library Agreement", + "licenseId": "iMatix", + "seeAlso": [ + "http://legacy.imatix.com/html/sfl/sfl4.htm#license" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-ND-3.0-IGO.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-ND-3.0-IGO.json", + "referenceNumber": 407, + "name": "Creative Commons Attribution Non Commercial No Derivatives 3.0 IGO", + "licenseId": "CC-BY-NC-ND-3.0-IGO", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-nd/3.0/igo/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-Source-Code.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-Source-Code.json", + "referenceNumber": 408, + "name": "BSD Source Code Attribution", + "licenseId": "BSD-Source-Code", + "seeAlso": [ + "https://github.com/robbiehanson/CocoaHTTPServer/blob/master/LICENSE.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Parity-6.0.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Parity-6.0.0.json", + "referenceNumber": 409, + "name": "The Parity Public License 6.0.0", + "licenseId": "Parity-6.0.0", + "seeAlso": [ + "https://paritylicense.com/versions/6.0.0.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/TCL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/TCL.json", + "referenceNumber": 410, + "name": "TCL/TK License", + "licenseId": "TCL", + "seeAlso": [ + "http://www.tcl.tk/software/tcltk/license.html", + "https://fedoraproject.org/wiki/Licensing/TCL" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Arphic-1999.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Arphic-1999.json", + "referenceNumber": 411, + "name": "Arphic Public License", + "licenseId": "Arphic-1999", + "seeAlso": [ + "http://ftp.gnu.org/gnu/non-gnu/chinese-fonts-truetype/LICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-SA-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-SA-3.0.json", + "referenceNumber": 412, + "name": "Creative Commons Attribution Share Alike 3.0 Unported", + "licenseId": "CC-BY-SA-3.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-sa/3.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Caldera.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Caldera.json", + "referenceNumber": 413, + "name": "Caldera License", + "licenseId": "Caldera", + "seeAlso": [ + "http://www.lemis.com/grog/UNIX/ancient-source-all.pdf" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AGPL-1.0.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/AGPL-1.0.json", + "referenceNumber": 414, + "name": "Affero General Public License v1.0", + "licenseId": "AGPL-1.0", + "seeAlso": [ + "http://www.affero.org/oagpl.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/IPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/IPL-1.0.json", + "referenceNumber": 415, + "name": "IBM Public License v1.0", + "licenseId": "IPL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/IPL-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LAL-1.3.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LAL-1.3.json", + "referenceNumber": 416, + "name": "Licence Art Libre 1.3", + "licenseId": "LAL-1.3", + "seeAlso": [ + "https://artlibre.org/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/EPICS.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EPICS.json", + "referenceNumber": 417, + "name": "EPICS Open License", + "licenseId": "EPICS", + "seeAlso": [ + "https://epics.anl.gov/license/open.php" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NGPL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NGPL.json", + "referenceNumber": 418, + "name": "Nethack General Public License", + "licenseId": "NGPL", + "seeAlso": [ + "https://opensource.org/licenses/NGPL" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/DRL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/DRL-1.0.json", + "referenceNumber": 419, + "name": "Detection Rule License 1.0", + "licenseId": "DRL-1.0", + "seeAlso": [ + "https://github.com/Neo23x0/sigma/blob/master/LICENSE.Detection.Rules.md" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-2-Clause-NetBSD.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/BSD-2-Clause-NetBSD.json", + "referenceNumber": 420, + "name": "BSD 2-Clause NetBSD License", + "licenseId": "BSD-2-Clause-NetBSD", + "seeAlso": [ + "http://www.netbsd.org/about/redistribution.html#default" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/ZPL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ZPL-1.1.json", + "referenceNumber": 421, + "name": "Zope Public License 1.1", + "licenseId": "ZPL-1.1", + "seeAlso": [ + "http://old.zope.org/Resources/License/ZPL-1.1" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GD.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GD.json", + "referenceNumber": 422, + "name": "GD License", + "licenseId": "GD", + "seeAlso": [ + "https://libgd.github.io/manuals/2.3.0/files/license-txt.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LPPL-1.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LPPL-1.2.json", + "referenceNumber": 423, + "name": "LaTeX Project Public License v1.2", + "licenseId": "LPPL-1.2", + "seeAlso": [ + "http://www.latex-project.org/lppl/lppl-1-2.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Dotseqn.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Dotseqn.json", + "referenceNumber": 424, + "name": "Dotseqn License", + "licenseId": "Dotseqn", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Dotseqn" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Spencer-99.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Spencer-99.json", + "referenceNumber": 425, + "name": "Spencer License 99", + "licenseId": "Spencer-99", + "seeAlso": [ + "http://www.opensource.apple.com/source/tcl/tcl-5/tcl/generic/regfronts.c" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.3.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.3.json", + "referenceNumber": 426, + "name": "Open LDAP Public License v2.3", + "licenseId": "OLDAP-2.3", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003dd32cf54a32d581ab475d23c810b0a7fbaf8d63c3" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/YPL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/YPL-1.1.json", + "referenceNumber": 427, + "name": "Yahoo! Public License v1.1", + "licenseId": "YPL-1.1", + "seeAlso": [ + "http://www.zimbra.com/license/yahoo_public_license_1.1.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Fair.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Fair.json", + "referenceNumber": 428, + "name": "Fair License", + "licenseId": "Fair", + "seeAlso": [ + "http://fairlicense.org/", + "https://opensource.org/licenses/Fair" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/Qhull.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Qhull.json", + "referenceNumber": 429, + "name": "Qhull License", + "licenseId": "Qhull", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Qhull" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.1-no-invariants-or-later.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.1-no-invariants-or-later.json", + "referenceNumber": 430, + "name": "GNU Free Documentation License v1.1 or later - no invariants", + "licenseId": "GFDL-1.1-no-invariants-or-later", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.1.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CECILL-C.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CECILL-C.json", + "referenceNumber": 431, + "name": "CeCILL-C Free Software License Agreement", + "licenseId": "CECILL-C", + "seeAlso": [ + "http://www.cecill.info/licences/Licence_CeCILL-C_V1-en.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/MulanPSL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MulanPSL-1.0.json", + "referenceNumber": 432, + "name": "Mulan Permissive Software License, Version 1", + "licenseId": "MulanPSL-1.0", + "seeAlso": [ + "https://license.coscl.org.cn/MulanPSL/", + "https://github.com/yuwenlong/longphp/blob/25dfb70cc2a466dc4bb55ba30901cbce08d164b5/LICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OLDAP-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-1.1.json", + "referenceNumber": 433, + "name": "Open LDAP Public License v1.1", + "licenseId": "OLDAP-1.1", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003d806557a5ad59804ef3a44d5abfbe91d706b0791f" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.1.json", + "referenceNumber": 434, + "name": "Open LDAP Public License v2.1", + "licenseId": "OLDAP-2.1", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003db0d176738e96a0d3b9f85cb51e140a86f21be715" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/LPL-1.02.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LPL-1.02.json", + "referenceNumber": 435, + "name": "Lucent Public License v1.02", + "licenseId": "LPL-1.02", + "seeAlso": [ + "http://plan9.bell-labs.com/plan9/license.html", + "https://opensource.org/licenses/LPL-1.02" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/UPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/UPL-1.0.json", + "referenceNumber": 436, + "name": "Universal Permissive License v1.0", + "licenseId": "UPL-1.0", + "seeAlso": [ + "https://opensource.org/licenses/UPL" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Abstyles.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Abstyles.json", + "referenceNumber": 437, + "name": "Abstyles License", + "licenseId": "Abstyles", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Abstyles" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/ZPL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ZPL-2.0.json", + "referenceNumber": 438, + "name": "Zope Public License 2.0", + "licenseId": "ZPL-2.0", + "seeAlso": [ + "http://old.zope.org/Resources/License/ZPL-2.0", + "https://opensource.org/licenses/ZPL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/MIT-0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MIT-0.json", + "referenceNumber": 439, + "name": "MIT No Attribution", + "licenseId": "MIT-0", + "seeAlso": [ + "https://github.com/aws/mit-0", + "https://romanrm.net/mit-zero", + "https://github.com/awsdocs/aws-cloud9-user-guide/blob/master/LICENSE-SAMPLECODE" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/LGPL-2.0-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LGPL-2.0-only.json", + "referenceNumber": 440, + "name": "GNU Library General Public License v2 only", + "licenseId": "LGPL-2.0-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/lgpl-2.0-standalone.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.3-no-invariants-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.3-no-invariants-only.json", + "referenceNumber": 441, + "name": "GNU Free Documentation License v1.3 only - no invariants", + "licenseId": "GFDL-1.3-no-invariants-only", + "seeAlso": [ + "https://www.gnu.org/licenses/fdl-1.3.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/AGPL-3.0.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/AGPL-3.0.json", + "referenceNumber": 442, + "name": "GNU Affero General Public License v3.0", + "licenseId": "AGPL-3.0", + "seeAlso": [ + "https://www.gnu.org/licenses/agpl.txt", + "https://opensource.org/licenses/AGPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/EPL-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/EPL-2.0.json", + "referenceNumber": 443, + "name": "Eclipse Public License 2.0", + "licenseId": "EPL-2.0", + "seeAlso": [ + "https://www.eclipse.org/legal/epl-2.0", + "https://www.opensource.org/licenses/EPL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/AFL-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/AFL-3.0.json", + "referenceNumber": 444, + "name": "Academic Free License v3.0", + "licenseId": "AFL-3.0", + "seeAlso": [ + "http://www.rosenlaw.com/AFL3.0.htm", + "https://opensource.org/licenses/afl-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/CDLA-Permissive-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CDLA-Permissive-1.0.json", + "referenceNumber": 445, + "name": "Community Data License Agreement Permissive 1.0", + "licenseId": "CDLA-Permissive-1.0", + "seeAlso": [ + "https://cdla.io/permissive-1-0" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Artistic-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Artistic-1.0.json", + "referenceNumber": 446, + "name": "Artistic License 1.0", + "licenseId": "Artistic-1.0", + "seeAlso": [ + "https://opensource.org/licenses/Artistic-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-NC-ND-4.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-NC-ND-4.0.json", + "referenceNumber": 447, + "name": "Creative Commons Attribution Non Commercial No Derivatives 4.0 International", + "licenseId": "CC-BY-NC-ND-4.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nc-nd/4.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/HTMLTIDY.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/HTMLTIDY.json", + "referenceNumber": 448, + "name": "HTML Tidy License", + "licenseId": "HTMLTIDY", + "seeAlso": [ + "https://github.com/htacg/tidy-html5/blob/next/README/LICENSE.md" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Glide.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Glide.json", + "referenceNumber": 449, + "name": "3dfx Glide License", + "licenseId": "Glide", + "seeAlso": [ + "http://www.users.on.net/~triforce/glidexp/COPYING.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/FSFAP.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/FSFAP.json", + "referenceNumber": 450, + "name": "FSF All Permissive License", + "licenseId": "FSFAP", + "seeAlso": [ + "https://www.gnu.org/prep/maintain/html_node/License-Notices-for-Other-Files.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LGPLLR.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/LGPLLR.json", + "referenceNumber": 451, + "name": "Lesser General Public License For Linguistic Resources", + "licenseId": "LGPLLR", + "seeAlso": [ + "http://www-igm.univ-mlv.fr/~unitex/lgpllr.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OGL-UK-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OGL-UK-3.0.json", + "referenceNumber": 452, + "name": "Open Government Licence v3.0", + "licenseId": "OGL-UK-3.0", + "seeAlso": [ + "http://www.nationalarchives.gov.uk/doc/open-government-licence/version/3/" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.2.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.2.json", + "referenceNumber": 453, + "name": "GNU Free Documentation License v1.2", + "licenseId": "GFDL-1.2", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.2.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/SSH-OpenSSH.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SSH-OpenSSH.json", + "referenceNumber": 454, + "name": "SSH OpenSSH license", + "licenseId": "SSH-OpenSSH", + "seeAlso": [ + "https://github.com/openssh/openssh-portable/blob/1b11ea7c58cd5c59838b5fa574cd456d6047b2d4/LICENCE#L10" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.1-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.1-only.json", + "referenceNumber": 455, + "name": "GNU Free Documentation License v1.1 only", + "licenseId": "GFDL-1.1-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.1.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/MIT-feh.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MIT-feh.json", + "referenceNumber": 456, + "name": "feh License", + "licenseId": "MIT-feh", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/MIT#feh" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/MPL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/MPL-1.0.json", + "referenceNumber": 457, + "name": "Mozilla Public License 1.0", + "licenseId": "MPL-1.0", + "seeAlso": [ + "http://www.mozilla.org/MPL/MPL-1.0.html", + "https://opensource.org/licenses/MPL-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/PostgreSQL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/PostgreSQL.json", + "referenceNumber": 458, + "name": "PostgreSQL License", + "licenseId": "PostgreSQL", + "seeAlso": [ + "http://www.postgresql.org/about/licence", + "https://opensource.org/licenses/PostgreSQL" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/OLDAP-2.2.2.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OLDAP-2.2.2.json", + "referenceNumber": 459, + "name": "Open LDAP Public License 2.2.2", + "licenseId": "OLDAP-2.2.2", + "seeAlso": [ + "http://www.openldap.org/devel/gitweb.cgi?p\u003dopenldap.git;a\u003dblob;f\u003dLICENSE;hb\u003ddf2cc1e21eb7c160695f5b7cffd6296c151ba188" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/SMPPL.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/SMPPL.json", + "referenceNumber": 460, + "name": "Secure Messaging Protocol Public License", + "licenseId": "SMPPL", + "seeAlso": [ + "https://github.com/dcblake/SMP/blob/master/Documentation/License.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/OFL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OFL-1.1.json", + "referenceNumber": 461, + "name": "SIL Open Font License 1.1", + "licenseId": "OFL-1.1", + "seeAlso": [ + "http://scripts.sil.org/cms/scripts/page.php?item_id\u003dOFL_web", + "https://opensource.org/licenses/OFL-1.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Leptonica.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Leptonica.json", + "referenceNumber": 462, + "name": "Leptonica License", + "licenseId": "Leptonica", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Leptonica" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CERN-OHL-1.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CERN-OHL-1.1.json", + "referenceNumber": 463, + "name": "CERN Open Hardware Licence v1.1", + "licenseId": "CERN-OHL-1.1", + "seeAlso": [ + "https://www.ohwr.org/project/licenses/wikis/cern-ohl-v1.1" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause-No-Nuclear-Warranty.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause-No-Nuclear-Warranty.json", + "referenceNumber": 464, + "name": "BSD 3-Clause No Nuclear Warranty", + "licenseId": "BSD-3-Clause-No-Nuclear-Warranty", + "seeAlso": [ + "https://jogamp.org/git/?p\u003dgluegen.git;a\u003dblob_plain;f\u003dLICENSE.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-ND-2.5.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-ND-2.5.json", + "referenceNumber": 465, + "name": "Creative Commons Attribution No Derivatives 2.5 Generic", + "licenseId": "CC-BY-ND-2.5", + "seeAlso": [ + "https://creativecommons.org/licenses/by-nd/2.5/legalcode" + ], + "isOsiApproved": false, + "isFsfLibre": false + }, + { + "reference": "https://spdx.org/licenses/CC-BY-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/CC-BY-1.0.json", + "referenceNumber": 466, + "name": "Creative Commons Attribution 1.0 Generic", + "licenseId": "CC-BY-1.0", + "seeAlso": [ + "https://creativecommons.org/licenses/by/1.0/legalcode" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GFDL-1.2-only.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/GFDL-1.2-only.json", + "referenceNumber": 467, + "name": "GNU Free Documentation License v1.2 only", + "licenseId": "GFDL-1.2-only", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/fdl-1.2.txt" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/OPUBL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/OPUBL-1.0.json", + "referenceNumber": 468, + "name": "Open Publication License v1.0", + "licenseId": "OPUBL-1.0", + "seeAlso": [ + "http://opencontent.org/openpub/", + "https://www.debian.org/opl", + "https://www.ctan.org/license/opl" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/libselinux-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/libselinux-1.0.json", + "referenceNumber": 469, + "name": "libselinux public domain notice", + "licenseId": "libselinux-1.0", + "seeAlso": [ + "https://github.com/SELinuxProject/selinux/blob/master/libselinux/LICENSE" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSD-3-Clause.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-3-Clause.json", + "referenceNumber": 470, + "name": "BSD 3-Clause \"New\" or \"Revised\" License", + "licenseId": "BSD-3-Clause", + "seeAlso": [ + "https://opensource.org/licenses/BSD-3-Clause" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/ANTLR-PD-fallback.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/ANTLR-PD-fallback.json", + "referenceNumber": 471, + "name": "ANTLR Software Rights Notice with license fallback", + "licenseId": "ANTLR-PD-fallback", + "seeAlso": [ + "http://www.antlr2.org/license.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/copyleft-next-0.3.1.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/copyleft-next-0.3.1.json", + "referenceNumber": 472, + "name": "copyleft-next 0.3.1", + "licenseId": "copyleft-next-0.3.1", + "seeAlso": [ + "https://github.com/copyleft-next/copyleft-next/blob/master/Releases/copyleft-next-0.3.1" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/GPL-1.0+.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-1.0+.json", + "referenceNumber": 473, + "name": "GNU General Public License v1.0 or later", + "licenseId": "GPL-1.0+", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/gpl-1.0-standalone.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/wxWindows.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/wxWindows.json", + "referenceNumber": 474, + "name": "wxWindows Library License", + "licenseId": "wxWindows", + "seeAlso": [ + "https://opensource.org/licenses/WXwindows" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/LGPL-3.0.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/LGPL-3.0.json", + "referenceNumber": 475, + "name": "GNU Lesser General Public License v3.0 only", + "licenseId": "LGPL-3.0", + "seeAlso": [ + "https://www.gnu.org/licenses/lgpl-3.0-standalone.html", + "https://www.gnu.org/licenses/lgpl+gpl-3.0.txt", + "https://opensource.org/licenses/LGPL-3.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/LGPL-2.1.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/LGPL-2.1.json", + "referenceNumber": 476, + "name": "GNU Lesser General Public License v2.1 only", + "licenseId": "LGPL-2.1", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/lgpl-2.1-standalone.html", + "https://opensource.org/licenses/LGPL-2.1" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/StandardML-NJ.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/StandardML-NJ.json", + "referenceNumber": 477, + "name": "Standard ML of New Jersey License", + "licenseId": "StandardML-NJ", + "seeAlso": [ + "http://www.smlnj.org//license.html" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/BSD-4-Clause.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-4-Clause.json", + "referenceNumber": 478, + "name": "BSD 4-Clause \"Original\" or \"Old\" License", + "licenseId": "BSD-4-Clause", + "seeAlso": [ + "http://directory.fsf.org/wiki/License:BSD_4Clause" + ], + "isOsiApproved": false, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0-with-bison-exception.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0-with-bison-exception.json", + "referenceNumber": 479, + "name": "GNU General Public License v2.0 w/Bison exception", + "licenseId": "GPL-2.0-with-bison-exception", + "seeAlso": [ + "http://git.savannah.gnu.org/cgit/bison.git/tree/data/yacc.c?id\u003d193d7c7054ba7197b0789e14965b739162319b5e#n141" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Apache-2.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Apache-2.0.json", + "referenceNumber": 480, + "name": "Apache License 2.0", + "licenseId": "Apache-2.0", + "seeAlso": [ + "https://www.apache.org/licenses/LICENSE-2.0", + "https://opensource.org/licenses/Apache-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Artistic-1.0-cl8.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Artistic-1.0-cl8.json", + "referenceNumber": 481, + "name": "Artistic License 1.0 w/clause 8", + "licenseId": "Artistic-1.0-cl8", + "seeAlso": [ + "https://opensource.org/licenses/Artistic-1.0" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/GPL-2.0.html", + "isDeprecatedLicenseId": true, + "detailsUrl": "https://spdx.org/licenses/GPL-2.0.json", + "referenceNumber": 482, + "name": "GNU General Public License v2.0 only", + "licenseId": "GPL-2.0", + "seeAlso": [ + "https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html", + "https://opensource.org/licenses/GPL-2.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Intel-ACPI.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Intel-ACPI.json", + "referenceNumber": 483, + "name": "Intel ACPI Software License Agreement", + "licenseId": "Intel-ACPI", + "seeAlso": [ + "https://fedoraproject.org/wiki/Licensing/Intel_ACPI_Software_License_Agreement" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/BSL-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSL-1.0.json", + "referenceNumber": 484, + "name": "Boost Software License 1.0", + "licenseId": "BSL-1.0", + "seeAlso": [ + "http://www.boost.org/LICENSE_1_0.txt", + "https://opensource.org/licenses/BSL-1.0" + ], + "isOsiApproved": true, + "isFsfLibre": true + }, + { + "reference": "https://spdx.org/licenses/Artistic-1.0-Perl.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Artistic-1.0-Perl.json", + "referenceNumber": 485, + "name": "Artistic License 1.0 (Perl)", + "licenseId": "Artistic-1.0-Perl", + "seeAlso": [ + "http://dev.perl.org/licenses/artistic.html" + ], + "isOsiApproved": true + }, + { + "reference": "https://spdx.org/licenses/BSD-2-Clause-Views.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/BSD-2-Clause-Views.json", + "referenceNumber": 486, + "name": "BSD 2-Clause with views sentence", + "licenseId": "BSD-2-Clause-Views", + "seeAlso": [ + "http://www.freebsd.org/copyright/freebsd-license.html", + "https://people.freebsd.org/~ivoras/wine/patch-wine-nvidia.sh", + "https://github.com/protegeproject/protege/blob/master/license.txt" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/Interbase-1.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/Interbase-1.0.json", + "referenceNumber": 487, + "name": "Interbase Public License v1.0", + "licenseId": "Interbase-1.0", + "seeAlso": [ + "https://web.archive.org/web/20060319014854/http://info.borland.com/devsupport/interbase/opensource/IPL.html" + ], + "isOsiApproved": false + }, + { + "reference": "https://spdx.org/licenses/NPOSL-3.0.html", + "isDeprecatedLicenseId": false, + "detailsUrl": "https://spdx.org/licenses/NPOSL-3.0.json", + "referenceNumber": 488, + "name": "Non-Profit Open Software License 3.0", + "licenseId": "NPOSL-3.0", + "seeAlso": [ + "https://opensource.org/licenses/NOSL3.0" + ], + "isOsiApproved": true + } + ], + "releaseDate": "2022-05-08" +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license.go b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license.go new file mode 100644 index 0000000000000000000000000000000000000000..a3029d2832f044095ecf5ff2555268ecf7d487fe --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license.go @@ -0,0 +1,20 @@ +package spdxlicense + +import ( + "strings" +) + +// https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/#license-short-name +// License generated in license_list.go uses a regular expression to help resolve cases where +// x.0.0 and x are supplied as version numbers. For SPDX compatibility, versions with trailing +// dot-zeroes are considered to be equivalent to versions without (e.g., “2.0.0” is considered equal to “2.0” and “2”). +// EX: gpl-2+ ---> GPL-2.0+ +// EX: gpl-2.0.0-only ---> GPL-2.0-only +// See the debian link for more details on the spdx license differences + +//go:generate go run ./generate + +func ID(id string) (string, bool) { + value, exists := licenseIDs[strings.ToLower(id)] + return value, exists +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_list.go b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_list.go new file mode 100644 index 0000000000000000000000000000000000000000..65c47f4383fa51e85b1d0c90bb7324c1eaeeb160 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_list.go @@ -0,0 +1,1074 @@ +// Code generated by go generate; DO NOT EDIT. +// This file was generated by robots at 2022-08-16 13:37:43.053262 -0400 EDT m=+0.183888850 +// using data from https://spdx.org/licenses/licenses.json +package spdxlicense + +const Version = "3.18" + +var licenseIDs = map[string]string{ + "0bsd": "0BSD", + "aal": "AAL", + "abstyles": "Abstyles", + "adobe-2006": "Adobe-2006", + "adobe-2006.0": "Adobe-2006", + "adobe-2006.0.0": "Adobe-2006", + "adobe-glyph": "Adobe-Glyph", + "adsl": "ADSL", + "afl-1": "AFL-1.1", + "afl-1.1": "AFL-1.1", + "afl-1.1.0": "AFL-1.1", + "afl-1.2": "AFL-1.2", + "afl-1.2.0": "AFL-1.2", + "afl-2": "AFL-2.0", + "afl-2.0": "AFL-2.0", + "afl-2.0.0": "AFL-2.0", + "afl-2.1": "AFL-2.1", + "afl-2.1.0": "AFL-2.1", + "afl-3": "AFL-3.0", + "afl-3.0": "AFL-3.0", + "afl-3.0.0": "AFL-3.0", + "afmparse": "Afmparse", + "agpl-1": "AGPL-1.0", + "agpl-1-only": "AGPL-1.0-only", + "agpl-1-or-later": "AGPL-1.0-or-later", + "agpl-1.0": "AGPL-1.0", + "agpl-1.0-only": "AGPL-1.0-only", + "agpl-1.0-or-later": "AGPL-1.0-or-later", + "agpl-1.0.0": "AGPL-1.0", + "agpl-1.0.0-only": "AGPL-1.0-only", + "agpl-1.0.0-or-later": "AGPL-1.0-or-later", + "agpl-3": "AGPL-3.0", + "agpl-3-only": "AGPL-3.0-only", + "agpl-3-or-later": "AGPL-3.0-or-later", + "agpl-3.0": "AGPL-3.0", + "agpl-3.0-only": "AGPL-3.0-only", + "agpl-3.0-or-later": "AGPL-3.0-or-later", + "agpl-3.0.0": "AGPL-3.0", + "agpl-3.0.0-only": "AGPL-3.0-only", + "agpl-3.0.0-or-later": "AGPL-3.0-or-later", + "aladdin": "Aladdin", + "amdplpa": "AMDPLPA", + "aml": "AML", + "ampas": "AMPAS", + "antlr-pd": "ANTLR-PD", + "antlr-pd-fallback": "ANTLR-PD-fallback", + "apache-1": "Apache-1.0", + "apache-1.0": "Apache-1.0", + "apache-1.0.0": "Apache-1.0", + "apache-1.1": "Apache-1.1", + "apache-1.1.0": "Apache-1.1", + "apache-2": "Apache-2.0", + "apache-2.0": "Apache-2.0", + "apache-2.0.0": "Apache-2.0", + "apafml": "APAFML", + "apl-1": "APL-1.0", + "apl-1.0": "APL-1.0", + "apl-1.0.0": "APL-1.0", + "app-s2p": "App-s2p", + "apsl-1": "APSL-1.0", + "apsl-1.0": "APSL-1.0", + "apsl-1.0.0": "APSL-1.0", + "apsl-1.1": "APSL-1.1", + "apsl-1.1.0": "APSL-1.1", + "apsl-1.2": "APSL-1.2", + "apsl-1.2.0": "APSL-1.2", + "apsl-2": "APSL-2.0", + "apsl-2.0": "APSL-2.0", + "apsl-2.0.0": "APSL-2.0", + "arphic-1999": "Arphic-1999", + "arphic-1999.0": "Arphic-1999", + "arphic-1999.0.0": "Arphic-1999", + "artistic-1": "Artistic-1.0", + "artistic-1-cl8": "Artistic-1.0-cl8", + "artistic-1-perl": "Artistic-1.0-Perl", + "artistic-1.0": "Artistic-1.0", + "artistic-1.0-cl8": "Artistic-1.0-cl8", + "artistic-1.0-perl": "Artistic-1.0-Perl", + "artistic-1.0.0": "Artistic-1.0", + "artistic-1.0.0-cl8": "Artistic-1.0-cl8", + "artistic-1.0.0-perl": "Artistic-1.0-Perl", + "artistic-2": "Artistic-2.0", + "artistic-2.0": "Artistic-2.0", + "artistic-2.0.0": "Artistic-2.0", + "baekmuk": "Baekmuk", + "bahyph": "Bahyph", + "barr": "Barr", + "beerware": "Beerware", + "bitstream-vera": "Bitstream-Vera", + "bittorrent-1": "BitTorrent-1.0", + "bittorrent-1.0": "BitTorrent-1.0", + "bittorrent-1.0.0": "BitTorrent-1.0", + "bittorrent-1.1": "BitTorrent-1.1", + "bittorrent-1.1.0": "BitTorrent-1.1", + "blessing": "blessing", + "blueoak-1": "BlueOak-1.0.0", + "blueoak-1.0": "BlueOak-1.0.0", + "blueoak-1.0.0": "BlueOak-1.0.0", + "borceux": "Borceux", + "bsd-1-clause": "BSD-1-Clause", + "bsd-1.0-clause": "BSD-1-Clause", + "bsd-1.0.0-clause": "BSD-1-Clause", + "bsd-2-clause": "BSD-2-Clause", + "bsd-2-clause-freebsd": "BSD-2-Clause-FreeBSD", + "bsd-2-clause-netbsd": "BSD-2-Clause-NetBSD", + "bsd-2-clause-patent": "BSD-2-Clause-Patent", + "bsd-2-clause-views": "BSD-2-Clause-Views", + "bsd-2.0-clause": "BSD-2-Clause", + "bsd-2.0-clause-freebsd": "BSD-2-Clause-FreeBSD", + "bsd-2.0-clause-netbsd": "BSD-2-Clause-NetBSD", + "bsd-2.0-clause-patent": "BSD-2-Clause-Patent", + "bsd-2.0-clause-views": "BSD-2-Clause-Views", + "bsd-2.0.0-clause": "BSD-2-Clause", + "bsd-2.0.0-clause-freebsd": "BSD-2-Clause-FreeBSD", + "bsd-2.0.0-clause-netbsd": "BSD-2-Clause-NetBSD", + "bsd-2.0.0-clause-patent": "BSD-2-Clause-Patent", + "bsd-2.0.0-clause-views": "BSD-2-Clause-Views", + "bsd-3-clause": "BSD-3-Clause", + "bsd-3-clause-attribution": "BSD-3-Clause-Attribution", + "bsd-3-clause-clear": "BSD-3-Clause-Clear", + "bsd-3-clause-lbnl": "BSD-3-Clause-LBNL", + "bsd-3-clause-modification": "BSD-3-Clause-Modification", + "bsd-3-clause-no-military-license": "BSD-3-Clause-No-Military-License", + "bsd-3-clause-no-nuclear-license": "BSD-3-Clause-No-Nuclear-License", + "bsd-3-clause-no-nuclear-license-2014": "BSD-3-Clause-No-Nuclear-License-2014", + "bsd-3-clause-no-nuclear-warranty": "BSD-3-Clause-No-Nuclear-Warranty", + "bsd-3-clause-open-mpi": "BSD-3-Clause-Open-MPI", + "bsd-3.0-clause": "BSD-3-Clause", + "bsd-3.0-clause-attribution": "BSD-3-Clause-Attribution", + "bsd-3.0-clause-clear": "BSD-3-Clause-Clear", + "bsd-3.0-clause-lbnl": "BSD-3-Clause-LBNL", + "bsd-3.0-clause-modification": "BSD-3-Clause-Modification", + "bsd-3.0-clause-no-military-license": "BSD-3-Clause-No-Military-License", + "bsd-3.0-clause-no-nuclear-license": "BSD-3-Clause-No-Nuclear-License", + "bsd-3.0-clause-no-nuclear-license-2014": "BSD-3-Clause-No-Nuclear-License-2014", + "bsd-3.0-clause-no-nuclear-warranty": "BSD-3-Clause-No-Nuclear-Warranty", + "bsd-3.0-clause-open-mpi": "BSD-3-Clause-Open-MPI", + "bsd-3.0.0-clause": "BSD-3-Clause", + "bsd-3.0.0-clause-attribution": "BSD-3-Clause-Attribution", + "bsd-3.0.0-clause-clear": "BSD-3-Clause-Clear", + "bsd-3.0.0-clause-lbnl": "BSD-3-Clause-LBNL", + "bsd-3.0.0-clause-modification": "BSD-3-Clause-Modification", + "bsd-3.0.0-clause-no-military-license": "BSD-3-Clause-No-Military-License", + "bsd-3.0.0-clause-no-nuclear-license": "BSD-3-Clause-No-Nuclear-License", + "bsd-3.0.0-clause-no-nuclear-license-2014": "BSD-3-Clause-No-Nuclear-License-2014", + "bsd-3.0.0-clause-no-nuclear-warranty": "BSD-3-Clause-No-Nuclear-Warranty", + "bsd-3.0.0-clause-open-mpi": "BSD-3-Clause-Open-MPI", + "bsd-4-clause": "BSD-4-Clause", + "bsd-4-clause-shortened": "BSD-4-Clause-Shortened", + "bsd-4-clause-uc": "BSD-4-Clause-UC", + "bsd-4.0-clause": "BSD-4-Clause", + "bsd-4.0-clause-shortened": "BSD-4-Clause-Shortened", + "bsd-4.0-clause-uc": "BSD-4-Clause-UC", + "bsd-4.0.0-clause": "BSD-4-Clause", + "bsd-4.0.0-clause-shortened": "BSD-4-Clause-Shortened", + "bsd-4.0.0-clause-uc": "BSD-4-Clause-UC", + "bsd-protection": "BSD-Protection", + "bsd-source-code": "BSD-Source-Code", + "bsl-1": "BSL-1.0", + "bsl-1.0": "BSL-1.0", + "bsl-1.0.0": "BSL-1.0", + "busl-1": "BUSL-1.1", + "busl-1.1": "BUSL-1.1", + "busl-1.1.0": "BUSL-1.1", + "bzip2-1": "bzip2-1.0.5", + "bzip2-1.0": "bzip2-1.0.5", + "bzip2-1.0.5": "bzip2-1.0.5", + "bzip2-1.0.6": "bzip2-1.0.6", + "c-uda-1": "C-UDA-1.0", + "c-uda-1.0": "C-UDA-1.0", + "c-uda-1.0.0": "C-UDA-1.0", + "cal-1": "CAL-1.0", + "cal-1-combined-work-exception": "CAL-1.0-Combined-Work-Exception", + "cal-1.0": "CAL-1.0", + "cal-1.0-combined-work-exception": "CAL-1.0-Combined-Work-Exception", + "cal-1.0.0": "CAL-1.0", + "cal-1.0.0-combined-work-exception": "CAL-1.0-Combined-Work-Exception", + "caldera": "Caldera", + "catosl-1": "CATOSL-1.1", + "catosl-1.1": "CATOSL-1.1", + "catosl-1.1.0": "CATOSL-1.1", + "cc-by-1": "CC-BY-1.0", + "cc-by-1.0": "CC-BY-1.0", + "cc-by-1.0.0": "CC-BY-1.0", + "cc-by-2": "CC-BY-2.0", + "cc-by-2-au": "CC-BY-2.5-AU", + "cc-by-2.0": "CC-BY-2.0", + "cc-by-2.0.0": "CC-BY-2.0", + "cc-by-2.5": "CC-BY-2.5", + "cc-by-2.5-au": "CC-BY-2.5-AU", + "cc-by-2.5.0": "CC-BY-2.5", + "cc-by-2.5.0-au": "CC-BY-2.5-AU", + "cc-by-3": "CC-BY-3.0", + "cc-by-3-at": "CC-BY-3.0-AT", + "cc-by-3-de": "CC-BY-3.0-DE", + "cc-by-3-igo": "CC-BY-3.0-IGO", + "cc-by-3-nl": "CC-BY-3.0-NL", + "cc-by-3-us": "CC-BY-3.0-US", + "cc-by-3.0": "CC-BY-3.0", + "cc-by-3.0-at": "CC-BY-3.0-AT", + "cc-by-3.0-de": "CC-BY-3.0-DE", + "cc-by-3.0-igo": "CC-BY-3.0-IGO", + "cc-by-3.0-nl": "CC-BY-3.0-NL", + "cc-by-3.0-us": "CC-BY-3.0-US", + "cc-by-3.0.0": "CC-BY-3.0", + "cc-by-3.0.0-at": "CC-BY-3.0-AT", + "cc-by-3.0.0-de": "CC-BY-3.0-DE", + "cc-by-3.0.0-igo": "CC-BY-3.0-IGO", + "cc-by-3.0.0-nl": "CC-BY-3.0-NL", + "cc-by-3.0.0-us": "CC-BY-3.0-US", + "cc-by-4": "CC-BY-4.0", + "cc-by-4.0": "CC-BY-4.0", + "cc-by-4.0.0": "CC-BY-4.0", + "cc-by-nc-1": "CC-BY-NC-1.0", + "cc-by-nc-1.0": "CC-BY-NC-1.0", + "cc-by-nc-1.0.0": "CC-BY-NC-1.0", + "cc-by-nc-2": "CC-BY-NC-2.0", + "cc-by-nc-2.0": "CC-BY-NC-2.0", + "cc-by-nc-2.0.0": "CC-BY-NC-2.0", + "cc-by-nc-2.5": "CC-BY-NC-2.5", + "cc-by-nc-2.5.0": "CC-BY-NC-2.5", + "cc-by-nc-3": "CC-BY-NC-3.0", + "cc-by-nc-3-de": "CC-BY-NC-3.0-DE", + "cc-by-nc-3.0": "CC-BY-NC-3.0", + "cc-by-nc-3.0-de": "CC-BY-NC-3.0-DE", + "cc-by-nc-3.0.0": "CC-BY-NC-3.0", + "cc-by-nc-3.0.0-de": "CC-BY-NC-3.0-DE", + "cc-by-nc-4": "CC-BY-NC-4.0", + "cc-by-nc-4.0": "CC-BY-NC-4.0", + "cc-by-nc-4.0.0": "CC-BY-NC-4.0", + "cc-by-nc-nd-1": "CC-BY-NC-ND-1.0", + "cc-by-nc-nd-1.0": "CC-BY-NC-ND-1.0", + "cc-by-nc-nd-1.0.0": "CC-BY-NC-ND-1.0", + "cc-by-nc-nd-2": "CC-BY-NC-ND-2.0", + "cc-by-nc-nd-2.0": "CC-BY-NC-ND-2.0", + "cc-by-nc-nd-2.0.0": "CC-BY-NC-ND-2.0", + "cc-by-nc-nd-2.5": "CC-BY-NC-ND-2.5", + "cc-by-nc-nd-2.5.0": "CC-BY-NC-ND-2.5", + "cc-by-nc-nd-3": "CC-BY-NC-ND-3.0", + "cc-by-nc-nd-3-de": "CC-BY-NC-ND-3.0-DE", + "cc-by-nc-nd-3-igo": "CC-BY-NC-ND-3.0-IGO", + "cc-by-nc-nd-3.0": "CC-BY-NC-ND-3.0", + "cc-by-nc-nd-3.0-de": "CC-BY-NC-ND-3.0-DE", + "cc-by-nc-nd-3.0-igo": "CC-BY-NC-ND-3.0-IGO", + "cc-by-nc-nd-3.0.0": "CC-BY-NC-ND-3.0", + "cc-by-nc-nd-3.0.0-de": "CC-BY-NC-ND-3.0-DE", + "cc-by-nc-nd-3.0.0-igo": "CC-BY-NC-ND-3.0-IGO", + "cc-by-nc-nd-4": "CC-BY-NC-ND-4.0", + "cc-by-nc-nd-4.0": "CC-BY-NC-ND-4.0", + "cc-by-nc-nd-4.0.0": "CC-BY-NC-ND-4.0", + "cc-by-nc-sa-1": "CC-BY-NC-SA-1.0", + "cc-by-nc-sa-1.0": "CC-BY-NC-SA-1.0", + "cc-by-nc-sa-1.0.0": "CC-BY-NC-SA-1.0", + "cc-by-nc-sa-2": "CC-BY-NC-SA-2.0", + "cc-by-nc-sa-2-fr": "CC-BY-NC-SA-2.0-FR", + "cc-by-nc-sa-2-uk": "CC-BY-NC-SA-2.0-UK", + "cc-by-nc-sa-2.0": "CC-BY-NC-SA-2.0", + "cc-by-nc-sa-2.0-fr": "CC-BY-NC-SA-2.0-FR", + "cc-by-nc-sa-2.0-uk": "CC-BY-NC-SA-2.0-UK", + "cc-by-nc-sa-2.0.0": "CC-BY-NC-SA-2.0", + "cc-by-nc-sa-2.0.0-fr": "CC-BY-NC-SA-2.0-FR", + "cc-by-nc-sa-2.0.0-uk": "CC-BY-NC-SA-2.0-UK", + "cc-by-nc-sa-2.5": "CC-BY-NC-SA-2.5", + "cc-by-nc-sa-2.5.0": "CC-BY-NC-SA-2.5", + "cc-by-nc-sa-3": "CC-BY-NC-SA-3.0", + "cc-by-nc-sa-3-de": "CC-BY-NC-SA-3.0-DE", + "cc-by-nc-sa-3-igo": "CC-BY-NC-SA-3.0-IGO", + "cc-by-nc-sa-3.0": "CC-BY-NC-SA-3.0", + "cc-by-nc-sa-3.0-de": "CC-BY-NC-SA-3.0-DE", + "cc-by-nc-sa-3.0-igo": "CC-BY-NC-SA-3.0-IGO", + "cc-by-nc-sa-3.0.0": "CC-BY-NC-SA-3.0", + "cc-by-nc-sa-3.0.0-de": "CC-BY-NC-SA-3.0-DE", + "cc-by-nc-sa-3.0.0-igo": "CC-BY-NC-SA-3.0-IGO", + "cc-by-nc-sa-4": "CC-BY-NC-SA-4.0", + "cc-by-nc-sa-4.0": "CC-BY-NC-SA-4.0", + "cc-by-nc-sa-4.0.0": "CC-BY-NC-SA-4.0", + "cc-by-nd-1": "CC-BY-ND-1.0", + "cc-by-nd-1.0": "CC-BY-ND-1.0", + "cc-by-nd-1.0.0": "CC-BY-ND-1.0", + "cc-by-nd-2": "CC-BY-ND-2.0", + "cc-by-nd-2.0": "CC-BY-ND-2.0", + "cc-by-nd-2.0.0": "CC-BY-ND-2.0", + "cc-by-nd-2.5": "CC-BY-ND-2.5", + "cc-by-nd-2.5.0": "CC-BY-ND-2.5", + "cc-by-nd-3": "CC-BY-ND-3.0", + "cc-by-nd-3-de": "CC-BY-ND-3.0-DE", + "cc-by-nd-3.0": "CC-BY-ND-3.0", + "cc-by-nd-3.0-de": "CC-BY-ND-3.0-DE", + "cc-by-nd-3.0.0": "CC-BY-ND-3.0", + "cc-by-nd-3.0.0-de": "CC-BY-ND-3.0-DE", + "cc-by-nd-4": "CC-BY-ND-4.0", + "cc-by-nd-4.0": "CC-BY-ND-4.0", + "cc-by-nd-4.0.0": "CC-BY-ND-4.0", + "cc-by-sa-1": "CC-BY-SA-1.0", + "cc-by-sa-1.0": "CC-BY-SA-1.0", + "cc-by-sa-1.0.0": "CC-BY-SA-1.0", + "cc-by-sa-2": "CC-BY-SA-2.0", + "cc-by-sa-2-jp": "CC-BY-SA-2.1-JP", + "cc-by-sa-2-uk": "CC-BY-SA-2.0-UK", + "cc-by-sa-2.0": "CC-BY-SA-2.0", + "cc-by-sa-2.0-uk": "CC-BY-SA-2.0-UK", + "cc-by-sa-2.0.0": "CC-BY-SA-2.0", + "cc-by-sa-2.0.0-uk": "CC-BY-SA-2.0-UK", + "cc-by-sa-2.1-jp": "CC-BY-SA-2.1-JP", + "cc-by-sa-2.1.0-jp": "CC-BY-SA-2.1-JP", + "cc-by-sa-2.5": "CC-BY-SA-2.5", + "cc-by-sa-2.5.0": "CC-BY-SA-2.5", + "cc-by-sa-3": "CC-BY-SA-3.0", + "cc-by-sa-3-at": "CC-BY-SA-3.0-AT", + "cc-by-sa-3-de": "CC-BY-SA-3.0-DE", + "cc-by-sa-3.0": "CC-BY-SA-3.0", + "cc-by-sa-3.0-at": "CC-BY-SA-3.0-AT", + "cc-by-sa-3.0-de": "CC-BY-SA-3.0-DE", + "cc-by-sa-3.0.0": "CC-BY-SA-3.0", + "cc-by-sa-3.0.0-at": "CC-BY-SA-3.0-AT", + "cc-by-sa-3.0.0-de": "CC-BY-SA-3.0-DE", + "cc-by-sa-4": "CC-BY-SA-4.0", + "cc-by-sa-4.0": "CC-BY-SA-4.0", + "cc-by-sa-4.0.0": "CC-BY-SA-4.0", + "cc-pddc": "CC-PDDC", + "cc0-1": "CC0-1.0", + "cc0-1.0": "CC0-1.0", + "cc0-1.0.0": "CC0-1.0", + "cddl-1": "CDDL-1.0", + "cddl-1.0": "CDDL-1.0", + "cddl-1.0.0": "CDDL-1.0", + "cddl-1.1": "CDDL-1.1", + "cddl-1.1.0": "CDDL-1.1", + "cdl-1": "CDL-1.0", + "cdl-1.0": "CDL-1.0", + "cdl-1.0.0": "CDL-1.0", + "cdla-permissive-1": "CDLA-Permissive-1.0", + "cdla-permissive-1.0": "CDLA-Permissive-1.0", + "cdla-permissive-1.0.0": "CDLA-Permissive-1.0", + "cdla-permissive-2": "CDLA-Permissive-2.0", + "cdla-permissive-2.0": "CDLA-Permissive-2.0", + "cdla-permissive-2.0.0": "CDLA-Permissive-2.0", + "cdla-sharing-1": "CDLA-Sharing-1.0", + "cdla-sharing-1.0": "CDLA-Sharing-1.0", + "cdla-sharing-1.0.0": "CDLA-Sharing-1.0", + "cecill-1": "CECILL-1.0", + "cecill-1.0": "CECILL-1.0", + "cecill-1.0.0": "CECILL-1.0", + "cecill-1.1": "CECILL-1.1", + "cecill-1.1.0": "CECILL-1.1", + "cecill-2": "CECILL-2.0", + "cecill-2.0": "CECILL-2.0", + "cecill-2.0.0": "CECILL-2.0", + "cecill-2.1": "CECILL-2.1", + "cecill-2.1.0": "CECILL-2.1", + "cecill-b": "CECILL-B", + "cecill-c": "CECILL-C", + "cern-ohl-1": "CERN-OHL-1.1", + "cern-ohl-1.1": "CERN-OHL-1.1", + "cern-ohl-1.1.0": "CERN-OHL-1.1", + "cern-ohl-1.2": "CERN-OHL-1.2", + "cern-ohl-1.2.0": "CERN-OHL-1.2", + "cern-ohl-p-2": "CERN-OHL-P-2.0", + "cern-ohl-p-2.0": "CERN-OHL-P-2.0", + "cern-ohl-p-2.0.0": "CERN-OHL-P-2.0", + "cern-ohl-s-2": "CERN-OHL-S-2.0", + "cern-ohl-s-2.0": "CERN-OHL-S-2.0", + "cern-ohl-s-2.0.0": "CERN-OHL-S-2.0", + "cern-ohl-w-2": "CERN-OHL-W-2.0", + "cern-ohl-w-2.0": "CERN-OHL-W-2.0", + "cern-ohl-w-2.0.0": "CERN-OHL-W-2.0", + "clartistic": "ClArtistic", + "cnri-jython": "CNRI-Jython", + "cnri-python": "CNRI-Python", + "cnri-python-gpl-compatible": "CNRI-Python-GPL-Compatible", + "coil-1": "COIL-1.0", + "coil-1.0": "COIL-1.0", + "coil-1.0.0": "COIL-1.0", + "community-spec-1": "Community-Spec-1.0", + "community-spec-1.0": "Community-Spec-1.0", + "community-spec-1.0.0": "Community-Spec-1.0", + "condor-1": "Condor-1.1", + "condor-1.1": "Condor-1.1", + "condor-1.1.0": "Condor-1.1", + "copyleft-next-0.3": "copyleft-next-0.3.0", + "copyleft-next-0.3.0": "copyleft-next-0.3.0", + "copyleft-next-0.3.1": "copyleft-next-0.3.1", + "cpal-1": "CPAL-1.0", + "cpal-1.0": "CPAL-1.0", + "cpal-1.0.0": "CPAL-1.0", + "cpl-1": "CPL-1.0", + "cpl-1.0": "CPL-1.0", + "cpl-1.0.0": "CPL-1.0", + "cpol-1": "CPOL-1.02", + "cpol-1.02": "CPOL-1.02", + "cpol-1.02.0": "CPOL-1.02", + "crossword": "Crossword", + "crystalstacker": "CrystalStacker", + "cua-opl-1": "CUA-OPL-1.0", + "cua-opl-1.0": "CUA-OPL-1.0", + "cua-opl-1.0.0": "CUA-OPL-1.0", + "cube": "Cube", + "curl": "curl", + "d-fsl-1": "D-FSL-1.0", + "d-fsl-1.0": "D-FSL-1.0", + "d-fsl-1.0.0": "D-FSL-1.0", + "diffmark": "diffmark", + "dl-de-by-2": "DL-DE-BY-2.0", + "dl-de-by-2.0": "DL-DE-BY-2.0", + "dl-de-by-2.0.0": "DL-DE-BY-2.0", + "doc": "DOC", + "dotseqn": "Dotseqn", + "drl-1": "DRL-1.0", + "drl-1.0": "DRL-1.0", + "drl-1.0.0": "DRL-1.0", + "dsdp": "DSDP", + "dvipdfm": "dvipdfm", + "ecl-1": "ECL-1.0", + "ecl-1.0": "ECL-1.0", + "ecl-1.0.0": "ECL-1.0", + "ecl-2": "ECL-2.0", + "ecl-2.0": "ECL-2.0", + "ecl-2.0.0": "ECL-2.0", + "ecos-2": "eCos-2.0", + "ecos-2.0": "eCos-2.0", + "ecos-2.0.0": "eCos-2.0", + "efl-1": "EFL-1.0", + "efl-1.0": "EFL-1.0", + "efl-1.0.0": "EFL-1.0", + "efl-2": "EFL-2.0", + "efl-2.0": "EFL-2.0", + "efl-2.0.0": "EFL-2.0", + "egenix": "eGenix", + "elastic-2": "Elastic-2.0", + "elastic-2.0": "Elastic-2.0", + "elastic-2.0.0": "Elastic-2.0", + "entessa": "Entessa", + "epics": "EPICS", + "epl-1": "EPL-1.0", + "epl-1.0": "EPL-1.0", + "epl-1.0.0": "EPL-1.0", + "epl-2": "EPL-2.0", + "epl-2.0": "EPL-2.0", + "epl-2.0.0": "EPL-2.0", + "erlpl-1": "ErlPL-1.1", + "erlpl-1.1": "ErlPL-1.1", + "erlpl-1.1.0": "ErlPL-1.1", + "etalab-2": "etalab-2.0", + "etalab-2.0": "etalab-2.0", + "etalab-2.0.0": "etalab-2.0", + "eudatagrid": "EUDatagrid", + "eupl-1": "EUPL-1.0", + "eupl-1.0": "EUPL-1.0", + "eupl-1.0.0": "EUPL-1.0", + "eupl-1.1": "EUPL-1.1", + "eupl-1.1.0": "EUPL-1.1", + "eupl-1.2": "EUPL-1.2", + "eupl-1.2.0": "EUPL-1.2", + "eurosym": "Eurosym", + "fair": "Fair", + "fdk-aac": "FDK-AAC", + "frameworx-1": "Frameworx-1.0", + "frameworx-1.0": "Frameworx-1.0", + "frameworx-1.0.0": "Frameworx-1.0", + "freebsd-doc": "FreeBSD-DOC", + "freeimage": "FreeImage", + "fsfap": "FSFAP", + "fsful": "FSFUL", + "fsfullr": "FSFULLR", + "ftl": "FTL", + "gd": "GD", + "gfdl-1": "GFDL-1.1", + "gfdl-1-invariants-only": "GFDL-1.1-invariants-only", + "gfdl-1-invariants-or-later": "GFDL-1.1-invariants-or-later", + "gfdl-1-no-invariants-only": "GFDL-1.1-no-invariants-only", + "gfdl-1-no-invariants-or-later": "GFDL-1.1-no-invariants-or-later", + "gfdl-1-only": "GFDL-1.1-only", + "gfdl-1-or-later": "GFDL-1.1-or-later", + "gfdl-1.1": "GFDL-1.1", + "gfdl-1.1-invariants-only": "GFDL-1.1-invariants-only", + "gfdl-1.1-invariants-or-later": "GFDL-1.1-invariants-or-later", + "gfdl-1.1-no-invariants-only": "GFDL-1.1-no-invariants-only", + "gfdl-1.1-no-invariants-or-later": "GFDL-1.1-no-invariants-or-later", + "gfdl-1.1-only": "GFDL-1.1-only", + "gfdl-1.1-or-later": "GFDL-1.1-or-later", + "gfdl-1.1.0": "GFDL-1.1", + "gfdl-1.1.0-invariants-only": "GFDL-1.1-invariants-only", + "gfdl-1.1.0-invariants-or-later": "GFDL-1.1-invariants-or-later", + "gfdl-1.1.0-no-invariants-only": "GFDL-1.1-no-invariants-only", + "gfdl-1.1.0-no-invariants-or-later": "GFDL-1.1-no-invariants-or-later", + "gfdl-1.1.0-only": "GFDL-1.1-only", + "gfdl-1.1.0-or-later": "GFDL-1.1-or-later", + "gfdl-1.2": "GFDL-1.2", + "gfdl-1.2-invariants-only": "GFDL-1.2-invariants-only", + "gfdl-1.2-invariants-or-later": "GFDL-1.2-invariants-or-later", + "gfdl-1.2-no-invariants-only": "GFDL-1.2-no-invariants-only", + "gfdl-1.2-no-invariants-or-later": "GFDL-1.2-no-invariants-or-later", + "gfdl-1.2-only": "GFDL-1.2-only", + "gfdl-1.2-or-later": "GFDL-1.2-or-later", + "gfdl-1.2.0": "GFDL-1.2", + "gfdl-1.2.0-invariants-only": "GFDL-1.2-invariants-only", + "gfdl-1.2.0-invariants-or-later": "GFDL-1.2-invariants-or-later", + "gfdl-1.2.0-no-invariants-only": "GFDL-1.2-no-invariants-only", + "gfdl-1.2.0-no-invariants-or-later": "GFDL-1.2-no-invariants-or-later", + "gfdl-1.2.0-only": "GFDL-1.2-only", + "gfdl-1.2.0-or-later": "GFDL-1.2-or-later", + "gfdl-1.3": "GFDL-1.3", + "gfdl-1.3-invariants-only": "GFDL-1.3-invariants-only", + "gfdl-1.3-invariants-or-later": "GFDL-1.3-invariants-or-later", + "gfdl-1.3-no-invariants-only": "GFDL-1.3-no-invariants-only", + "gfdl-1.3-no-invariants-or-later": "GFDL-1.3-no-invariants-or-later", + "gfdl-1.3-only": "GFDL-1.3-only", + "gfdl-1.3-or-later": "GFDL-1.3-or-later", + "gfdl-1.3.0": "GFDL-1.3", + "gfdl-1.3.0-invariants-only": "GFDL-1.3-invariants-only", + "gfdl-1.3.0-invariants-or-later": "GFDL-1.3-invariants-or-later", + "gfdl-1.3.0-no-invariants-only": "GFDL-1.3-no-invariants-only", + "gfdl-1.3.0-no-invariants-or-later": "GFDL-1.3-no-invariants-or-later", + "gfdl-1.3.0-only": "GFDL-1.3-only", + "gfdl-1.3.0-or-later": "GFDL-1.3-or-later", + "giftware": "Giftware", + "gl2ps": "GL2PS", + "glide": "Glide", + "glulxe": "Glulxe", + "glwtpl": "GLWTPL", + "gnuplot": "gnuplot", + "gpl-1": "GPL-1.0-only", + "gpl-1+": "GPL-1.0-or-later", + "gpl-1-only": "GPL-1.0-only", + "gpl-1-or-later": "GPL-1.0-or-later", + "gpl-1.0": "GPL-1.0-only", + "gpl-1.0+": "GPL-1.0-or-later", + "gpl-1.0-only": "GPL-1.0-only", + "gpl-1.0-or-later": "GPL-1.0-or-later", + "gpl-1.0.0": "GPL-1.0-only", + "gpl-1.0.0+": "GPL-1.0-or-later", + "gpl-1.0.0-only": "GPL-1.0-only", + "gpl-1.0.0-or-later": "GPL-1.0-or-later", + "gpl-2": "GPL-2.0-only", + "gpl-2+": "GPL-2.0-or-later", + "gpl-2-only": "GPL-2.0-only", + "gpl-2-or-later": "GPL-2.0-or-later", + "gpl-2-with-autoconf-exception": "GPL-2.0-with-autoconf-exception", + "gpl-2-with-bison-exception": "GPL-2.0-with-bison-exception", + "gpl-2-with-classpath-exception": "GPL-2.0-with-classpath-exception", + "gpl-2-with-font-exception": "GPL-2.0-with-font-exception", + "gpl-2-with-gcc-exception": "GPL-2.0-with-GCC-exception", + "gpl-2.0": "GPL-2.0-only", + "gpl-2.0+": "GPL-2.0-or-later", + "gpl-2.0-only": "GPL-2.0-only", + "gpl-2.0-or-later": "GPL-2.0-or-later", + "gpl-2.0-with-autoconf-exception": "GPL-2.0-with-autoconf-exception", + "gpl-2.0-with-bison-exception": "GPL-2.0-with-bison-exception", + "gpl-2.0-with-classpath-exception": "GPL-2.0-with-classpath-exception", + "gpl-2.0-with-font-exception": "GPL-2.0-with-font-exception", + "gpl-2.0-with-gcc-exception": "GPL-2.0-with-GCC-exception", + "gpl-2.0.0": "GPL-2.0-only", + "gpl-2.0.0+": "GPL-2.0-or-later", + "gpl-2.0.0-only": "GPL-2.0-only", + "gpl-2.0.0-or-later": "GPL-2.0-or-later", + "gpl-2.0.0-with-autoconf-exception": "GPL-2.0-with-autoconf-exception", + "gpl-2.0.0-with-bison-exception": "GPL-2.0-with-bison-exception", + "gpl-2.0.0-with-classpath-exception": "GPL-2.0-with-classpath-exception", + "gpl-2.0.0-with-font-exception": "GPL-2.0-with-font-exception", + "gpl-2.0.0-with-gcc-exception": "GPL-2.0-with-GCC-exception", + "gpl-3": "GPL-3.0-only", + "gpl-3+": "GPL-3.0-or-later", + "gpl-3-only": "GPL-3.0-only", + "gpl-3-or-later": "GPL-3.0-or-later", + "gpl-3-with-autoconf-exception": "GPL-3.0-with-autoconf-exception", + "gpl-3-with-gcc-exception": "GPL-3.0-with-GCC-exception", + "gpl-3.0": "GPL-3.0-only", + "gpl-3.0+": "GPL-3.0-or-later", + "gpl-3.0-only": "GPL-3.0-only", + "gpl-3.0-or-later": "GPL-3.0-or-later", + "gpl-3.0-with-autoconf-exception": "GPL-3.0-with-autoconf-exception", + "gpl-3.0-with-gcc-exception": "GPL-3.0-with-GCC-exception", + "gpl-3.0.0": "GPL-3.0-only", + "gpl-3.0.0+": "GPL-3.0-or-later", + "gpl-3.0.0-only": "GPL-3.0-only", + "gpl-3.0.0-or-later": "GPL-3.0-or-later", + "gpl-3.0.0-with-autoconf-exception": "GPL-3.0-with-autoconf-exception", + "gpl-3.0.0-with-gcc-exception": "GPL-3.0-with-GCC-exception", + "gsoap-1.3.0b": "gSOAP-1.3b", + "gsoap-1.3b": "gSOAP-1.3b", + "gsoap-1b": "gSOAP-1.3b", + "haskellreport": "HaskellReport", + "hippocratic-2": "Hippocratic-2.1", + "hippocratic-2.1": "Hippocratic-2.1", + "hippocratic-2.1.0": "Hippocratic-2.1", + "hpnd": "HPND", + "hpnd-sell-variant": "HPND-sell-variant", + "htmltidy": "HTMLTIDY", + "ibm-pibs": "IBM-pibs", + "icu": "ICU", + "ijg": "IJG", + "imagemagick": "ImageMagick", + "imatix": "iMatix", + "imlib2": "Imlib2", + "info-zip": "Info-ZIP", + "intel": "Intel", + "intel-acpi": "Intel-ACPI", + "interbase-1": "Interbase-1.0", + "interbase-1.0": "Interbase-1.0", + "interbase-1.0.0": "Interbase-1.0", + "ipa": "IPA", + "ipl-1": "IPL-1.0", + "ipl-1.0": "IPL-1.0", + "ipl-1.0.0": "IPL-1.0", + "isc": "ISC", + "jam": "Jam", + "jasper-2": "JasPer-2.0", + "jasper-2.0": "JasPer-2.0", + "jasper-2.0.0": "JasPer-2.0", + "jpnic": "JPNIC", + "json": "JSON", + "lal-1": "LAL-1.2", + "lal-1.2": "LAL-1.2", + "lal-1.2.0": "LAL-1.2", + "lal-1.3": "LAL-1.3", + "lal-1.3.0": "LAL-1.3", + "latex2e": "Latex2e", + "leptonica": "Leptonica", + "lgpl-2": "LGPL-2.0-only", + "lgpl-2+": "LGPL-2.0-or-later", + "lgpl-2-only": "LGPL-2.0-only", + "lgpl-2-or-later": "LGPL-2.0-or-later", + "lgpl-2.0": "LGPL-2.0-only", + "lgpl-2.0+": "LGPL-2.0-or-later", + "lgpl-2.0-only": "LGPL-2.0-only", + "lgpl-2.0-or-later": "LGPL-2.0-or-later", + "lgpl-2.0.0": "LGPL-2.0-only", + "lgpl-2.0.0+": "LGPL-2.0-or-later", + "lgpl-2.0.0-only": "LGPL-2.0-only", + "lgpl-2.0.0-or-later": "LGPL-2.0-or-later", + "lgpl-2.1": "LGPL-2.1-only", + "lgpl-2.1+": "LGPL-2.1+", + "lgpl-2.1-only": "LGPL-2.1-only", + "lgpl-2.1-or-later": "LGPL-2.1-or-later", + "lgpl-2.1.0": "LGPL-2.1-only", + "lgpl-2.1.0+": "LGPL-2.1+", + "lgpl-2.1.0-only": "LGPL-2.1-only", + "lgpl-2.1.0-or-later": "LGPL-2.1-or-later", + "lgpl-3": "LGPL-3.0-only", + "lgpl-3+": "LGPL-3.0-or-later", + "lgpl-3-only": "LGPL-3.0-only", + "lgpl-3-or-later": "LGPL-3.0-or-later", + "lgpl-3.0": "LGPL-3.0-only", + "lgpl-3.0+": "LGPL-3.0-or-later", + "lgpl-3.0-only": "LGPL-3.0-only", + "lgpl-3.0-or-later": "LGPL-3.0-or-later", + "lgpl-3.0.0": "LGPL-3.0-only", + "lgpl-3.0.0+": "LGPL-3.0-or-later", + "lgpl-3.0.0-only": "LGPL-3.0-only", + "lgpl-3.0.0-or-later": "LGPL-3.0-or-later", + "lgpllr": "LGPLLR", + "libpng": "Libpng", + "libpng-2": "libpng-2.0", + "libpng-2.0": "libpng-2.0", + "libpng-2.0.0": "libpng-2.0", + "libselinux-1": "libselinux-1.0", + "libselinux-1.0": "libselinux-1.0", + "libselinux-1.0.0": "libselinux-1.0", + "libtiff": "libtiff", + "liliq-p-1": "LiLiQ-P-1.1", + "liliq-p-1.1": "LiLiQ-P-1.1", + "liliq-p-1.1.0": "LiLiQ-P-1.1", + "liliq-r-1": "LiLiQ-R-1.1", + "liliq-r-1.1": "LiLiQ-R-1.1", + "liliq-r-1.1.0": "LiLiQ-R-1.1", + "liliq-rplus-1": "LiLiQ-Rplus-1.1", + "liliq-rplus-1.1": "LiLiQ-Rplus-1.1", + "liliq-rplus-1.1.0": "LiLiQ-Rplus-1.1", + "linux-man-pages-copyleft": "Linux-man-pages-copyleft", + "linux-openib": "Linux-OpenIB", + "lpl-1": "LPL-1.0", + "lpl-1.0": "LPL-1.0", + "lpl-1.0.0": "LPL-1.0", + "lpl-1.02": "LPL-1.02", + "lpl-1.02.0": "LPL-1.02", + "lppl-1": "LPPL-1.0", + "lppl-1.0": "LPPL-1.0", + "lppl-1.0.0": "LPPL-1.0", + "lppl-1.1": "LPPL-1.1", + "lppl-1.1.0": "LPPL-1.1", + "lppl-1.2": "LPPL-1.2", + "lppl-1.2.0": "LPPL-1.2", + "lppl-1.3.0a": "LPPL-1.3a", + "lppl-1.3.0c": "LPPL-1.3c", + "lppl-1.3a": "LPPL-1.3a", + "lppl-1.3c": "LPPL-1.3c", + "lppl-1a": "LPPL-1.3a", + "lppl-1c": "LPPL-1.3c", + "lzma-sdk-9": "LZMA-SDK-9.22", + "lzma-sdk-9-to-9.20": "LZMA-SDK-9.11-to-9.20", + "lzma-sdk-9.11-to-9.20": "LZMA-SDK-9.11-to-9.20", + "lzma-sdk-9.11.0-to-9.20": "LZMA-SDK-9.11-to-9.20", + "lzma-sdk-9.22": "LZMA-SDK-9.22", + "lzma-sdk-9.22.0": "LZMA-SDK-9.22", + "makeindex": "MakeIndex", + "minpack": "Minpack", + "miros": "MirOS", + "mit": "MIT", + "mit-0": "MIT-0", + "mit-advertising": "MIT-advertising", + "mit-cmu": "MIT-CMU", + "mit-enna": "MIT-enna", + "mit-feh": "MIT-feh", + "mit-modern-variant": "MIT-Modern-Variant", + "mit-open-group": "MIT-open-group", + "mitnfa": "MITNFA", + "motosoto": "Motosoto", + "mpi-permissive": "mpi-permissive", + "mpich2": "mpich2", + "mpl-1": "MPL-1.0", + "mpl-1.0": "MPL-1.0", + "mpl-1.0.0": "MPL-1.0", + "mpl-1.1": "MPL-1.1", + "mpl-1.1.0": "MPL-1.1", + "mpl-2": "MPL-2.0", + "mpl-2-no-copyleft-exception": "MPL-2.0-no-copyleft-exception", + "mpl-2.0": "MPL-2.0", + "mpl-2.0-no-copyleft-exception": "MPL-2.0-no-copyleft-exception", + "mpl-2.0.0": "MPL-2.0", + "mpl-2.0.0-no-copyleft-exception": "MPL-2.0-no-copyleft-exception", + "mplus": "mplus", + "ms-lpl": "MS-LPL", + "ms-pl": "MS-PL", + "ms-rl": "MS-RL", + "mtll": "MTLL", + "mulanpsl-1": "MulanPSL-1.0", + "mulanpsl-1.0": "MulanPSL-1.0", + "mulanpsl-1.0.0": "MulanPSL-1.0", + "mulanpsl-2": "MulanPSL-2.0", + "mulanpsl-2.0": "MulanPSL-2.0", + "mulanpsl-2.0.0": "MulanPSL-2.0", + "multics": "Multics", + "mup": "Mup", + "naist-2003": "NAIST-2003", + "naist-2003.0": "NAIST-2003", + "naist-2003.0.0": "NAIST-2003", + "nasa-1": "NASA-1.3", + "nasa-1.3": "NASA-1.3", + "nasa-1.3.0": "NASA-1.3", + "naumen": "Naumen", + "nbpl-1": "NBPL-1.0", + "nbpl-1.0": "NBPL-1.0", + "nbpl-1.0.0": "NBPL-1.0", + "ncgl-uk-2": "NCGL-UK-2.0", + "ncgl-uk-2.0": "NCGL-UK-2.0", + "ncgl-uk-2.0.0": "NCGL-UK-2.0", + "ncsa": "NCSA", + "net-snmp": "Net-SNMP", + "netcdf": "NetCDF", + "newsletr": "Newsletr", + "ngpl": "NGPL", + "nicta-1": "NICTA-1.0", + "nicta-1.0": "NICTA-1.0", + "nicta-1.0.0": "NICTA-1.0", + "nist-pd": "NIST-PD", + "nist-pd-fallback": "NIST-PD-fallback", + "nlod-1": "NLOD-1.0", + "nlod-1.0": "NLOD-1.0", + "nlod-1.0.0": "NLOD-1.0", + "nlod-2": "NLOD-2.0", + "nlod-2.0": "NLOD-2.0", + "nlod-2.0.0": "NLOD-2.0", + "nlpl": "NLPL", + "nokia": "Nokia", + "nosl": "NOSL", + "noweb": "Noweb", + "npl-1": "NPL-1.0", + "npl-1.0": "NPL-1.0", + "npl-1.0.0": "NPL-1.0", + "npl-1.1": "NPL-1.1", + "npl-1.1.0": "NPL-1.1", + "nposl-3": "NPOSL-3.0", + "nposl-3.0": "NPOSL-3.0", + "nposl-3.0.0": "NPOSL-3.0", + "nrl": "NRL", + "ntp": "NTP", + "ntp-0": "NTP-0", + "nunit": "Nunit", + "o-uda-1": "O-UDA-1.0", + "o-uda-1.0": "O-UDA-1.0", + "o-uda-1.0.0": "O-UDA-1.0", + "occt-pl": "OCCT-PL", + "oclc-2": "OCLC-2.0", + "oclc-2.0": "OCLC-2.0", + "oclc-2.0.0": "OCLC-2.0", + "odbl-1": "ODbL-1.0", + "odbl-1.0": "ODbL-1.0", + "odbl-1.0.0": "ODbL-1.0", + "odc-by-1": "ODC-By-1.0", + "odc-by-1.0": "ODC-By-1.0", + "odc-by-1.0.0": "ODC-By-1.0", + "ofl-1": "OFL-1.0", + "ofl-1-no-rfn": "OFL-1.0-no-RFN", + "ofl-1-rfn": "OFL-1.0-RFN", + "ofl-1.0": "OFL-1.0", + "ofl-1.0-no-rfn": "OFL-1.0-no-RFN", + "ofl-1.0-rfn": "OFL-1.0-RFN", + "ofl-1.0.0": "OFL-1.0", + "ofl-1.0.0-no-rfn": "OFL-1.0-no-RFN", + "ofl-1.0.0-rfn": "OFL-1.0-RFN", + "ofl-1.1": "OFL-1.1", + "ofl-1.1-no-rfn": "OFL-1.1-no-RFN", + "ofl-1.1-rfn": "OFL-1.1-RFN", + "ofl-1.1.0": "OFL-1.1", + "ofl-1.1.0-no-rfn": "OFL-1.1-no-RFN", + "ofl-1.1.0-rfn": "OFL-1.1-RFN", + "ogc-1": "OGC-1.0", + "ogc-1.0": "OGC-1.0", + "ogc-1.0.0": "OGC-1.0", + "ogdl-taiwan-1": "OGDL-Taiwan-1.0", + "ogdl-taiwan-1.0": "OGDL-Taiwan-1.0", + "ogdl-taiwan-1.0.0": "OGDL-Taiwan-1.0", + "ogl-canada-2": "OGL-Canada-2.0", + "ogl-canada-2.0": "OGL-Canada-2.0", + "ogl-canada-2.0.0": "OGL-Canada-2.0", + "ogl-uk-1": "OGL-UK-1.0", + "ogl-uk-1.0": "OGL-UK-1.0", + "ogl-uk-1.0.0": "OGL-UK-1.0", + "ogl-uk-2": "OGL-UK-2.0", + "ogl-uk-2.0": "OGL-UK-2.0", + "ogl-uk-2.0.0": "OGL-UK-2.0", + "ogl-uk-3": "OGL-UK-3.0", + "ogl-uk-3.0": "OGL-UK-3.0", + "ogl-uk-3.0.0": "OGL-UK-3.0", + "ogtsl": "OGTSL", + "oldap-1": "OLDAP-1.1", + "oldap-1.1": "OLDAP-1.1", + "oldap-1.1.0": "OLDAP-1.1", + "oldap-1.2": "OLDAP-1.2", + "oldap-1.2.0": "OLDAP-1.2", + "oldap-1.3": "OLDAP-1.3", + "oldap-1.3.0": "OLDAP-1.3", + "oldap-1.4": "OLDAP-1.4", + "oldap-1.4.0": "OLDAP-1.4", + "oldap-2": "OLDAP-2.0", + "oldap-2.0": "OLDAP-2.0", + "oldap-2.0.0": "OLDAP-2.0", + "oldap-2.0.1": "OLDAP-2.0.1", + "oldap-2.1": "OLDAP-2.1", + "oldap-2.1.0": "OLDAP-2.1", + "oldap-2.2": "OLDAP-2.2", + "oldap-2.2.0": "OLDAP-2.2", + "oldap-2.2.1": "OLDAP-2.2.1", + "oldap-2.2.2": "OLDAP-2.2.2", + "oldap-2.3": "OLDAP-2.3", + "oldap-2.3.0": "OLDAP-2.3", + "oldap-2.4": "OLDAP-2.4", + "oldap-2.4.0": "OLDAP-2.4", + "oldap-2.5": "OLDAP-2.5", + "oldap-2.5.0": "OLDAP-2.5", + "oldap-2.6": "OLDAP-2.6", + "oldap-2.6.0": "OLDAP-2.6", + "oldap-2.7": "OLDAP-2.7", + "oldap-2.7.0": "OLDAP-2.7", + "oldap-2.8": "OLDAP-2.8", + "oldap-2.8.0": "OLDAP-2.8", + "oml": "OML", + "openssl": "OpenSSL", + "opl-1": "OPL-1.0", + "opl-1.0": "OPL-1.0", + "opl-1.0.0": "OPL-1.0", + "opubl-1": "OPUBL-1.0", + "opubl-1.0": "OPUBL-1.0", + "opubl-1.0.0": "OPUBL-1.0", + "oset-pl-2": "OSET-PL-2.1", + "oset-pl-2.1": "OSET-PL-2.1", + "oset-pl-2.1.0": "OSET-PL-2.1", + "osl-1": "OSL-1.0", + "osl-1.0": "OSL-1.0", + "osl-1.0.0": "OSL-1.0", + "osl-1.1": "OSL-1.1", + "osl-1.1.0": "OSL-1.1", + "osl-2": "OSL-2.0", + "osl-2.0": "OSL-2.0", + "osl-2.0.0": "OSL-2.0", + "osl-2.1": "OSL-2.1", + "osl-2.1.0": "OSL-2.1", + "osl-3": "OSL-3.0", + "osl-3.0": "OSL-3.0", + "osl-3.0.0": "OSL-3.0", + "parity-6": "Parity-6.0.0", + "parity-6.0": "Parity-6.0.0", + "parity-6.0.0": "Parity-6.0.0", + "parity-7": "Parity-7.0.0", + "parity-7.0": "Parity-7.0.0", + "parity-7.0.0": "Parity-7.0.0", + "pddl-1": "PDDL-1.0", + "pddl-1.0": "PDDL-1.0", + "pddl-1.0.0": "PDDL-1.0", + "php-3": "PHP-3.0", + "php-3.0": "PHP-3.0", + "php-3.0.0": "PHP-3.0", + "php-3.01": "PHP-3.01", + "php-3.01.0": "PHP-3.01", + "plexus": "Plexus", + "polyform-noncommercial-1": "PolyForm-Noncommercial-1.0.0", + "polyform-noncommercial-1.0": "PolyForm-Noncommercial-1.0.0", + "polyform-noncommercial-1.0.0": "PolyForm-Noncommercial-1.0.0", + "polyform-small-business-1": "PolyForm-Small-Business-1.0.0", + "polyform-small-business-1.0": "PolyForm-Small-Business-1.0.0", + "polyform-small-business-1.0.0": "PolyForm-Small-Business-1.0.0", + "postgresql": "PostgreSQL", + "psf-2": "PSF-2.0", + "psf-2.0": "PSF-2.0", + "psf-2.0.0": "PSF-2.0", + "psfrag": "psfrag", + "psutils": "psutils", + "python-2": "Python-2.0", + "python-2.0": "Python-2.0", + "python-2.0.0": "Python-2.0", + "python-2.0.1": "Python-2.0.1", + "qhull": "Qhull", + "qpl-1": "QPL-1.0", + "qpl-1.0": "QPL-1.0", + "qpl-1.0.0": "QPL-1.0", + "rdisc": "Rdisc", + "rhecos-1": "RHeCos-1.1", + "rhecos-1.1": "RHeCos-1.1", + "rhecos-1.1.0": "RHeCos-1.1", + "rpl-1": "RPL-1.1", + "rpl-1.1": "RPL-1.1", + "rpl-1.1.0": "RPL-1.1", + "rpl-1.5": "RPL-1.5", + "rpl-1.5.0": "RPL-1.5", + "rpsl-1": "RPSL-1.0", + "rpsl-1.0": "RPSL-1.0", + "rpsl-1.0.0": "RPSL-1.0", + "rsa-md": "RSA-MD", + "rscpl": "RSCPL", + "ruby": "Ruby", + "sax-pd": "SAX-PD", + "saxpath": "Saxpath", + "scea": "SCEA", + "schemereport": "SchemeReport", + "sendmail": "Sendmail", + "sendmail-8": "Sendmail-8.23", + "sendmail-8.23": "Sendmail-8.23", + "sendmail-8.23.0": "Sendmail-8.23", + "sgi-b-1": "SGI-B-1.0", + "sgi-b-1.0": "SGI-B-1.0", + "sgi-b-1.0.0": "SGI-B-1.0", + "sgi-b-1.1": "SGI-B-1.1", + "sgi-b-1.1.0": "SGI-B-1.1", + "sgi-b-2": "SGI-B-2.0", + "sgi-b-2.0": "SGI-B-2.0", + "sgi-b-2.0.0": "SGI-B-2.0", + "shl-0.5": "SHL-0.5", + "shl-0.5.0": "SHL-0.5", + "shl-0.51": "SHL-0.51", + "shl-0.51.0": "SHL-0.51", + "simpl-2": "SimPL-2.0", + "simpl-2.0": "SimPL-2.0", + "simpl-2.0.0": "SimPL-2.0", + "sissl": "SISSL", + "sissl-1": "SISSL-1.2", + "sissl-1.2": "SISSL-1.2", + "sissl-1.2.0": "SISSL-1.2", + "sleepycat": "Sleepycat", + "smlnj": "SMLNJ", + "smppl": "SMPPL", + "snia": "SNIA", + "spencer-86": "Spencer-86", + "spencer-86.0": "Spencer-86", + "spencer-86.0.0": "Spencer-86", + "spencer-94": "Spencer-94", + "spencer-94.0": "Spencer-94", + "spencer-94.0.0": "Spencer-94", + "spencer-99": "Spencer-99", + "spencer-99.0": "Spencer-99", + "spencer-99.0.0": "Spencer-99", + "spl-1": "SPL-1.0", + "spl-1.0": "SPL-1.0", + "spl-1.0.0": "SPL-1.0", + "ssh-openssh": "SSH-OpenSSH", + "ssh-short": "SSH-short", + "sspl-1": "SSPL-1.0", + "sspl-1.0": "SSPL-1.0", + "sspl-1.0.0": "SSPL-1.0", + "standardml-nj": "StandardML-NJ", + "sugarcrm-1": "SugarCRM-1.1.3", + "sugarcrm-1.1": "SugarCRM-1.1.3", + "sugarcrm-1.1.3": "SugarCRM-1.1.3", + "swl": "SWL", + "tapr-ohl-1": "TAPR-OHL-1.0", + "tapr-ohl-1.0": "TAPR-OHL-1.0", + "tapr-ohl-1.0.0": "TAPR-OHL-1.0", + "tcl": "TCL", + "tcp-wrappers": "TCP-wrappers", + "tmate": "TMate", + "torque-1": "TORQUE-1.1", + "torque-1.1": "TORQUE-1.1", + "torque-1.1.0": "TORQUE-1.1", + "tosl": "TOSL", + "tu-berlin-1": "TU-Berlin-1.0", + "tu-berlin-1.0": "TU-Berlin-1.0", + "tu-berlin-1.0.0": "TU-Berlin-1.0", + "tu-berlin-2": "TU-Berlin-2.0", + "tu-berlin-2.0": "TU-Berlin-2.0", + "tu-berlin-2.0.0": "TU-Berlin-2.0", + "ucl-1": "UCL-1.0", + "ucl-1.0": "UCL-1.0", + "ucl-1.0.0": "UCL-1.0", + "unicode-dfs-2015": "Unicode-DFS-2015", + "unicode-dfs-2015.0": "Unicode-DFS-2015", + "unicode-dfs-2015.0.0": "Unicode-DFS-2015", + "unicode-dfs-2016": "Unicode-DFS-2016", + "unicode-dfs-2016.0": "Unicode-DFS-2016", + "unicode-dfs-2016.0.0": "Unicode-DFS-2016", + "unicode-tou": "Unicode-TOU", + "unlicense": "Unlicense", + "upl-1": "UPL-1.0", + "upl-1.0": "UPL-1.0", + "upl-1.0.0": "UPL-1.0", + "vim": "Vim", + "vostrom": "VOSTROM", + "vsl-1": "VSL-1.0", + "vsl-1.0": "VSL-1.0", + "vsl-1.0.0": "VSL-1.0", + "w3c": "W3C", + "w3c-19980720": "W3C-19980720", + "w3c-19980720.0": "W3C-19980720", + "w3c-19980720.0.0": "W3C-19980720", + "w3c-20150513": "W3C-20150513", + "w3c-20150513.0": "W3C-20150513", + "w3c-20150513.0.0": "W3C-20150513", + "watcom-1": "Watcom-1.0", + "watcom-1.0": "Watcom-1.0", + "watcom-1.0.0": "Watcom-1.0", + "wsuipa": "Wsuipa", + "wtfpl": "WTFPL", + "wxwindows": "wxWindows", + "x11": "X11", + "x11-distribute-modifications-variant": "X11-distribute-modifications-variant", + "xerox": "Xerox", + "xfree86-1": "XFree86-1.1", + "xfree86-1.1": "XFree86-1.1", + "xfree86-1.1.0": "XFree86-1.1", + "xinetd": "xinetd", + "xnet": "Xnet", + "xpp": "xpp", + "xskat": "XSkat", + "ypl-1": "YPL-1.0", + "ypl-1.0": "YPL-1.0", + "ypl-1.0.0": "YPL-1.0", + "ypl-1.1": "YPL-1.1", + "ypl-1.1.0": "YPL-1.1", + "zed": "Zed", + "zend-2": "Zend-2.0", + "zend-2.0": "Zend-2.0", + "zend-2.0.0": "Zend-2.0", + "zimbra-1": "Zimbra-1.3", + "zimbra-1.3": "Zimbra-1.3", + "zimbra-1.3.0": "Zimbra-1.3", + "zimbra-1.4": "Zimbra-1.4", + "zimbra-1.4.0": "Zimbra-1.4", + "zlib": "Zlib", + "zlib-acknowledgement": "zlib-acknowledgement", + "zpl-1": "ZPL-1.1", + "zpl-1.1": "ZPL-1.1", + "zpl-1.1.0": "ZPL-1.1", + "zpl-2": "ZPL-2.0", + "zpl-2.0": "ZPL-2.0", + "zpl-2.0.0": "ZPL-2.0", + "zpl-2.1": "ZPL-2.1", + "zpl-2.1.0": "ZPL-2.1", +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_list_test.go b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_list_test.go new file mode 100644 index 0000000000000000000000000000000000000000..7751f1a7c823e47ef576f913d20eaece9d22a3f7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_list_test.go @@ -0,0 +1,16 @@ +package spdxlicense + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestLicenceListIDs(t *testing.T) { + // do a sanity check on the generated data + assert.Equal(t, "0BSD", licenseIDs["0bsd"]) + assert.Equal(t, "ZPL-2.1", licenseIDs["zpl-2.1"]) + assert.Equal(t, "GPL-2.0-only", licenseIDs["gpl-2"]) + assert.Equal(t, "GPL-2.0-or-later", licenseIDs["gpl-2+"]) + assert.NotEmpty(t, Version) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_test.go b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_test.go new file mode 100644 index 0000000000000000000000000000000000000000..11456f3c386ab3765b594319e5179d713b5b6123 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/spdxlicense/license_test.go @@ -0,0 +1,60 @@ +package spdxlicense + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestIDParse(t *testing.T) { + var tests = []struct { + shortName string + spdx string + }{ + { + "GPL-1-only", + "GPL-1.0-only", + }, + { + "GPL-2", + "GPL-2.0-only", + }, + { + "GPL-2+", + "GPL-2.0-or-later", + }, + { + "GPL-3.0.0-or-later", + "GPL-3.0-or-later", + }, + { + "GPL-3-with-autoconf-exception", + "GPL-3.0-with-autoconf-exception", + }, + { + "CC-by-nc-3-de", + "CC-BY-NC-3.0-DE", + }, + // the below few cases are NOT expected, however, seem unavoidable given the current approach + { + "w3c-20150513.0.0", + "W3C-20150513", + }, + { + "spencer-86.0.0", + "Spencer-86", + }, + { + "unicode-dfs-2015.0.0", + "Unicode-DFS-2015", + }, + } + + for _, test := range tests { + t.Run(test.shortName, func(t *testing.T) { + got, exists := ID(test.shortName) + assert.True(t, exists) + assert.Equal(t, test.spdx, got) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/string_helpers.go b/ci/tools/openeuler-purl/syft-dev/internal/string_helpers.go new file mode 100644 index 0000000000000000000000000000000000000000..87bebea915ad0233a93041ccd8aa3375666fd28f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/string_helpers.go @@ -0,0 +1,21 @@ +package internal + +import "strings" + +// HasAnyOfPrefixes returns an indication if the given string has any of the given prefixes. +func HasAnyOfPrefixes(input string, prefixes ...string) bool { + for _, prefix := range prefixes { + if strings.HasPrefix(input, prefix) { + return true + } + } + + return false +} + +func TruncateMiddleEllipsis(input string, maxLen int) string { + if len(input) <= maxLen { + return input + } + return input[:maxLen/2] + "..." + input[len(input)-(maxLen/2):] +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/string_helpers_test.go b/ci/tools/openeuler-purl/syft-dev/internal/string_helpers_test.go new file mode 100644 index 0000000000000000000000000000000000000000..f89a0820fca795631a1bb559b18d38f654c72996 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/string_helpers_test.go @@ -0,0 +1,106 @@ +package internal + +import ( + "strconv" + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestHasAnyOfPrefixes(t *testing.T) { + tests := []struct { + name string + input string + prefixes []string + expected bool + }{ + { + name: "go case", + input: "this has something", + prefixes: []string{ + "this has", + "that does not have", + }, + expected: true, + }, + { + name: "no match", + input: "this has something", + prefixes: []string{ + "this DOES NOT has", + "that does not have", + }, + expected: false, + }, + { + name: "empty", + input: "this has something", + prefixes: []string{}, + expected: false, + }, + { + name: "positive match last", + input: "this has something", + prefixes: []string{ + "that does not have", + "this has", + }, + expected: true, + }, + { + name: "empty input", + input: "", + prefixes: []string{ + "that does not have", + "this has", + }, + expected: false, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, HasAnyOfPrefixes(test.input, test.prefixes...)) + }) + } +} + +func TestTruncateMiddleEllipsis(t *testing.T) { + tests := []struct { + input string + len int + expected string + }{ + { + input: "nobody expects the spanish inquisition", + len: 39, + expected: "nobody expects the spanish inquisition", + }, + { + input: "nobody expects the spanish inquisition", + len: 30, + expected: "nobody expects ...ish inquisition", + }, + { + input: "nobody expects the spanish inquisition", + len: 38, + expected: "nobody expects the spanish inquisition", + }, + { + input: "", + len: 30, + expected: "", + }, + { + input: "", + len: 0, + expected: "", + }, + } + + for _, test := range tests { + t.Run(test.input+":"+strconv.Itoa(test.len), func(t *testing.T) { + assert.Equal(t, test.expected, TruncateMiddleEllipsis(test.input, test.len)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/stringset.go b/ci/tools/openeuler-purl/syft-dev/internal/stringset.go new file mode 100644 index 0000000000000000000000000000000000000000..536e0a8a71def8e67b5e07866764f195d0bced91 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/stringset.go @@ -0,0 +1,43 @@ +package internal + +import "sort" + +// StringSet represents a set of string types. +type StringSet map[string]struct{} + +// NewStringSet creates a new empty StringSet. +func NewStringSet(start ...string) StringSet { + ret := make(StringSet) + for _, s := range start { + ret.Add(s) + } + return ret +} + +// Add a string to the set. +func (s StringSet) Add(i string) { + s[i] = struct{}{} +} + +// Remove a string from the set. +func (s StringSet) Remove(i string) { + delete(s, i) +} + +// Contains indicates if the given string is contained within the set. +func (s StringSet) Contains(i string) bool { + _, ok := s[i] + return ok +} + +// ToSlice returns a sorted slice of strings that are contained within the set. +func (s StringSet) ToSlice() []string { + ret := make([]string, len(s)) + idx := 0 + for v := range s { + ret[idx] = v + idx++ + } + sort.Strings(ret) + return ret +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/tprint.go b/ci/tools/openeuler-purl/syft-dev/internal/tprint.go new file mode 100644 index 0000000000000000000000000000000000000000..43d57cba5f950b1e600c197edd7c27c20538d3e7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/tprint.go @@ -0,0 +1,16 @@ +package internal + +import ( + "bytes" + "text/template" +) + +// Tprintf renders a string from a given template string and field values +func Tprintf(tmpl string, data map[string]interface{}) string { + t := template.Must(template.New("").Parse(tmpl)) + buf := &bytes.Buffer{} + if err := t.Execute(buf, data); err != nil { + return "" + } + return buf.String() +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/ui/common_event_handlers.go b/ci/tools/openeuler-purl/syft-dev/internal/ui/common_event_handlers.go new file mode 100644 index 0000000000000000000000000000000000000000..39b131e8087cf605eca794a8fdd1a5e3be1506f5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/ui/common_event_handlers.go @@ -0,0 +1,23 @@ +package ui + +import ( + "fmt" + + syftEventParsers "github.com/anchore/syft/syft/event/parsers" + "github.com/wagoodman/go-partybus" +) + +// handleExit is a UI function for processing the Exit bus event, +// and calling the given function to output the contents. +func handleExit(event partybus.Event) error { + // show the report to stdout + fn, err := syftEventParsers.ParseExit(event) + if err != nil { + return fmt.Errorf("bad CatalogerFinished event: %w", err) + } + + if err := fn(); err != nil { + return fmt.Errorf("unable to show package catalog report: %v", err) + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/ui/components/spinner.go b/ci/tools/openeuler-purl/syft-dev/internal/ui/components/spinner.go new file mode 100644 index 0000000000000000000000000000000000000000..debc8cb961ee126f271595432289a207bf70ffb2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/ui/components/spinner.go @@ -0,0 +1,42 @@ +package components + +import ( + "strings" + "sync" +) + +// TODO: move me to a common module (used in multiple repos) + +const ( + SpinnerDotSet = "⠋⠙⠹⠸⠼⠴⠦⠧⠇⠏" +) + +type Spinner struct { + index int + charset []string + lock sync.Mutex +} + +func NewSpinner(charset string) Spinner { + return Spinner{ + charset: strings.Split(charset, ""), + } +} + +func (s *Spinner) Current() string { + s.lock.Lock() + defer s.lock.Unlock() + + return s.charset[s.index] +} + +func (s *Spinner) Next() string { + s.lock.Lock() + defer s.lock.Unlock() + c := s.charset[s.index] + s.index++ + if s.index >= len(s.charset) { + s.index = 0 + } + return c +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/ui/ephemeral_terminal_ui.go b/ci/tools/openeuler-purl/syft-dev/internal/ui/ephemeral_terminal_ui.go new file mode 100644 index 0000000000000000000000000000000000000000..7cf7ad329ea0a1f0a692c371362abc95a039000b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/ui/ephemeral_terminal_ui.go @@ -0,0 +1,153 @@ +//go:build linux || darwin +// +build linux darwin + +package ui + +import ( + "bytes" + "context" + "fmt" + "io" + "os" + "sync" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/internal/logger" + syftEvent "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/ui" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/jotframe/pkg/frame" +) + +// ephemeralTerminalUI provides an "ephemeral" terminal user interface to display the application state dynamically. +// The terminal is placed into raw mode and the cursor is manipulated to allow for a dynamic, multi-line +// UI (provided by the jotframe lib), for this reason all other application mechanisms that write to the screen +// must be suppressed before starting (such as logs); since bytes in the device and in application memory combine to make +// a shared state, bytes coming from elsewhere to the screen will disrupt this state. +// +// This UI is primarily driven off of events from the event bus, creating single-line terminal widgets to represent a +// published element on the event bus, typically polling the element for the latest state. This allows for the UI to +// control update frequency to the screen, provide "liveness" indications that are interpolated between bus events, +// and overall loosely couple the bus events from screen interactions. +// +// By convention, all elements published on the bus should be treated as read-only, and publishers on the bus should +// attempt to enforce this when possible by wrapping complex objects with interfaces to prescribe interactions. Also by +// convention, each new event that the UI should respond to should be added either in this package as a handler function, +// or in the shared ui package as a function on the main handler object. All handler functions should be completed +// processing an event before the ETUI exits (coordinated with a sync.WaitGroup) +type ephemeralTerminalUI struct { + unsubscribe func() error + handler *ui.Handler + waitGroup *sync.WaitGroup + frame *frame.Frame + logBuffer *bytes.Buffer + uiOutput *os.File +} + +// NewEphemeralTerminalUI writes all events to a TUI and writes the final report to the given writer. +func NewEphemeralTerminalUI() UI { + return &ephemeralTerminalUI{ + handler: ui.NewHandler(), + waitGroup: &sync.WaitGroup{}, + uiOutput: os.Stderr, + } +} + +func (h *ephemeralTerminalUI) Setup(unsubscribe func() error) error { + h.unsubscribe = unsubscribe + hideCursor(h.uiOutput) + + // prep the logger to not clobber the screen from now on (logrus only) + h.logBuffer = bytes.NewBufferString("") + logWrapper, ok := log.Log.(*logger.LogrusLogger) + if ok { + logWrapper.Logger.SetOutput(h.logBuffer) + } + + return h.openScreen() +} + +func (h *ephemeralTerminalUI) Handle(event partybus.Event) error { + ctx := context.Background() + switch { + case h.handler.RespondsTo(event): + if err := h.handler.Handle(ctx, h.frame, event, h.waitGroup); err != nil { + log.Errorf("unable to show %s event: %+v", event.Type, err) + } + + case event.Type == syftEvent.AppUpdateAvailable: + if err := handleAppUpdateAvailable(ctx, h.frame, event, h.waitGroup); err != nil { + log.Errorf("unable to show %s event: %+v", event.Type, err) + } + + case event.Type == syftEvent.Exit: + // we need to close the screen now since signaling the sbom is ready means that we + // are about to write bytes to stdout, so we should reset the terminal state first + h.closeScreen(false) + + if err := handleExit(event); err != nil { + log.Errorf("unable to show %s event: %+v", event.Type, err) + } + + // this is the last expected event, stop listening to events + return h.unsubscribe() + } + return nil +} + +func (h *ephemeralTerminalUI) openScreen() error { + config := frame.Config{ + PositionPolicy: frame.PolicyFloatForward, + // only report output to stderr, reserve report output for stdout + Output: h.uiOutput, + } + + fr, err := frame.New(config) + if err != nil { + return fmt.Errorf("failed to create the screen object: %w", err) + } + h.frame = fr + + return nil +} + +func (h *ephemeralTerminalUI) closeScreen(force bool) { + // we may have other background processes still displaying progress, wait for them to + // finish before discontinuing dynamic content and showing the final report + if !h.frame.IsClosed() { + if !force { + h.waitGroup.Wait() + } + h.frame.Close() + // TODO: there is a race condition within frame.Close() that sometimes leads to an extra blank line being output + frame.Close() + + // only flush the log on close + h.flushLog() + } +} + +func (h *ephemeralTerminalUI) flushLog() { + // flush any errors to the screen before the report + logWrapper, ok := log.Log.(*logger.LogrusLogger) + if ok { + fmt.Fprint(logWrapper.Output, h.logBuffer.String()) + logWrapper.Logger.SetOutput(h.uiOutput) + } else { + fmt.Fprint(h.uiOutput, h.logBuffer.String()) + } +} + +func (h *ephemeralTerminalUI) Teardown(force bool) error { + h.closeScreen(force) + showCursor(h.uiOutput) + return nil +} + +func hideCursor(output io.Writer) { + fmt.Fprint(output, "\x1b[?25l") +} + +func showCursor(output io.Writer) { + fmt.Fprint(output, "\x1b[?25h") +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/ui/etui_event_handlers.go b/ci/tools/openeuler-purl/syft-dev/internal/ui/etui_event_handlers.go new file mode 100644 index 0000000000000000000000000000000000000000..fcd998e44269e1e4ef90a589c3511a173ec0a24c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/ui/etui_event_handlers.go @@ -0,0 +1,36 @@ +//go:build linux || darwin +// +build linux darwin + +package ui + +import ( + "context" + "fmt" + "io" + "sync" + + "github.com/anchore/syft/internal" + "github.com/gookit/color" + "github.com/wagoodman/jotframe/pkg/frame" + + syftEventParsers "github.com/anchore/syft/syft/event/parsers" + "github.com/wagoodman/go-partybus" +) + +// handleAppUpdateAvailable is a UI handler function to display a new application version to the top of the screen. +func handleAppUpdateAvailable(_ context.Context, fr *frame.Frame, event partybus.Event, _ *sync.WaitGroup) error { + newVersion, err := syftEventParsers.ParseAppUpdateAvailable(event) + if err != nil { + return fmt.Errorf("bad AppUpdateAvailable event: %w", err) + } + + line, err := fr.Prepend() + if err != nil { + return err + } + + message := color.Magenta.Sprintf("New version of %s is available: %s", internal.ApplicationName, newVersion) + _, _ = io.WriteString(line, message) + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/ui/logger_ui.go b/ci/tools/openeuler-purl/syft-dev/internal/ui/logger_ui.go new file mode 100644 index 0000000000000000000000000000000000000000..53cd9f7a9525fe5c0ea9abb828bba56d0062ef75 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/ui/logger_ui.go @@ -0,0 +1,39 @@ +package ui + +import ( + "github.com/anchore/syft/internal/log" + syftEvent "github.com/anchore/syft/syft/event" + "github.com/wagoodman/go-partybus" +) + +type loggerUI struct { + unsubscribe func() error +} + +// NewLoggerUI writes all events to the common application logger and writes the final report to the given writer. +func NewLoggerUI() UI { + return &loggerUI{} +} + +func (l *loggerUI) Setup(unsubscribe func() error) error { + l.unsubscribe = unsubscribe + return nil +} + +func (l loggerUI) Handle(event partybus.Event) error { + // ignore all events except for the final event + if event.Type != syftEvent.Exit { + return nil + } + + if err := handleExit(event); err != nil { + log.Warnf("unable to show catalog image finished event: %+v", err) + } + + // this is the last expected event, stop listening to events + return l.unsubscribe() +} + +func (l loggerUI) Teardown(_ bool) error { + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/ui/select.go b/ci/tools/openeuler-purl/syft-dev/internal/ui/select.go new file mode 100644 index 0000000000000000000000000000000000000000..b8b3adf193f45c8e6b82dfd51cdd0a8dd266df0d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/ui/select.go @@ -0,0 +1,31 @@ +//go:build linux || darwin +// +build linux darwin + +package ui + +import ( + "os" + "runtime" + + "golang.org/x/term" +) + +// Select is responsible for determining the specific UI function given select user option, the current platform +// config values, and environment status (such as a TTY being present). The first UI in the returned slice of UIs +// is intended to be used and the UIs that follow are meant to be attempted only in a fallback posture when there +// are environmental problems (e.g. cannot write to the terminal). A writer is provided to capture the output of +// the final SBOM report. +func Select(verbose, quiet bool) (uis []UI) { + isStdoutATty := term.IsTerminal(int(os.Stdout.Fd())) + isStderrATty := term.IsTerminal(int(os.Stderr.Fd())) + notATerminal := !isStderrATty && !isStdoutATty + + switch { + case runtime.GOOS == "windows" || verbose || quiet || notATerminal || !isStderrATty: + uis = append(uis, NewLoggerUI()) + default: + uis = append(uis, NewEphemeralTerminalUI()) + } + + return uis +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/ui/select_windows.go b/ci/tools/openeuler-purl/syft-dev/internal/ui/select_windows.go new file mode 100644 index 0000000000000000000000000000000000000000..cd8c79839ec351ca636356e64b86d6756549dfc8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/ui/select_windows.go @@ -0,0 +1,13 @@ +//go:build windows +// +build windows + +package ui + +// Select is responsible for determining the specific UI function given select user option, the current platform +// config values, and environment status (such as a TTY being present). The first UI in the returned slice of UIs +// is intended to be used and the UIs that follow are meant to be attempted only in a fallback posture when there +// are environmental problems (e.g. cannot write to the terminal). A writer is provided to capture the output of +// the final SBOM report. +func Select(verbose, quiet bool) (uis []UI) { + return append(uis, NewLoggerUI()) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/ui/ui.go b/ci/tools/openeuler-purl/syft-dev/internal/ui/ui.go new file mode 100644 index 0000000000000000000000000000000000000000..cb551f1cfcbb1ea881678744e854bc3589366538 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/ui/ui.go @@ -0,0 +1,11 @@ +package ui + +import ( + "github.com/wagoodman/go-partybus" +) + +type UI interface { + Setup(unsubscribe func() error) error + partybus.Handler + Teardown(force bool) error +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/version/build.go b/ci/tools/openeuler-purl/syft-dev/internal/version/build.go new file mode 100644 index 0000000000000000000000000000000000000000..a0d5fc1d2e3dc91fe3901244c9a984fd85a4b1f0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/version/build.go @@ -0,0 +1,54 @@ +/* +Package version contains all build time metadata (version, build time, git commit, etc). +*/ +package version + +import ( + "fmt" + "runtime" + "strings" + + "github.com/anchore/syft/internal" +) + +const valueNotProvided = "[not provided]" + +// all variables here are provided as build-time arguments, with clear default values +var version = valueNotProvided +var gitCommit = valueNotProvided +var gitDescription = valueNotProvided +var buildDate = valueNotProvided +var platform = fmt.Sprintf("%s/%s", runtime.GOOS, runtime.GOARCH) + +// Version defines the application version details (generally from build information) +type Version struct { + Version string `json:"version"` // application semantic version + JSONSchemaVersion string `json:"jsonSchemaVersion"` // application semantic JSON schema version + GitCommit string `json:"gitCommit"` // git SHA at build-time + GitDescription string `json:"gitDescription"` // output of 'git describe --dirty --always --tags' + BuildDate string `json:"buildDate"` // date of the build + GoVersion string `json:"goVersion"` // go runtime version at build-time + Compiler string `json:"compiler"` // compiler used at build-time + Platform string `json:"platform"` // GOOS and GOARCH at build-time +} + +func (v Version) IsProductionBuild() bool { + if strings.Contains(v.Version, "SNAPSHOT") || strings.Contains(v.Version, valueNotProvided) { + return false + } + return true +} + +// FromBuild provides all version details +func FromBuild() Version { + return Version{ + Version: version, + JSONSchemaVersion: internal.JSONSchemaVersion, + GitCommit: gitCommit, + GitDescription: gitDescription, + BuildDate: buildDate, + GoVersion: runtime.Version(), + Compiler: runtime.Compiler, + Platform: platform, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/version/update.go b/ci/tools/openeuler-purl/syft-dev/internal/version/update.go new file mode 100644 index 0000000000000000000000000000000000000000..00141d14272165c4159c0f0f1c9f653ba671a15a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/version/update.go @@ -0,0 +1,73 @@ +package version + +import ( + "fmt" + "io" + "net/http" + "strings" + + hashiVersion "github.com/anchore/go-version" + "github.com/anchore/syft/internal" +) + +var latestAppVersionURL = struct { + host string + path string +}{ + host: "https://toolbox-data.anchore.io", + path: fmt.Sprintf("/%s/releases/latest/VERSION", internal.ApplicationName), +} + +// IsUpdateAvailable indicates if there is a newer application version available, and if so, what the new version is. +func IsUpdateAvailable() (bool, string, error) { + currentBuildInfo := FromBuild() + if !currentBuildInfo.IsProductionBuild() { + // don't allow for non-production builds to check for a version. + return false, "", nil + } + currentVersion, err := hashiVersion.NewVersion(currentBuildInfo.Version) + if err != nil { + return false, "", fmt.Errorf("failed to parse current application version: %w", err) + } + + latestVersion, err := fetchLatestApplicationVersion() + if err != nil { + return false, "", err + } + + if latestVersion.GreaterThan(currentVersion) { + return true, latestVersion.String(), nil + } + + return false, "", nil +} + +func fetchLatestApplicationVersion() (*hashiVersion.Version, error) { + req, err := http.NewRequest(http.MethodGet, latestAppVersionURL.host+latestAppVersionURL.path, nil) + if err != nil { + return nil, fmt.Errorf("failed to create request for latest version: %w", err) + } + + client := http.Client{} + resp, err := client.Do(req) + if err != nil { + return nil, fmt.Errorf("failed to fetch latest version: %w", err) + } + defer resp.Body.Close() + + if resp.StatusCode != http.StatusOK { + return nil, fmt.Errorf("HTTP %d on fetching latest version: %s", resp.StatusCode, resp.Status) + } + + versionBytes, err := io.ReadAll(resp.Body) + if err != nil { + return nil, fmt.Errorf("failed to read latest version: %w", err) + } + + versionStr := strings.TrimSuffix(string(versionBytes), "\n") + if len(versionStr) > 50 { + return nil, fmt.Errorf("version too long: %q", versionStr[:50]) + } + + return hashiVersion.NewVersion(versionStr) +} diff --git a/ci/tools/openeuler-purl/syft-dev/internal/version/update_test.go b/ci/tools/openeuler-purl/syft-dev/internal/version/update_test.go new file mode 100644 index 0000000000000000000000000000000000000000..c79750540328726b66860633a0f1f72fe9e5f71c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/internal/version/update_test.go @@ -0,0 +1,218 @@ +package version + +import ( + "net/http" + "net/http/httptest" + "testing" + + hashiVersion "github.com/anchore/go-version" +) + +func TestIsUpdateAvailable(t *testing.T) { + tests := []struct { + name string + buildVersion string + latestVersion string + code int + isAvailable bool + newVersion string + err bool + }{ + { + name: "equal", + buildVersion: "1.0.0", + latestVersion: "1.0.0", + code: 200, + isAvailable: false, + newVersion: "", + err: false, + }, + { + name: "hasUpdate", + buildVersion: "1.0.0", + latestVersion: "1.2.0", + code: 200, + isAvailable: true, + newVersion: "1.2.0", + err: false, + }, + { + name: "aheadOfLatest", + buildVersion: "1.2.0", + latestVersion: "1.0.0", + code: 200, + isAvailable: false, + newVersion: "", + err: false, + }, + { + name: "EmptyUpdate", + buildVersion: "1.0.0", + latestVersion: "", + code: 200, + isAvailable: false, + newVersion: "", + err: true, + }, + { + name: "GarbageUpdate", + buildVersion: "1.0.0", + latestVersion: "hdfjksdhfhkj", + code: 200, + isAvailable: false, + newVersion: "", + err: true, + }, + { + name: "BadUpdate", + buildVersion: "1.0.0", + latestVersion: "1.0.", + code: 500, + isAvailable: false, + newVersion: "", + err: true, + }, + { + name: "NoBuildVersion", + buildVersion: valueNotProvided, + latestVersion: "1.0.0", + code: 200, + isAvailable: false, + newVersion: "", + err: false, + }, + { + name: "SnapshotBuildVersion", + buildVersion: "2.0.0-SHAPSHOT-a78bf9c", + latestVersion: "1.0.0", + code: 200, + isAvailable: false, + newVersion: "", + err: false, + }, + { + name: "BadUpdateValidVersion", + buildVersion: "1.0.0", + latestVersion: "2.0.0", + code: 404, + isAvailable: false, + newVersion: "", + err: true, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + // setup mocks + // local... + version = test.buildVersion + // remote... + handler := http.NewServeMux() + handler.HandleFunc(latestAppVersionURL.path, func(w http.ResponseWriter, r *http.Request) { + w.WriteHeader(test.code) + _, _ = w.Write([]byte(test.latestVersion)) + }) + mockSrv := httptest.NewServer(handler) + latestAppVersionURL.host = mockSrv.URL + defer mockSrv.Close() + + isAvailable, newVersion, err := IsUpdateAvailable() + if err != nil && !test.err { + t.Fatalf("got error but expected none: %+v", err) + } else if err == nil && test.err { + t.Fatalf("expected error but got none") + } + + if newVersion != test.newVersion { + t.Errorf("unexpected NEW version: %+v", newVersion) + } + + if isAvailable != test.isAvailable { + t.Errorf("unexpected result: %+v", isAvailable) + } + }) + } + +} + +func TestFetchLatestApplicationVersion(t *testing.T) { + tests := []struct { + name string + response string + code int + err bool + expected *hashiVersion.Version + }{ + { + name: "gocase", + response: "1.0.0", + code: 200, + expected: hashiVersion.Must(hashiVersion.NewVersion("1.0.0")), + }, + { + name: "garbage", + response: "garbage", + code: 200, + expected: nil, + err: true, + }, + { + name: "http 500", + response: "1.0.0", + code: 500, + expected: nil, + err: true, + }, + { + name: "http 404", + response: "1.0.0", + code: 404, + expected: nil, + err: true, + }, + { + name: "empty", + response: "", + code: 200, + expected: nil, + err: true, + }, + { + name: "too long", + response: "this is really long this is really long this is really long this is really long this is really long this is really long this is really long this is really long ", + code: 200, + expected: nil, + err: true, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + // setup mock + handler := http.NewServeMux() + handler.HandleFunc(latestAppVersionURL.path, func(w http.ResponseWriter, r *http.Request) { + w.WriteHeader(test.code) + _, _ = w.Write([]byte(test.response)) + }) + mockSrv := httptest.NewServer(handler) + latestAppVersionURL.host = mockSrv.URL + defer mockSrv.Close() + + actual, err := fetchLatestApplicationVersion() + if err != nil && !test.err { + t.Fatalf("got error but expected none: %+v", err) + } else if err == nil && test.err { + t.Fatalf("expected error but got none") + } + + if err != nil { + return + } + + if actual.String() != test.expected.String() { + t.Errorf("unexpected version: %+v", actual.String()) + } + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/.gitignore b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..472d439fa14f37a9fed2299cdded1a9469534b38 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/.gitignore @@ -0,0 +1,2 @@ +bom.xml +bom.json diff --git a/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/Makefile b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..8b10c792eca3ea945e9fe35f30cb313296b6b1be --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/Makefile @@ -0,0 +1,7 @@ +.DEFAULT_GOAL := validate-schema +.PHONY: validate-schema +validate-schema: + go run ../../cmd/syft/main.go ubuntu:latest -vv -o cyclonedx > bom.xml + xmllint --noout --schema ./cyclonedx.xsd bom.xml + go run ../../cmd/syft/main.go ubuntu:latest -vv -o cyclonedx-json > bom.json + ../../.tmp/yajsv -s cyclonedx.json bom.json diff --git a/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/README.md b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/README.md new file mode 100644 index 0000000000000000000000000000000000000000..200d6393e30a061c6893133b1a5bdd10da9ad122 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/README.md @@ -0,0 +1,7 @@ +# CycloneDX Schemas + +`syft` generates a CycloneDX BOm output. We want to be able to validate the CycloneDX schemas +(and dependent schemas) against generated syft output. The best way to do this is with `xmllint`, +however, this tool does not know how to deal with references from HTTP, only the local filesystem. +For this reason we've included a copy of all schemas needed to validate `syft` output, modified +to reference local copies of dependent schemas. diff --git a/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/cyclonedx.json b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/cyclonedx.json new file mode 100644 index 0000000000000000000000000000000000000000..dafd884524c6aa11c2725d87df68fd0789c1af32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/cyclonedx.json @@ -0,0 +1,1697 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "$id": "http://cyclonedx.org/schema/bom-1.4.schema.json", + "type": "object", + "title": "CycloneDX Software Bill of Materials Standard", + "$comment" : "CycloneDX JSON schema is published under the terms of the Apache License 2.0.", + "required": [ + "bomFormat", + "specVersion", + "version" + ], + "additionalProperties": false, + "properties": { + "$schema": { + "type": "string", + "enum": [ + "http://cyclonedx.org/schema/bom-1.4.schema.json" + ] + }, + "bomFormat": { + "type": "string", + "title": "BOM Format", + "description": "Specifies the format of the BOM. This helps to identify the file as CycloneDX since BOMs do not have a filename convention nor does JSON schema support namespaces. This value MUST be \"CycloneDX\".", + "enum": [ + "CycloneDX" + ] + }, + "specVersion": { + "type": "string", + "title": "CycloneDX Specification Version", + "description": "The version of the CycloneDX specification a BOM conforms to (starting at version 1.2).", + "examples": ["1.4"] + }, + "serialNumber": { + "type": "string", + "title": "BOM Serial Number", + "description": "Every BOM generated SHOULD have a unique serial number, even if the contents of the BOM have not changed over time. If specified, the serial number MUST conform to RFC-4122. Use of serial numbers are RECOMMENDED.", + "examples": ["urn:uuid:3e671687-395b-41f5-a30f-a58921a69b79"], + "pattern": "^urn:uuid:[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$" + }, + "version": { + "type": "integer", + "title": "BOM Version", + "description": "Whenever an existing BOM is modified, either manually or through automated processes, the version of the BOM SHOULD be incremented by 1. When a system is presented with multiple BOMs with identical serial numbers, the system SHOULD use the most recent version of the BOM. The default version is '1'.", + "default": 1, + "examples": [1] + }, + "metadata": { + "$ref": "#/definitions/metadata", + "title": "BOM Metadata", + "description": "Provides additional information about a BOM." + }, + "components": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/component"}, + "uniqueItems": true, + "title": "Components", + "description": "A list of software and hardware components." + }, + "services": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/service"}, + "uniqueItems": true, + "title": "Services", + "description": "A list of services. This may include microservices, function-as-a-service, and other types of network or intra-process services." + }, + "externalReferences": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/externalReference"}, + "title": "External References", + "description": "External references provide a way to document systems, sites, and information that may be relevant but which are not included with the BOM." + }, + "dependencies": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/dependency"}, + "uniqueItems": true, + "title": "Dependencies", + "description": "Provides the ability to document dependency relationships." + }, + "compositions": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/compositions"}, + "uniqueItems": true, + "title": "Compositions", + "description": "Compositions describe constituent parts (including components, services, and dependency relationships) and their completeness." + }, + "vulnerabilities": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/vulnerability"}, + "uniqueItems": true, + "title": "Vulnerabilities", + "description": "Vulnerabilities identified in components or services." + }, + "signature": { + "$ref": "#/definitions/signature", + "title": "Signature", + "description": "Enveloped signature in [JSON Signature Format (JSF)](https://cyberphone.github.io/doc/security/jsf.html)." + } + }, + "definitions": { + "refType": { + "$comment": "Identifier-DataType for interlinked elements.", + "type": "string" + }, + "metadata": { + "type": "object", + "title": "BOM Metadata Object", + "additionalProperties": false, + "properties": { + "timestamp": { + "type": "string", + "format": "date-time", + "title": "Timestamp", + "description": "The date and time (timestamp) when the BOM was created." + }, + "tools": { + "type": "array", + "title": "Creation Tools", + "description": "The tool(s) used in the creation of the BOM.", + "additionalItems": false, + "items": {"$ref": "#/definitions/tool"} + }, + "authors" :{ + "type": "array", + "title": "Authors", + "description": "The person(s) who created the BOM. Authors are common in BOMs created through manual processes. BOMs created through automated means may not have authors.", + "additionalItems": false, + "items": {"$ref": "#/definitions/organizationalContact"} + }, + "component": { + "title": "Component", + "description": "The component that the BOM describes.", + "$ref": "#/definitions/component" + }, + "manufacture": { + "title": "Manufacture", + "description": "The organization that manufactured the component that the BOM describes.", + "$ref": "#/definitions/organizationalEntity" + }, + "supplier": { + "title": "Supplier", + "description": " The organization that supplied the component that the BOM describes. The supplier may often be the manufacturer, but may also be a distributor or repackager.", + "$ref": "#/definitions/organizationalEntity" + }, + "licenses": { + "type": "array", + "title": "BOM License(s)", + "additionalItems": false, + "items": {"$ref": "#/definitions/licenseChoice"} + }, + "properties": { + "type": "array", + "title": "Properties", + "description": "Provides the ability to document properties in a name-value store. This provides flexibility to include data not officially supported in the standard without having to use additional namespaces or create extensions. Unlike key-value stores, properties support duplicate names, each potentially having different values. Property names of interest to the general public are encouraged to be registered in the [CycloneDX Property Taxonomy](https://github.com/CycloneDX/cyclonedx-property-taxonomy). Formal registration is OPTIONAL.", + "additionalItems": false, + "items": {"$ref": "#/definitions/property"} + } + } + }, + "tool": { + "type": "object", + "title": "Tool", + "description": "Information about the automated or manual tool used", + "additionalProperties": false, + "properties": { + "vendor": { + "type": "string", + "title": "Tool Vendor", + "description": "The name of the vendor who created the tool" + }, + "name": { + "type": "string", + "title": "Tool Name", + "description": "The name of the tool" + }, + "version": { + "type": "string", + "title": "Tool Version", + "description": "The version of the tool" + }, + "hashes": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/hash"}, + "title": "Hashes", + "description": "The hashes of the tool (if applicable)." + }, + "externalReferences": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/externalReference"}, + "title": "External References", + "description": "External references provide a way to document systems, sites, and information that may be relevant but which are not included with the BOM." + } + } + }, + "organizationalEntity": { + "type": "object", + "title": "Organizational Entity Object", + "description": "", + "additionalProperties": false, + "properties": { + "name": { + "type": "string", + "title": "Name", + "description": "The name of the organization", + "examples": [ + "Example Inc." + ] + }, + "url": { + "type": "array", + "items": { + "type": "string", + "format": "iri-reference" + }, + "title": "URL", + "description": "The URL of the organization. Multiple URLs are allowed.", + "examples": ["https://example.com"] + }, + "contact": { + "type": "array", + "title": "Contact", + "description": "A contact at the organization. Multiple contacts are allowed.", + "additionalItems": false, + "items": {"$ref": "#/definitions/organizationalContact"} + } + } + }, + "organizationalContact": { + "type": "object", + "title": "Organizational Contact Object", + "description": "", + "additionalProperties": false, + "properties": { + "name": { + "type": "string", + "title": "Name", + "description": "The name of a contact", + "examples": ["Contact name"] + }, + "email": { + "type": "string", + "format": "idn-email", + "title": "Email Address", + "description": "The email address of the contact.", + "examples": ["firstname.lastname@example.com"] + }, + "phone": { + "type": "string", + "title": "Phone", + "description": "The phone number of the contact.", + "examples": ["800-555-1212"] + } + } + }, + "component": { + "type": "object", + "title": "Component Object", + "required": [ + "type", + "name" + ], + "additionalProperties": false, + "properties": { + "type": { + "type": "string", + "enum": [ + "application", + "framework", + "library", + "container", + "operating-system", + "device", + "firmware", + "file" + ], + "title": "Component Type", + "description": "Specifies the type of component. For software components, classify as application if no more specific appropriate classification is available or cannot be determined for the component. Types include:\n\n* __application__ = A software application. Refer to [https://en.wikipedia.org/wiki/Application_software](https://en.wikipedia.org/wiki/Application_software) for information about applications.\n* __framework__ = A software framework. Refer to [https://en.wikipedia.org/wiki/Software_framework](https://en.wikipedia.org/wiki/Software_framework) for information on how frameworks vary slightly from libraries.\n* __library__ = A software library. Refer to [https://en.wikipedia.org/wiki/Library_(computing)](https://en.wikipedia.org/wiki/Library_(computing))\n for information about libraries. All third-party and open source reusable components will likely be a library. If the library also has key features of a framework, then it should be classified as a framework. If not, or is unknown, then specifying library is RECOMMENDED.\n* __container__ = A packaging and/or runtime format, not specific to any particular technology, which isolates software inside the container from software outside of a container through virtualization technology. Refer to [https://en.wikipedia.org/wiki/OS-level_virtualization](https://en.wikipedia.org/wiki/OS-level_virtualization)\n* __operating-system__ = A software operating system without regard to deployment model (i.e. installed on physical hardware, virtual machine, image, etc) Refer to [https://en.wikipedia.org/wiki/Operating_system](https://en.wikipedia.org/wiki/Operating_system)\n* __device__ = A hardware device such as a processor, or chip-set. A hardware device containing firmware SHOULD include a component for the physical hardware itself, and another component of type 'firmware' or 'operating-system' (whichever is relevant), describing information about the software running on the device.\n* __firmware__ = A special type of software that provides low-level control over a devices hardware. Refer to [https://en.wikipedia.org/wiki/Firmware](https://en.wikipedia.org/wiki/Firmware)\n* __file__ = A computer file. Refer to [https://en.wikipedia.org/wiki/Computer_file](https://en.wikipedia.org/wiki/Computer_file) for information about files.", + "examples": ["library"] + }, + "mime-type": { + "type": "string", + "title": "Mime-Type", + "description": "The optional mime-type of the component. When used on file components, the mime-type can provide additional context about the kind of file being represented such as an image, font, or executable. Some library or framework components may also have an associated mime-type.", + "examples": ["image/jpeg"], + "pattern": "^[-+a-z0-9.]+/[-+a-z0-9.]+$" + }, + "bom-ref": { + "$ref": "#/definitions/refType", + "title": "BOM Reference", + "description": "An optional identifier which can be used to reference the component elsewhere in the BOM. Every bom-ref MUST be unique within the BOM." + }, + "supplier": { + "title": "Component Supplier", + "description": " The organization that supplied the component. The supplier may often be the manufacturer, but may also be a distributor or repackager.", + "$ref": "#/definitions/organizationalEntity" + }, + "author": { + "type": "string", + "title": "Component Author", + "description": "The person(s) or organization(s) that authored the component", + "examples": ["Acme Inc"] + }, + "publisher": { + "type": "string", + "title": "Component Publisher", + "description": "The person(s) or organization(s) that published the component", + "examples": ["Acme Inc"] + }, + "group": { + "type": "string", + "title": "Component Group", + "description": "The grouping name or identifier. This will often be a shortened, single name of the company or project that produced the component, or the source package or domain name. Whitespace and special characters should be avoided. Examples include: apache, org.apache.commons, and apache.org.", + "examples": ["com.acme"] + }, + "name": { + "type": "string", + "title": "Component Name", + "description": "The name of the component. This will often be a shortened, single name of the component. Examples: commons-lang3 and jquery", + "examples": ["tomcat-catalina"] + }, + "version": { + "type": "string", + "title": "Component Version", + "description": "The component version. The version should ideally comply with semantic versioning but is not enforced.", + "examples": ["9.0.14"] + }, + "description": { + "type": "string", + "title": "Component Description", + "description": "Specifies a description for the component" + }, + "scope": { + "type": "string", + "enum": [ + "required", + "optional", + "excluded" + ], + "title": "Component Scope", + "description": "Specifies the scope of the component. If scope is not specified, 'required' scope SHOULD be assumed by the consumer of the BOM.", + "default": "required" + }, + "hashes": { + "type": "array", + "title": "Component Hashes", + "additionalItems": false, + "items": {"$ref": "#/definitions/hash"} + }, + "licenses": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/licenseChoice"}, + "title": "Component License(s)" + }, + "copyright": { + "type": "string", + "title": "Component Copyright", + "description": "A copyright notice informing users of the underlying claims to copyright ownership in a published work.", + "examples": ["Acme Inc"] + }, + "cpe": { + "type": "string", + "title": "Component Common Platform Enumeration (CPE)", + "description": "Specifies a well-formed CPE name that conforms to the CPE 2.2 or 2.3 specification. See [https://nvd.nist.gov/products/cpe](https://nvd.nist.gov/products/cpe)", + "examples": ["cpe:2.3:a:acme:component_framework:-:*:*:*:*:*:*:*"] + }, + "purl": { + "type": "string", + "title": "Component Package URL (purl)", + "description": "Specifies the package-url (purl). The purl, if specified, MUST be valid and conform to the specification defined at: [https://github.com/package-url/purl-spec](https://github.com/package-url/purl-spec)", + "examples": ["pkg:maven/com.acme/tomcat-catalina@9.0.14?packaging=jar"] + }, + "swid": { + "$ref": "#/definitions/swid", + "title": "SWID Tag", + "description": "Specifies metadata and content for [ISO-IEC 19770-2 Software Identification (SWID) Tags](https://www.iso.org/standard/65666.html)." + }, + "modified": { + "type": "boolean", + "title": "Component Modified From Original", + "description": "[Deprecated] - DO NOT USE. This will be removed in a future version. Use the pedigree element instead to supply information on exactly how the component was modified. A boolean value indicating if the component has been modified from the original. A value of true indicates the component is a derivative of the original. A value of false indicates the component has not been modified from the original." + }, + "pedigree": { + "type": "object", + "title": "Component Pedigree", + "description": "Component pedigree is a way to document complex supply chain scenarios where components are created, distributed, modified, redistributed, combined with other components, etc. Pedigree supports viewing this complex chain from the beginning, the end, or anywhere in the middle. It also provides a way to document variants where the exact relation may not be known.", + "additionalProperties": false, + "properties": { + "ancestors": { + "type": "array", + "title": "Ancestors", + "description": "Describes zero or more components in which a component is derived from. This is commonly used to describe forks from existing projects where the forked version contains a ancestor node containing the original component it was forked from. For example, Component A is the original component. Component B is the component being used and documented in the BOM. However, Component B contains a pedigree node with a single ancestor documenting Component A - the original component from which Component B is derived from.", + "additionalItems": false, + "items": {"$ref": "#/definitions/component"} + }, + "descendants": { + "type": "array", + "title": "Descendants", + "description": "Descendants are the exact opposite of ancestors. This provides a way to document all forks (and their forks) of an original or root component.", + "additionalItems": false, + "items": {"$ref": "#/definitions/component"} + }, + "variants": { + "type": "array", + "title": "Variants", + "description": "Variants describe relations where the relationship between the components are not known. For example, if Component A contains nearly identical code to Component B. They are both related, but it is unclear if one is derived from the other, or if they share a common ancestor.", + "additionalItems": false, + "items": {"$ref": "#/definitions/component"} + }, + "commits": { + "type": "array", + "title": "Commits", + "description": "A list of zero or more commits which provide a trail describing how the component deviates from an ancestor, descendant, or variant.", + "additionalItems": false, + "items": {"$ref": "#/definitions/commit"} + }, + "patches": { + "type": "array", + "title": "Patches", + "description": ">A list of zero or more patches describing how the component deviates from an ancestor, descendant, or variant. Patches may be complimentary to commits or may be used in place of commits.", + "additionalItems": false, + "items": {"$ref": "#/definitions/patch"} + }, + "notes": { + "type": "string", + "title": "Notes", + "description": "Notes, observations, and other non-structured commentary describing the components pedigree." + } + } + }, + "externalReferences": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/externalReference"}, + "title": "External References", + "description": "External references provide a way to document systems, sites, and information that may be relevant but which are not included with the BOM." + }, + "components": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/component"}, + "uniqueItems": true, + "title": "Components", + "description": "A list of software and hardware components included in the parent component. This is not a dependency tree. It provides a way to specify a hierarchical representation of component assemblies, similar to system → subsystem → parts assembly in physical supply chains." + }, + "evidence": { + "$ref": "#/definitions/componentEvidence", + "title": "Evidence", + "description": "Provides the ability to document evidence collected through various forms of extraction or analysis." + }, + "releaseNotes": { + "$ref": "#/definitions/releaseNotes", + "title": "Release notes", + "description": "Specifies optional release notes." + }, + "properties": { + "type": "array", + "title": "Properties", + "description": "Provides the ability to document properties in a name-value store. This provides flexibility to include data not officially supported in the standard without having to use additional namespaces or create extensions. Unlike key-value stores, properties support duplicate names, each potentially having different values. Property names of interest to the general public are encouraged to be registered in the [CycloneDX Property Taxonomy](https://github.com/CycloneDX/cyclonedx-property-taxonomy). Formal registration is OPTIONAL.", + "additionalItems": false, + "items": {"$ref": "#/definitions/property"} + }, + "signature": { + "$ref": "#/definitions/signature", + "title": "Signature", + "description": "Enveloped signature in [JSON Signature Format (JSF)](https://cyberphone.github.io/doc/security/jsf.html)." + } + } + }, + "swid": { + "type": "object", + "title": "SWID Tag", + "description": "Specifies metadata and content for ISO-IEC 19770-2 Software Identification (SWID) Tags.", + "required": [ + "tagId", + "name" + ], + "additionalProperties": false, + "properties": { + "tagId": { + "type": "string", + "title": "Tag ID", + "description": "Maps to the tagId of a SoftwareIdentity." + }, + "name": { + "type": "string", + "title": "Name", + "description": "Maps to the name of a SoftwareIdentity." + }, + "version": { + "type": "string", + "title": "Version", + "default": "0.0", + "description": "Maps to the version of a SoftwareIdentity." + }, + "tagVersion": { + "type": "integer", + "title": "Tag Version", + "default": 0, + "description": "Maps to the tagVersion of a SoftwareIdentity." + }, + "patch": { + "type": "boolean", + "title": "Patch", + "default": false, + "description": "Maps to the patch of a SoftwareIdentity." + }, + "text": { + "title": "Attachment text", + "description": "Specifies the metadata and content of the SWID tag.", + "$ref": "#/definitions/attachment" + }, + "url": { + "type": "string", + "title": "URL", + "description": "The URL to the SWID file.", + "format": "iri-reference" + } + } + }, + "attachment": { + "type": "object", + "title": "Attachment", + "description": "Specifies the metadata and content for an attachment.", + "required": [ + "content" + ], + "additionalProperties": false, + "properties": { + "contentType": { + "type": "string", + "title": "Content-Type", + "description": "Specifies the content type of the text. Defaults to text/plain if not specified.", + "default": "text/plain" + }, + "encoding": { + "type": "string", + "title": "Encoding", + "description": "Specifies the optional encoding the text is represented in.", + "enum": [ + "base64" + ] + }, + "content": { + "type": "string", + "title": "Attachment Text", + "description": "The attachment data. Proactive controls such as input validation and sanitization should be employed to prevent misuse of attachment text." + } + } + }, + "hash": { + "type": "object", + "title": "Hash Objects", + "required": [ + "alg", + "content" + ], + "additionalProperties": false, + "properties": { + "alg": { + "$ref": "#/definitions/hash-alg" + }, + "content": { + "$ref": "#/definitions/hash-content" + } + } + }, + "hash-alg": { + "type": "string", + "enum": [ + "MD5", + "SHA-1", + "SHA-256", + "SHA-384", + "SHA-512", + "SHA3-256", + "SHA3-384", + "SHA3-512", + "BLAKE2b-256", + "BLAKE2b-384", + "BLAKE2b-512", + "BLAKE3" + ], + "title": "Hash Algorithm" + }, + "hash-content": { + "type": "string", + "title": "Hash Content (value)", + "examples": ["3942447fac867ae5cdb3229b658f4d48"], + "pattern": "^([a-fA-F0-9]{32}|[a-fA-F0-9]{40}|[a-fA-F0-9]{64}|[a-fA-F0-9]{96}|[a-fA-F0-9]{128})$" + }, + "license": { + "type": "object", + "title": "License Object", + "oneOf": [ + { + "required": ["id"] + }, + { + "required": ["name"] + } + ], + "additionalProperties": false, + "properties": { + "id": { + "$ref": "spdx.schema.json", + "title": "License ID (SPDX)", + "description": "A valid SPDX license ID", + "examples": ["Apache-2.0"] + }, + "name": { + "type": "string", + "title": "License Name", + "description": "If SPDX does not define the license used, this field may be used to provide the license name", + "examples": ["Acme Software License"] + }, + "text": { + "title": "License text", + "description": "An optional way to include the textual content of a license.", + "$ref": "#/definitions/attachment" + }, + "url": { + "type": "string", + "title": "License URL", + "description": "The URL to the license file. If specified, a 'license' externalReference should also be specified for completeness", + "examples": ["https://www.apache.org/licenses/LICENSE-2.0.txt"], + "format": "iri-reference" + } + } + }, + "licenseChoice": { + "type": "object", + "title": "License(s)", + "additionalProperties": false, + "properties": { + "license": { + "$ref": "#/definitions/license" + }, + "expression": { + "type": "string", + "title": "SPDX License Expression", + "examples": [ + "Apache-2.0 AND (MIT OR GPL-2.0-only)", + "GPL-3.0-only WITH Classpath-exception-2.0" + ] + } + }, + "oneOf":[ + { + "required": ["license"] + }, + { + "required": ["expression"] + } + ] + }, + "commit": { + "type": "object", + "title": "Commit", + "description": "Specifies an individual commit", + "additionalProperties": false, + "properties": { + "uid": { + "type": "string", + "title": "UID", + "description": "A unique identifier of the commit. This may be version control specific. For example, Subversion uses revision numbers whereas git uses commit hashes." + }, + "url": { + "type": "string", + "title": "URL", + "description": "The URL to the commit. This URL will typically point to a commit in a version control system.", + "format": "iri-reference" + }, + "author": { + "title": "Author", + "description": "The author who created the changes in the commit", + "$ref": "#/definitions/identifiableAction" + }, + "committer": { + "title": "Committer", + "description": "The person who committed or pushed the commit", + "$ref": "#/definitions/identifiableAction" + }, + "message": { + "type": "string", + "title": "Message", + "description": "The text description of the contents of the commit" + } + } + }, + "patch": { + "type": "object", + "title": "Patch", + "description": "Specifies an individual patch", + "required": [ + "type" + ], + "additionalProperties": false, + "properties": { + "type": { + "type": "string", + "enum": [ + "unofficial", + "monkey", + "backport", + "cherry-pick" + ], + "title": "Type", + "description": "Specifies the purpose for the patch including the resolution of defects, security issues, or new behavior or functionality.\n\n* __unofficial__ = A patch which is not developed by the creators or maintainers of the software being patched. Refer to [https://en.wikipedia.org/wiki/Unofficial_patch](https://en.wikipedia.org/wiki/Unofficial_patch)\n* __monkey__ = A patch which dynamically modifies runtime behavior. Refer to [https://en.wikipedia.org/wiki/Monkey_patch](https://en.wikipedia.org/wiki/Monkey_patch)\n* __backport__ = A patch which takes code from a newer version of software and applies it to older versions of the same software. Refer to [https://en.wikipedia.org/wiki/Backporting](https://en.wikipedia.org/wiki/Backporting)\n* __cherry-pick__ = A patch created by selectively applying commits from other versions or branches of the same software." + }, + "diff": { + "title": "Diff", + "description": "The patch file (or diff) that show changes. Refer to [https://en.wikipedia.org/wiki/Diff](https://en.wikipedia.org/wiki/Diff)", + "$ref": "#/definitions/diff" + }, + "resolves": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/issue"}, + "title": "Resolves", + "description": "A collection of issues the patch resolves" + } + } + }, + "diff": { + "type": "object", + "title": "Diff", + "description": "The patch file (or diff) that show changes. Refer to https://en.wikipedia.org/wiki/Diff", + "additionalProperties": false, + "properties": { + "text": { + "title": "Diff text", + "description": "Specifies the optional text of the diff", + "$ref": "#/definitions/attachment" + }, + "url": { + "type": "string", + "title": "URL", + "description": "Specifies the URL to the diff", + "format": "iri-reference" + } + } + }, + "issue": { + "type": "object", + "title": "Diff", + "description": "An individual issue that has been resolved.", + "required": [ + "type" + ], + "additionalProperties": false, + "properties": { + "type": { + "type": "string", + "enum": [ + "defect", + "enhancement", + "security" + ], + "title": "Type", + "description": "Specifies the type of issue" + }, + "id": { + "type": "string", + "title": "ID", + "description": "The identifier of the issue assigned by the source of the issue" + }, + "name": { + "type": "string", + "title": "Name", + "description": "The name of the issue" + }, + "description": { + "type": "string", + "title": "Description", + "description": "A description of the issue" + }, + "source": { + "type": "object", + "title": "Source", + "description": "The source of the issue where it is documented", + "additionalProperties": false, + "properties": { + "name": { + "type": "string", + "title": "Name", + "description": "The name of the source. For example 'National Vulnerability Database', 'NVD', and 'Apache'" + }, + "url": { + "type": "string", + "title": "URL", + "description": "The url of the issue documentation as provided by the source", + "format": "iri-reference" + } + } + }, + "references": { + "type": "array", + "items": { + "type": "string", + "format": "iri-reference" + }, + "title": "References", + "description": "A collection of URL's for reference. Multiple URLs are allowed.", + "examples": ["https://example.com"] + } + } + }, + "identifiableAction": { + "type": "object", + "title": "Identifiable Action", + "description": "Specifies an individual commit", + "additionalProperties": false, + "properties": { + "timestamp": { + "type": "string", + "format": "date-time", + "title": "Timestamp", + "description": "The timestamp in which the action occurred" + }, + "name": { + "type": "string", + "title": "Name", + "description": "The name of the individual who performed the action" + }, + "email": { + "type": "string", + "format": "idn-email", + "title": "E-mail", + "description": "The email address of the individual who performed the action" + } + } + }, + "externalReference": { + "type": "object", + "title": "External Reference", + "description": "Specifies an individual external reference", + "required": [ + "url", + "type" + ], + "additionalProperties": false, + "properties": { + "url": { + "type": "string", + "title": "URL", + "description": "The URL to the external reference", + "format": "iri-reference" + }, + "comment": { + "type": "string", + "title": "Comment", + "description": "An optional comment describing the external reference" + }, + "type": { + "type": "string", + "title": "Type", + "description": "Specifies the type of external reference. There are built-in types to describe common references. If a type does not exist for the reference being referred to, use the \"other\" type.", + "enum": [ + "vcs", + "issue-tracker", + "website", + "advisories", + "bom", + "mailing-list", + "social", + "chat", + "documentation", + "support", + "distribution", + "license", + "build-meta", + "build-system", + "release-notes", + "other" + ] + }, + "hashes": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/hash"}, + "title": "Hashes", + "description": "The hashes of the external reference (if applicable)." + } + } + }, + "dependency": { + "type": "object", + "title": "Dependency", + "description": "Defines the direct dependencies of a component. Components that do not have their own dependencies MUST be declared as empty elements within the graph. Components that are not represented in the dependency graph MAY have unknown dependencies. It is RECOMMENDED that implementations assume this to be opaque and not an indicator of a component being dependency-free.", + "required": [ + "ref" + ], + "additionalProperties": false, + "properties": { + "ref": { + "$ref": "#/definitions/refType", + "title": "Reference", + "description": "References a component by the components bom-ref attribute" + }, + "dependsOn": { + "type": "array", + "uniqueItems": true, + "additionalItems": false, + "items": { + "$ref": "#/definitions/refType" + }, + "title": "Depends On", + "description": "The bom-ref identifiers of the components that are dependencies of this dependency object." + } + } + }, + "service": { + "type": "object", + "title": "Service Object", + "required": [ + "name" + ], + "additionalProperties": false, + "properties": { + "bom-ref": { + "$ref": "#/definitions/refType", + "title": "BOM Reference", + "description": "An optional identifier which can be used to reference the service elsewhere in the BOM. Every bom-ref MUST be unique within the BOM." + }, + "provider": { + "title": "Provider", + "description": "The organization that provides the service.", + "$ref": "#/definitions/organizationalEntity" + }, + "group": { + "type": "string", + "title": "Service Group", + "description": "The grouping name, namespace, or identifier. This will often be a shortened, single name of the company or project that produced the service or domain name. Whitespace and special characters should be avoided.", + "examples": ["com.acme"] + }, + "name": { + "type": "string", + "title": "Service Name", + "description": "The name of the service. This will often be a shortened, single name of the service.", + "examples": ["ticker-service"] + }, + "version": { + "type": "string", + "title": "Service Version", + "description": "The service version.", + "examples": ["1.0.0"] + }, + "description": { + "type": "string", + "title": "Service Description", + "description": "Specifies a description for the service" + }, + "endpoints": { + "type": "array", + "items": { + "type": "string", + "format": "iri-reference" + }, + "title": "Endpoints", + "description": "The endpoint URIs of the service. Multiple endpoints are allowed.", + "examples": ["https://example.com/api/v1/ticker"] + }, + "authenticated": { + "type": "boolean", + "title": "Authentication Required", + "description": "A boolean value indicating if the service requires authentication. A value of true indicates the service requires authentication prior to use. A value of false indicates the service does not require authentication." + }, + "x-trust-boundary": { + "type": "boolean", + "title": "Crosses Trust Boundary", + "description": "A boolean value indicating if use of the service crosses a trust zone or boundary. A value of true indicates that by using the service, a trust boundary is crossed. A value of false indicates that by using the service, a trust boundary is not crossed." + }, + "data": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/dataClassification"}, + "title": "Data Classification", + "description": "Specifies the data classification." + }, + "licenses": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/licenseChoice"}, + "title": "Component License(s)" + }, + "externalReferences": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/externalReference"}, + "title": "External References", + "description": "External references provide a way to document systems, sites, and information that may be relevant but which are not included with the BOM." + }, + "services": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/service"}, + "uniqueItems": true, + "title": "Services", + "description": "A list of services included or deployed behind the parent service. This is not a dependency tree. It provides a way to specify a hierarchical representation of service assemblies." + }, + "releaseNotes": { + "$ref": "#/definitions/releaseNotes", + "title": "Release notes", + "description": "Specifies optional release notes." + }, + "properties": { + "type": "array", + "title": "Properties", + "description": "Provides the ability to document properties in a name-value store. This provides flexibility to include data not officially supported in the standard without having to use additional namespaces or create extensions. Unlike key-value stores, properties support duplicate names, each potentially having different values. Property names of interest to the general public are encouraged to be registered in the [CycloneDX Property Taxonomy](https://github.com/CycloneDX/cyclonedx-property-taxonomy). Formal registration is OPTIONAL.", + "additionalItems": false, + "items": {"$ref": "#/definitions/property"} + }, + "signature": { + "$ref": "#/definitions/signature", + "title": "Signature", + "description": "Enveloped signature in [JSON Signature Format (JSF)](https://cyberphone.github.io/doc/security/jsf.html)." + } + } + }, + "dataClassification": { + "type": "object", + "title": "Hash Objects", + "required": [ + "flow", + "classification" + ], + "additionalProperties": false, + "properties": { + "flow": { + "$ref": "#/definitions/dataFlow", + "title": "Directional Flow", + "description": "Specifies the flow direction of the data. Direction is relative to the service. Inbound flow states that data enters the service. Outbound flow states that data leaves the service. Bi-directional states that data flows both ways, and unknown states that the direction is not known." + }, + "classification": { + "type": "string", + "title": "Classification", + "description": "Data classification tags data according to its type, sensitivity, and value if altered, stolen, or destroyed." + } + } + }, + "dataFlow": { + "type": "string", + "enum": [ + "inbound", + "outbound", + "bi-directional", + "unknown" + ], + "title": "Data flow direction", + "description": "Specifies the flow direction of the data. Direction is relative to the service. Inbound flow states that data enters the service. Outbound flow states that data leaves the service. Bi-directional states that data flows both ways, and unknown states that the direction is not known." + }, + + "copyright": { + "type": "object", + "title": "Copyright", + "required": [ + "text" + ], + "additionalProperties": false, + "properties": { + "text": { + "type": "string", + "title": "Copyright Text" + } + } + }, + + "componentEvidence": { + "type": "object", + "title": "Evidence", + "description": "Provides the ability to document evidence collected through various forms of extraction or analysis.", + "additionalProperties": false, + "properties": { + "licenses": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/licenseChoice"}, + "title": "Component License(s)" + }, + "copyright": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/copyright"}, + "title": "Copyright" + } + } + }, + "compositions": { + "type": "object", + "title": "Compositions", + "required": [ + "aggregate" + ], + "additionalProperties": false, + "properties": { + "aggregate": { + "$ref": "#/definitions/aggregateType", + "title": "Aggregate", + "description": "Specifies an aggregate type that describe how complete a relationship is." + }, + "assemblies": { + "type": "array", + "uniqueItems": true, + "items": { + "type": "string" + }, + "title": "BOM references", + "description": "The bom-ref identifiers of the components or services being described. Assemblies refer to nested relationships whereby a constituent part may include other constituent parts. References do not cascade to child parts. References are explicit for the specified constituent part only." + }, + "dependencies": { + "type": "array", + "uniqueItems": true, + "items": { + "type": "string" + }, + "title": "BOM references", + "description": "The bom-ref identifiers of the components or services being described. Dependencies refer to a relationship whereby an independent constituent part requires another independent constituent part. References do not cascade to transitive dependencies. References are explicit for the specified dependency only." + }, + "signature": { + "$ref": "#/definitions/signature", + "title": "Signature", + "description": "Enveloped signature in [JSON Signature Format (JSF)](https://cyberphone.github.io/doc/security/jsf.html)." + } + } + }, + "aggregateType": { + "type": "string", + "default": "not_specified", + "enum": [ + "complete", + "incomplete", + "incomplete_first_party_only", + "incomplete_third_party_only", + "unknown", + "not_specified" + ] + }, + "property": { + "type": "object", + "title": "Lightweight name-value pair", + "properties": { + "name": { + "type": "string", + "title": "Name", + "description": "The name of the property. Duplicate names are allowed, each potentially having a different value." + }, + "value": { + "type": "string", + "title": "Value", + "description": "The value of the property." + } + } + }, + "localeType": { + "type": "string", + "pattern": "^([a-z]{2})(-[A-Z]{2})?$", + "title": "Locale", + "description": "Defines a syntax for representing two character language code (ISO-639) followed by an optional two character country code. The language code MUST be lower case. If the country code is specified, the country code MUST be upper case. The language code and country code MUST be separated by a minus sign. Examples: en, en-US, fr, fr-CA" + }, + "releaseType": { + "type": "string", + "examples": [ + "major", + "minor", + "patch", + "pre-release", + "internal" + ], + "description": "The software versioning type. It is RECOMMENDED that the release type use one of 'major', 'minor', 'patch', 'pre-release', or 'internal'. Representing all possible software release types is not practical, so standardizing on the recommended values, whenever possible, is strongly encouraged.\n\n* __major__ = A major release may contain significant changes or may introduce breaking changes.\n* __minor__ = A minor release, also known as an update, may contain a smaller number of changes than major releases.\n* __patch__ = Patch releases are typically unplanned and may resolve defects or important security issues.\n* __pre-release__ = A pre-release may include alpha, beta, or release candidates and typically have limited support. They provide the ability to preview a release prior to its general availability.\n* __internal__ = Internal releases are not for public consumption and are intended to be used exclusively by the project or manufacturer that produced it." + }, + "note": { + "type": "object", + "title": "Note", + "description": "A note containing the locale and content.", + "required": [ + "text" + ], + "additionalProperties": false, + "properties": { + "locale": { + "$ref": "#/definitions/localeType", + "title": "Locale", + "description": "The ISO-639 (or higher) language code and optional ISO-3166 (or higher) country code. Examples include: \"en\", \"en-US\", \"fr\" and \"fr-CA\"" + }, + "text": { + "title": "Release note content", + "description": "Specifies the full content of the release note.", + "$ref": "#/definitions/attachment" + } + } + }, + "releaseNotes": { + "type": "object", + "title": "Release notes", + "required": [ + "type" + ], + "additionalProperties": false, + "properties": { + "type": { + "$ref": "#/definitions/releaseType", + "title": "Type", + "description": "The software versioning type the release note describes." + }, + "title": { + "type": "string", + "title": "Title", + "description": "The title of the release." + }, + "featuredImage": { + "type": "string", + "format": "iri-reference", + "title": "Featured image", + "description": "The URL to an image that may be prominently displayed with the release note." + }, + "socialImage": { + "type": "string", + "format": "iri-reference", + "title": "Social image", + "description": "The URL to an image that may be used in messaging on social media platforms." + }, + "description": { + "type": "string", + "title": "Description", + "description": "A short description of the release." + }, + "timestamp": { + "type": "string", + "format": "date-time", + "title": "Timestamp", + "description": "The date and time (timestamp) when the release note was created." + }, + "aliases": { + "type": "array", + "items": { + "type": "string" + }, + "title": "Aliases", + "description": "One or more alternate names the release may be referred to. This may include unofficial terms used by development and marketing teams (e.g. code names)." + }, + "tags": { + "type": "array", + "items": { + "type": "string" + }, + "title": "Tags", + "description": "One or more tags that may aid in search or retrieval of the release note." + }, + "resolves": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/issue"}, + "title": "Resolves", + "description": "A collection of issues that have been resolved." + }, + "notes": { + "type": "array", + "additionalItems": false, + "items": {"$ref": "#/definitions/note"}, + "title": "Notes", + "description": "Zero or more release notes containing the locale and content. Multiple note objects may be specified to support release notes in a wide variety of languages." + }, + "properties": { + "type": "array", + "title": "Properties", + "description": "Provides the ability to document properties in a name-value store. This provides flexibility to include data not officially supported in the standard without having to use additional namespaces or create extensions. Unlike key-value stores, properties support duplicate names, each potentially having different values. Property names of interest to the general public are encouraged to be registered in the [CycloneDX Property Taxonomy](https://github.com/CycloneDX/cyclonedx-property-taxonomy). Formal registration is OPTIONAL.", + "additionalItems": false, + "items": {"$ref": "#/definitions/property"} + } + } + }, + "advisory": { + "type": "object", + "title": "Advisory", + "description": "Title and location where advisory information can be obtained. An advisory is a notification of a threat to a component, service, or system.", + "required": ["url"], + "additionalProperties": false, + "properties": { + "title": { + "type": "string", + "title": "Title", + "description": "An optional name of the advisory." + }, + "url": { + "type": "string", + "title": "URL", + "format": "iri-reference", + "description": "Location where the advisory can be obtained." + } + } + }, + "cwe": { + "type": "integer", + "minimum": 1, + "title": "CWE", + "description": "Integer representation of a Common Weaknesses Enumerations (CWE). For example 399 (of https://cwe.mitre.org/data/definitions/399.html)" + }, + "severity": { + "type": "string", + "title": "Severity", + "description": "Textual representation of the severity of the vulnerability adopted by the analysis method. If the analysis method uses values other than what is provided, the user is expected to translate appropriately.", + "enum": [ + "critical", + "high", + "medium", + "low", + "info", + "none", + "unknown" + ] + }, + "scoreMethod": { + "type": "string", + "title": "Method", + "description": "Specifies the severity or risk scoring methodology or standard used.\n\n* CVSSv2 - [Common Vulnerability Scoring System v2](https://www.first.org/cvss/v2/)\n* CVSSv3 - [Common Vulnerability Scoring System v3](https://www.first.org/cvss/v3-0/)\n* CVSSv31 - [Common Vulnerability Scoring System v3.1](https://www.first.org/cvss/v3-1/)\n* OWASP - [OWASP Risk Rating Methodology](https://owasp.org/www-community/OWASP_Risk_Rating_Methodology)", + "enum": [ + "CVSSv2", + "CVSSv3", + "CVSSv31", + "OWASP", + "other" + ] + }, + "impactAnalysisState": { + "type": "string", + "title": "Impact Analysis State", + "description": "Declares the current state of an occurrence of a vulnerability, after automated or manual analysis. \n\n* __resolved__ = the vulnerability has been remediated. \n* __resolved\\_with\\_pedigree__ = the vulnerability has been remediated and evidence of the changes are provided in the affected components pedigree containing verifiable commit history and/or diff(s). \n* __exploitable__ = the vulnerability may be directly or indirectly exploitable. \n* __in\\_triage__ = the vulnerability is being investigated. \n* __false\\_positive__ = the vulnerability is not specific to the component or service and was falsely identified or associated. \n* __not\\_affected__ = the component or service is not affected by the vulnerability. Justification should be specified for all not_affected cases.", + "enum": [ + "resolved", + "resolved_with_pedigree", + "exploitable", + "in_triage", + "false_positive", + "not_affected" + ] + }, + "impactAnalysisJustification": { + "type": "string", + "title": "Impact Analysis Justification", + "description": "The rationale of why the impact analysis state was asserted. \n\n* __code\\_not\\_present__ = the code has been removed or tree-shaked. \n* __code\\_not\\_reachable__ = the vulnerable code is not invoked at runtime. \n* __requires\\_configuration__ = exploitability requires a configurable option to be set/unset. \n* __requires\\_dependency__ = exploitability requires a dependency that is not present. \n* __requires\\_environment__ = exploitability requires a certain environment which is not present. \n* __protected\\_by\\_compiler__ = exploitability requires a compiler flag to be set/unset. \n* __protected\\_at\\_runtime__ = exploits are prevented at runtime. \n* __protected\\_at\\_perimeter__ = attacks are blocked at physical, logical, or network perimeter. \n* __protected\\_by\\_mitigating\\_control__ = preventative measures have been implemented that reduce the likelihood and/or impact of the vulnerability.", + "enum": [ + "code_not_present", + "code_not_reachable", + "requires_configuration", + "requires_dependency", + "requires_environment", + "protected_by_compiler", + "protected_at_runtime", + "protected_at_perimeter", + "protected_by_mitigating_control" + ] + }, + "rating": { + "type": "object", + "title": "Rating", + "description": "Defines the severity or risk ratings of a vulnerability.", + "additionalProperties": false, + "properties": { + "source": { + "$ref": "#/definitions/vulnerabilitySource", + "description": "The source that calculated the severity or risk rating of the vulnerability." + }, + "score": { + "type": "number", + "title": "Score", + "description": "The numerical score of the rating." + }, + "severity": { + "$ref": "#/definitions/severity", + "description": "Textual representation of the severity that corresponds to the numerical score of the rating." + }, + "method": { + "$ref": "#/definitions/scoreMethod" + }, + "vector": { + "type": "string", + "title": "Vector", + "description": "Textual representation of the metric values used to score the vulnerability" + }, + "justification": { + "type": "string", + "title": "Justification", + "description": "An optional reason for rating the vulnerability as it was" + } + } + }, + "vulnerabilitySource": { + "type": "object", + "title": "Source", + "description": "The source of vulnerability information. This is often the organization that published the vulnerability.", + "additionalProperties": false, + "properties": { + "url": { + "type": "string", + "title": "URL", + "description": "The url of the vulnerability documentation as provided by the source.", + "examples": [ + "https://nvd.nist.gov/vuln/detail/CVE-2021-39182" + ] + }, + "name": { + "type": "string", + "title": "Name", + "description": "The name of the source.", + "examples": [ + "NVD", + "National Vulnerability Database", + "OSS Index", + "VulnDB", + "GitHub Advisories" + ] + } + } + }, + "vulnerability": { + "type": "object", + "title": "Vulnerability", + "description": "Defines a weakness in an component or service that could be exploited or triggered by a threat source.", + "additionalProperties": false, + "properties": { + "bom-ref": { + "$ref": "#/definitions/refType", + "title": "BOM Reference", + "description": "An optional identifier which can be used to reference the vulnerability elsewhere in the BOM. Every bom-ref MUST be unique within the BOM." + }, + "id": { + "type": "string", + "title": "ID", + "description": "The identifier that uniquely identifies the vulnerability.", + "examples": [ + "CVE-2021-39182", + "GHSA-35m5-8cvj-8783", + "SNYK-PYTHON-ENROCRYPT-1912876" + ] + }, + "source": { + "$ref": "#/definitions/vulnerabilitySource", + "description": "The source that published the vulnerability." + }, + "references": { + "type": "array", + "title": "References", + "description": "Zero or more pointers to vulnerabilities that are the equivalent of the vulnerability specified. Often times, the same vulnerability may exist in multiple sources of vulnerability intelligence, but have different identifiers. References provide a way to correlate vulnerabilities across multiple sources of vulnerability intelligence.", + "additionalItems": false, + "items": { + "required": [ + "id", + "source" + ], + "additionalProperties": false, + "properties": { + "id": { + "type": "string", + "title": "ID", + "description": "An identifier that uniquely identifies the vulnerability.", + "examples": [ + "CVE-2021-39182", + "GHSA-35m5-8cvj-8783", + "SNYK-PYTHON-ENROCRYPT-1912876" + ] + }, + "source": { + "$ref": "#/definitions/vulnerabilitySource", + "description": "The source that published the vulnerability." + } + } + } + }, + "ratings": { + "type": "array", + "title": "Ratings", + "description": "List of vulnerability ratings", + "additionalItems": false, + "items": { + "$ref": "#/definitions/rating" + } + }, + "cwes": { + "type": "array", + "title": "CWEs", + "description": "List of Common Weaknesses Enumerations (CWEs) codes that describes this vulnerability. For example 399 (of https://cwe.mitre.org/data/definitions/399.html)", + "examples": ["399"], + "additionalItems": false, + "items": { + "$ref": "#/definitions/cwe" + } + }, + "description": { + "type": "string", + "title": "Description", + "description": "A description of the vulnerability as provided by the source." + }, + "detail": { + "type": "string", + "title": "Details", + "description": "If available, an in-depth description of the vulnerability as provided by the source organization. Details often include examples, proof-of-concepts, and other information useful in understanding root cause." + }, + "recommendation": { + "type": "string", + "title": "Details", + "description": "Recommendations of how the vulnerability can be remediated or mitigated." + }, + "advisories": { + "type": "array", + "title": "Advisories", + "description": "Published advisories of the vulnerability if provided.", + "additionalItems": false, + "items": { + "$ref": "#/definitions/advisory" + } + }, + "created": { + "type": "string", + "format": "date-time", + "title": "Created", + "description": "The date and time (timestamp) when the vulnerability record was created in the vulnerability database." + }, + "published": { + "type": "string", + "format": "date-time", + "title": "Published", + "description": "The date and time (timestamp) when the vulnerability record was first published." + }, + "updated": { + "type": "string", + "format": "date-time", + "title": "Updated", + "description": "The date and time (timestamp) when the vulnerability record was last updated." + }, + "credits": { + "type": "object", + "title": "Credits", + "description": "Individuals or organizations credited with the discovery of the vulnerability.", + "additionalProperties": false, + "properties": { + "organizations": { + "type": "array", + "title": "Organizations", + "description": "The organizations credited with vulnerability discovery.", + "additionalItems": false, + "items": { + "$ref": "#/definitions/organizationalEntity" + } + }, + "individuals": { + "type": "array", + "title": "Individuals", + "description": "The individuals, not associated with organizations, that are credited with vulnerability discovery.", + "additionalItems": false, + "items": { + "$ref": "#/definitions/organizationalContact" + } + } + } + }, + "tools": { + "type": "array", + "title": "Creation Tools", + "description": "The tool(s) used to identify, confirm, or score the vulnerability.", + "additionalItems": false, + "items": {"$ref": "#/definitions/tool"} + }, + "analysis": { + "type": "object", + "title": "Impact Analysis", + "description": "An assessment of the impact and exploitability of the vulnerability.", + "additionalProperties": false, + "properties": { + "state": { + "$ref": "#/definitions/impactAnalysisState" + }, + "justification": { + "$ref": "#/definitions/impactAnalysisJustification" + }, + "response": { + "type": "array", + "title": "Response", + "description": "A response to the vulnerability by the manufacturer, supplier, or project responsible for the affected component or service. More than one response is allowed. Responses are strongly encouraged for vulnerabilities where the analysis state is exploitable.", + "additionalItems": false, + "items": { + "type": "string", + "enum": [ + "can_not_fix", + "will_not_fix", + "update", + "rollback", + "workaround_available" + ] + } + }, + "detail": { + "type": "string", + "title": "Detail", + "description": "Detailed description of the impact including methods used during assessment. If a vulnerability is not exploitable, this field should include specific details on why the component or service is not impacted by this vulnerability." + } + } + }, + "affects": { + "type": "array", + "uniqueItems": true, + "additionalItems": false, + "items": { + "required": [ + "ref" + ], + "additionalProperties": false, + "properties": { + "ref": { + "$ref": "#/definitions/refType", + "title": "Reference", + "description": "References a component or service by the objects bom-ref" + }, + "versions": { + "type": "array", + "title": "Versions", + "description": "Zero or more individual versions or range of versions.", + "additionalItems": false, + "items": { + "oneOf": [ + { + "required": ["version"] + }, + { + "required": ["range"] + } + ], + "additionalProperties": false, + "properties": { + "version": { + "description": "A single version of a component or service.", + "$ref": "#/definitions/version" + }, + "range": { + "description": "A version range specified in Package URL Version Range syntax (vers) which is defined at https://github.com/package-url/purl-spec/VERSION-RANGE-SPEC.rst", + "$ref": "#/definitions/version" + }, + "status": { + "description": "The vulnerability status for the version or range of versions.", + "$ref": "#/definitions/affectedStatus", + "default": "affected" + } + } + } + } + } + }, + "title": "Affects", + "description": "The components or services that are affected by the vulnerability." + }, + "properties": { + "type": "array", + "title": "Properties", + "description": "Provides the ability to document properties in a name-value store. This provides flexibility to include data not officially supported in the standard without having to use additional namespaces or create extensions. Unlike key-value stores, properties support duplicate names, each potentially having different values. Property names of interest to the general public are encouraged to be registered in the [CycloneDX Property Taxonomy](https://github.com/CycloneDX/cyclonedx-property-taxonomy). Formal registration is OPTIONAL.", + "additionalItems": false, + "items": { + "$ref": "#/definitions/property" + } + } + } + }, + "affectedStatus": { + "description": "The vulnerability status of a given version or range of versions of a product. The statuses 'affected' and 'unaffected' indicate that the version is affected or unaffected by the vulnerability. The status 'unknown' indicates that it is unknown or unspecified whether the given version is affected. There can be many reasons for an 'unknown' status, including that an investigation has not been undertaken or that a vendor has not disclosed the status.", + "type": "string", + "enum": [ + "affected", + "unaffected", + "unknown" + ] + }, + "version": { + "description": "A single version of a component or service.", + "type": "string", + "minLength": 1, + "maxLength": 1024 + }, + "range": { + "description": "A version range specified in Package URL Version Range syntax (vers) which is defined at https://github.com/package-url/purl-spec/VERSION-RANGE-SPEC.rst", + "type": "string", + "minLength": 1, + "maxLength": 1024 + }, + "signature": { + "$ref": "jsf-0.82.schema.json#/definitions/signature", + "title": "Signature", + "description": "Enveloped signature in [JSON Signature Format (JSF)](https://cyberphone.github.io/doc/security/jsf.html)." + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/cyclonedx.xsd b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/cyclonedx.xsd new file mode 100644 index 0000000000000000000000000000000000000000..f9859c78910bf95688b743c92563c9ff09e69ba4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/cyclonedx.xsd @@ -0,0 +1,2407 @@ + + + + + + + + + CycloneDX Software Bill of Materials Standard + https://cyclonedx.org/ + Apache License, Version 2.0 + + + + + + Identifier-DataType for interlinked elements. + + + + + + + + + The date and time (timestamp) when the BOM was created. + + + + + The tool(s) used in the creation of the BOM. + + + + + + + + + + The person(s) who created the BOM. Authors are common in BOMs created through + manual processes. BOMs created through automated means may not have authors. + + + + + + + + + + The component that the BOM describes. + + + + + The organization that manufactured the component that the BOM describes. + + + + + The organization that supplied the component that the BOM describes. The + supplier may often be the manufacturer, but may also be a distributor or repackager. + + + + + + Provides the ability to document properties in a key/value store. + This provides flexibility to include data not officially supported in the standard + without having to use additional namespaces or create extensions. Property names + of interest to the general public are encouraged to be registered in the + CycloneDX Property Taxonomy - https://github.com/CycloneDX/cyclonedx-property-taxonomy. + Formal registration is OPTIONAL. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + The name of the organization + + + + + The URL of the organization. Multiple URLs are allowed. + + + + + A contact person at the organization. Multiple contacts are allowed. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + Information about the automated or manual tool used + + + + + The name of the vendor who created the tool + + + + + The name of the tool + + + + + The version of the tool + + + + + + + + + + + + Provides the ability to document external references related to the tool. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + The name of the contact + + + + + The email address of the contact. + + + + + The phone number of the contact. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + The organization that supplied the component. The supplier may often + be the manufacturer, but may also be a distributor or repackager. + + + + + The person(s) or organization(s) that authored the component + + + + + The person(s) or organization(s) that published the component + + + + + The grouping name or identifier. This will often be a shortened, single + name of the company or project that produced the component, or the source package or + domain name. Whitespace and special characters should be avoided. Examples include: + apache, org.apache.commons, and apache.org. + + + + + The name of the component. This will often be a shortened, single name + of the component. Examples: commons-lang3 and jquery + + + + + The component version. The version should ideally comply with semantic versioning + but is not enforced. + + + + + Specifies a description for the component + + + + + Specifies the scope of the component. If scope is not specified, 'required' + scope SHOULD be assumed by the consumer of the BOM. + + + + + + + + + + + + + A copyright notice informing users of the underlying claims to + copyright ownership in a published work. + + + + + + Specifies a well-formed CPE name that conforms to the CPE 2.2 or 2.3 specification. See https://nvd.nist.gov/products/cpe + + + + + + + Specifies the package-url (purl). The purl, if specified, MUST be valid and conform + to the specification defined at: https://github.com/package-url/purl-spec + + + + + + + Specifies metadata and content for ISO-IEC 19770-2 Software Identification (SWID) Tags. + + + + + + + DEPRECATED - DO NOT USE. This will be removed in a future version. Use the pedigree + element instead to supply information on exactly how the component was modified. + A boolean value indicating if the component has been modified from the original. + A value of true indicates the component is a derivative of the original. + A value of false indicates the component has not been modified from the original. + + + + + + + Component pedigree is a way to document complex supply chain scenarios where components are + created, distributed, modified, redistributed, combined with other components, etc. + + + + + + Provides the ability to document external references related to the + component or to the project the component describes. + + + + + Provides the ability to document properties in a key/value store. + This provides flexibility to include data not officially supported in the standard + without having to use additional namespaces or create extensions. Property names + of interest to the general public are encouraged to be registered in the + CycloneDX Property Taxonomy - https://github.com/CycloneDX/cyclonedx-property-taxonomy. + Formal registration is OPTIONAL. + + + + + + A list of software and hardware components included in the parent component. This is not a + dependency tree. It provides a way to specify a hierarchical representation of component + assemblies, similar to system -> subsystem -> parts assembly in physical supply chains. + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + Provides the ability to document evidence collected through various forms of extraction or analysis. + + + + + Specifies optional release notes. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + Specifies the type of component. For software components, classify as application if no more + specific appropriate classification is available or cannot be determined for the component. + + + + + + + The OPTIONAL mime-type of the component. When used on file components, the mime-type + can provide additional context about the kind of file being represented such as an image, + font, or executable. Some library or framework components may also have an associated mime-type. + + + + + + + An optional identifier which can be used to reference the component elsewhere in the BOM. + Uniqueness is enforced within all elements and children of the root-level bom element. + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + + A valid SPDX license ID + + + + + If SPDX does not define the license used, this field may be used to provide the license name + + + + + + Specifies the optional full text of the attachment + + + + + The URL to the attachment file. If the attachment is a license or BOM, + an externalReference should also be specified for completeness. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + + + The attachment data. Proactive controls such as input validation and sanitization should be employed to prevent misuse of attachment text. + + + + Specifies the content type of the text. Defaults to text/plain + if not specified. + + + + + + Specifies the optional encoding the text is represented in + + + + + + + + + + Specifies the file hash of the component + + + + + + Specifies the algorithm used to create the hash + + + + + + + + + + + The component is required for runtime + + + + + The component is optional at runtime. Optional components are components that + are not capable of being called due to them not be installed or otherwise accessible by any means. + Components that are installed but due to configuration or other restrictions are prohibited from + being called must be scoped as 'required'. + + + + + Components that are excluded provide the ability to document component usage + for test and other non-runtime purposes. Excluded components are not reachable within a call + graph at runtime. + + + + + + + + + + A software application. Refer to https://en.wikipedia.org/wiki/Application_software + for information about applications. + + + + + A software framework. Refer to https://en.wikipedia.org/wiki/Software_framework + for information on how frameworks vary slightly from libraries. + + + + + A software library. Refer to https://en.wikipedia.org/wiki/Library_(computing) + for information about libraries. All third-party and open source reusable components will likely + be a library. If the library also has key features of a framework, then it should be classified + as a framework. If not, or is unknown, then specifying library is recommended. + + + + + A packaging and/or runtime format, not specific to any particular technology, + which isolates software inside the container from software outside of a container through + virtualization technology. Refer to https://en.wikipedia.org/wiki/OS-level_virtualization + + + + + A software operating system without regard to deployment model + (i.e. installed on physical hardware, virtual machine, image, etc) Refer to + https://en.wikipedia.org/wiki/Operating_system + + + + + A hardware device such as a processor, or chip-set. A hardware device + containing firmware SHOULD include a component for the physical hardware itself, and another + component of type 'firmware' or 'operating-system' (whichever is relevant), describing + information about the software running on the device. + + + + + A special type of software that provides low-level control over a devices + hardware. Refer to https://en.wikipedia.org/wiki/Firmware + + + + + A computer file. Refer to https://en.wikipedia.org/wiki/Computer_file + for information about files. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Define the format for acceptable CPE URIs. Supports CPE 2.2 and CPE 2.3 formats. + Refer to https://nvd.nist.gov/products/cpe for official specification. + + + + + + + + + + + + Specifies the full content of the SWID tag. + + + + + The URL to the SWID file. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + Maps to the tagId of a SoftwareIdentity. + + + + + Maps to the name of a SoftwareIdentity. + + + + + Maps to the version of a SoftwareIdentity. + + + + + Maps to the tagVersion of a SoftwareIdentity. + + + + + Maps to the patch of a SoftwareIdentity. + + + + + + + + Defines a string representation of a UUID conforming to RFC 4122. + + + + + + + + + + + + Version Control System + + + + + Issue or defect tracking system, or an Application Lifecycle Management (ALM) system + + + + + Website + + + + + Security advisories + + + + + Bill-of-material document (CycloneDX, SPDX, SWID, etc) + + + + + Mailing list or discussion group + + + + + Social media account + + + + + Real-time chat platform + + + + + Documentation, guides, or how-to instructions + + + + + Community or commercial support + + + + + Direct or repository download location + + + + + The URL to the license file. If a license URL has been defined in the license + node, it should also be defined as an external reference for completeness + + + + + Build-system specific meta file (i.e. pom.xml, package.json, .nuspec, etc) + + + + + URL to an automated build system + + + + + URL to release notes + + + + + Use this if no other types accurately describe the purpose of the external reference + + + + + + + + + External references provide a way to document systems, sites, and information that may be relevant + but which are not included with the BOM. + + + + + + Zero or more external references can be defined + + + + + + + + + + The URL to the external reference + + + + + An optional comment describing the external reference + + + + + + + + + + + + + Specifies the type of external reference. There are built-in types to describe common + references. If a type does not exist for the reference being referred to, use the "other" type. + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + Zero or more commits can be specified. + + + + + Specifies an individual commit. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + + + A unique identifier of the commit. This may be version control + specific. For example, Subversion uses revision numbers whereas git uses commit hashes. + + + + + + The URL to the commit. This URL will typically point to a commit + in a version control system. + + + + + + The author who created the changes in the commit + + + + + The person who committed or pushed the commit + + + + + The text description of the contents of the commit + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + Zero or more patches can be specified. + + + + + Specifies an individual patch. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + + + The patch file (or diff) that show changes. + Refer to https://en.wikipedia.org/wiki/Diff + + + + + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + Specifies the purpose for the patch including the resolution of defects, + security issues, or new behavior or functionality + + + + + + + + + A patch which is not developed by the creators or maintainers of the software + being patched. Refer to https://en.wikipedia.org/wiki/Unofficial_patch + + + + + A patch which dynamically modifies runtime behavior. + Refer to https://en.wikipedia.org/wiki/Monkey_patch + + + + + A patch which takes code from a newer version of software and applies + it to older versions of the same software. Refer to https://en.wikipedia.org/wiki/Backporting + + + + + A patch created by selectively applying commits from other versions or + branches of the same software. + + + + + + + + + + A fault, flaw, or bug in software + + + + + A new feature or behavior in software + + + + + A special type of defect which impacts security + + + + + + + + + + Specifies the optional text of the diff + + + + + Specifies the URL to the diff + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + + An individual issue that has been resolved. + + + + + + The identifier of the issue assigned by the source of the issue + + + + + The name of the issue + + + + + A description of the issue + + + + + + + The source of the issue where it is documented. + + + + + + + The name of the source. For example "National Vulnerability Database", + "NVD", and "Apache" + + + + + + + The url of the issue documentation as provided by the source + + + + + + + + + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + Specifies the type of issue + + + + + + + + + The timestamp in which the action occurred + + + + + The name of the individual who performed the action + + + + + The email address of the individual who performed the action + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + + Component pedigree is a way to document complex supply chain scenarios where components are created, + distributed, modified, redistributed, combined with other components, etc. Pedigree supports viewing + this complex chain from the beginning, the end, or anywhere in the middle. It also provides a way to + document variants where the exact relation may not be known. + + + + + + Describes zero or more components in which a component is derived + from. This is commonly used to describe forks from existing projects where the forked version + contains a ancestor node containing the original component it was forked from. For example, + Component A is the original component. Component B is the component being used and documented + in the BOM. However, Component B contains a pedigree node with a single ancestor documenting + Component A - the original component from which Component B is derived from. + + + + + + Descendants are the exact opposite of ancestors. This provides a + way to document all forks (and their forks) of an original or root component. + + + + + + Variants describe relations where the relationship between the + components are not known. For example, if Component A contains nearly identical code to + Component B. They are both related, but it is unclear if one is derived from the other, + or if they share a common ancestor. + + + + + + A list of zero or more commits which provide a trail describing + how the component deviates from an ancestor, descendant, or variant. + + + + + A list of zero or more patches describing how the component + deviates from an ancestor, descendant, or variant. Patches may be complimentary to commits + or may be used in place of commits. + + + + + Notes, observations, and other non-structured commentary + describing the components pedigree. + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + + + + + References a component or service by the its bom-ref attribute + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + Components that do not have their own dependencies MUST be declared as empty + elements within the graph. Components that are not represented in the dependency graph MAY + have unknown dependencies. It is RECOMMENDED that implementations assume this to be opaque + and not an indicator of a component being dependency-free. + + + + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + The organization that provides the service. + + + + + The grouping name, namespace, or identifier. This will often be a shortened, + single name of the company or project that produced the service or domain name. + Whitespace and special characters should be avoided. + + + + + The name of the service. This will often be a shortened, single name + of the service. + + + + + The service version. + + + + + Specifies a description for the service. + + + + + + + + A service endpoint URI. + + + + + + + + A boolean value indicating if the service requires authentication. + A value of true indicates the service requires authentication prior to use. + A value of false indicates the service does not require authentication. + + + + + A boolean value indicating if use of the service crosses a trust zone or boundary. + A value of true indicates that by using the service, a trust boundary is crossed. + A value of false indicates that by using the service, a trust boundary is not crossed. + + + + + + + + Specifies the data classification. + + + + + + + + + Provides the ability to document external references related to the service. + + + + + Provides the ability to document properties in a key/value store. + This provides flexibility to include data not officially supported in the standard + without having to use additional namespaces or create extensions. Property names + of interest to the general public are encouraged to be registered in the + CycloneDX Property Taxonomy - https://github.com/CycloneDX/cyclonedx-property-taxonomy. + Formal registration is OPTIONAL. + + + + + + A list of services included or deployed behind the parent service. This is not a dependency + tree. It provides a way to specify a hierarchical representation of service assemblies. + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + Specifies optional release notes. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + An optional identifier which can be used to reference the service elsewhere in the BOM. + Uniqueness is enforced within all elements and children of the root-level bom element. + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + Specifies the data classification. + + + + + + Specifies the flow direction of the data. + + + + + + + + + Specifies the flow direction of the data. Valid values are: + inbound, outbound, bi-directional, and unknown. Direction is relative to the service. + Inbound flow states that data enters the service. Outbound flow states that data + leaves the service. Bi-directional states that data flows both ways, and unknown + states that the direction is not known. + + + + + + + + + + + + + + + A valid SPDX license expression. + Refer to https://spdx.org/specifications for syntax requirements + + + + + + + + + + + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + Specifies an aggregate type that describe how complete a relationship is. + + + + + + The bom-ref identifiers of the components or services being described. Assemblies refer to + nested relationships whereby a constituent part may include other constituent parts. References + do not cascade to child parts. References are explicit for the specified constituent part only. + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + + The bom-ref identifiers of the components or services being described. Dependencies refer to a + relationship whereby an independent constituent part requires another independent constituent + part. References do not cascade to transitive dependencies. References are explicit for the + specified dependency only. + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + + + + + + The relationship is complete. No further relationships including constituent components, services, or dependencies exist. + + + + + The relationship is incomplete. Additional relationships exist and may include constituent components, services, or dependencies. + + + + + The relationship is incomplete. Only relationships for first-party components, services, or their dependencies are represented. + + + + + The relationship is incomplete. Only relationships for third-party components, services, or their dependencies are represented. + + + + + The relationship may be complete or incomplete. This usually signifies a 'best-effort' to obtain constituent components, services, or dependencies but the completeness is inconclusive. + + + + + The relationship completeness is not specified. + + + + + + + + + Defines a syntax for representing two character language code (ISO-639) followed by an optional two + character country code. The language code MUST be lower case. If the country code is specified, the + country code MUST be upper case. The language code and country code MUST be separated by a minus sign. + Examples: en, en-US, fr, fr-CA + + + + + + + + + + + + The software versioning type. It is RECOMMENDED that the release type use one + of 'major', 'minor', 'patch', 'pre-release', or 'internal'. Representing all possible software + release types is not practical, so standardizing on the recommended values, whenever possible, + is strongly encouraged. + * major = A major release may contain significant changes or may introduce breaking changes. + * minor = A minor release, also known as an update, may contain a smaller number of changes than major releases. + * patch = Patch releases are typically unplanned and may resolve defects or important security issues. + * pre-release = A pre-release may include alpha, beta, or release candidates and typically have + limited support. They provide the ability to preview a release prior to its general availability. + * internal = Internal releases are not for public consumption and are intended to be used exclusively + by the project or manufacturer that produced it. + + + + + + The title of the release. + + + + + The URL to an image that may be prominently displayed with the release note. + + + + + The URL to an image that may be used in messaging on social media platforms. + + + + + A short description of the release. + + + + + The date and time (timestamp) when the release note was created. + + + + + + + + One or more alternate names the release may be referred to. This may + include unofficial terms used by development and marketing teams (e.g. code names). + + + + + + + + + + + One or more tags that may aid in search or retrieval of the release note. + + + + + + + + A collection of issues that have been resolved. + + + + + + + + + + + + + Zero or more release notes containing the locale and content. Multiple + note elements may be specified to support release notes in a wide variety of languages. + + + + + + The ISO-639 (or higher) language code and optional ISO-3166 + (or higher) country code. Examples include: "en", "en-US", "fr" and "fr-CA". + + + + + Specifies the full content of the release note. + + + + + + + + + + + Provides the ability to document properties in a key/value store. + This provides flexibility to include data not officially supported in the standard + without having to use additional namespaces or create extensions. Property names + of interest to the general public are encouraged to be registered in the + CycloneDX Property Taxonomy - https://github.com/CycloneDX/cyclonedx-property-taxonomy. + Formal registration is OPTIONAL. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + References a component or service by the its bom-ref attribute + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + Specifies an individual property with a name and value. + + + + + + The name of the property. Duplicate names are allowed, each potentially having a different value. + + + + + + + + + + + Defines a weakness in an component or service that could be exploited or triggered by a threat source. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + The identifier that uniquely identifies the vulnerability. For example: + CVE-2021-39182, GHSA-35m5-8cvj-8783, and SNYK-PYTHON-ENROCRYPT-1912876. + + + + + The source that published the vulnerability. + + + + + Zero or more pointers to vulnerabilities that are the equivalent of the + vulnerability specified. Often times, the same vulnerability may exist in multiple sources of + vulnerability intelligence, but have different identifiers. References provide a way to + correlate vulnerabilities across multiple sources of vulnerability intelligence. + + + + + + A pointer to a vulnerability that is the equivalent of the + vulnerability specified. + + + + + + The identifier that uniquely identifies the vulnerability. For example: + CVE-2021-39182, GHSA-35m5-8cvj-8783, and SNYK-PYTHON-ENROCRYPT-1912876. + + + + + The source that published the vulnerability. + + + + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + + + List of vulnerability ratings. + + + + + + + + + + + + List of Common Weaknesses Enumerations (CWEs) codes that describes this vulnerability. + For example 399 (of https://cwe.mitre.org/data/definitions/399.html) + + + + + + + + + + A description of the vulnerability as provided by the source. + + + + + If available, an in-depth description of the vulnerability as provided by the + source organization. Details often include examples, proof-of-concepts, and other information + useful in understanding root cause. + + + + + Recommendations of how the vulnerability can be remediated or mitigated. + + + + + + + Published advisories of the vulnerability if provided. + + + + + + + + + + The date and time (timestamp) when the vulnerability record was created in the vulnerability database. + + + + + The date and time (timestamp) when the vulnerability record was first published. + + + + + The date and time (timestamp) when the vulnerability record was last updated. + + + + + Individuals or organizations credited with the discovery of the vulnerability. + + + + + + The organizations credited with vulnerability discovery. + + + + + + + + + + The individuals, not associated with organizations, that are credited with vulnerability discovery. + + + + + + + + + + + + + The tool(s) used to identify, confirm, or score the vulnerability. + + + + + + + + + + + + An assessment of the impact and exploitability of the vulnerability. + + + + + + + Declares the current state of an occurrence of a vulnerability, after automated or manual analysis. + + + + + + + The rationale of why the impact analysis state was asserted. + + + + + + A response to the vulnerability by the manufacturer, supplier, or + project responsible for the affected component or service. More than one response + is allowed. Responses are strongly encouraged for vulnerabilities where the analysis + state is exploitable. + + + + + + + + + + + Detailed description of the impact including methods used during assessment. + If a vulnerability is not exploitable, this field should include specific details + on why the component or service is not impacted by this vulnerability. + + + + + + + + + The components or services that are affected by the vulnerability. + + + + + + + + + References a component or service by the objects bom-ref. + + + + + Zero or more individual versions or range of versions. + + + + + + + + + + A single version of a component or service. + + + + + A version range specified in Package URL Version Range syntax (vers) which is defined at https://github.com/package-url/purl-spec/VERSION-RANGE-SPEC.rst + + + + + + + The vulnerability status for the version or range of versions. + + + + + + + + + + + + + + + + + + + + An optional identifier which can be used to reference the vulnerability elsewhere in the BOM. + Uniqueness is enforced within all elements and children of the root-level bom element. + + + + + + + + + + The name of the source. + For example: NVD, National Vulnerability Database, OSS Index, VulnDB, and GitHub Advisories + + + + + + The url of the vulnerability documentation as provided by the source. + For example: https://nvd.nist.gov/vuln/detail/CVE-2021-39182 + + + + + + + + + + The source that calculated the severity or risk rating of the vulnerability. + + + + + The numerical score of the rating. + + + + + Textual representation of the severity that corresponds to the numerical score of the rating. + + + + + The risk scoring methodology/standard used. + + + + + Textual representation of the metric values used to score the vulnerability. + + + + + An optional reason for rating the vulnerability as it was. + + + + + + + + + + An optional name of the advisory. + + + + + Location where the advisory can be obtained. + + + + + + + + + Textual representation of the severity of the vulnerability adopted by the analysis method. If the + analysis method uses values other than what is provided, the user is expected to translate appropriately. + + + + + + + + + + + + + + + + + Declares the current state of an occurrence of a vulnerability, after automated or manual analysis. + + + + + + + The vulnerability has been remediated. + + + + + + + The vulnerability has been remediated and evidence of the changes are provided in the affected + components pedigree containing verifiable commit history and/or diff(s). + + + + + + + The vulnerability may be directly or indirectly exploitable. + + + + + + + The vulnerability is being investigated. + + + + + + + The vulnerability is not specific to the component or service and was falsely identified or associated. + + + + + + + The component or service is not affected by the vulnerability. Justification should be specified + for all not_affected cases. + + + + + + + + + + The rationale of why the impact analysis state was asserted. + + + + + + + The code has been removed or tree-shaked. + + + + + + + The vulnerable code is not invoked at runtime. + + + + + + + Exploitability requires a configurable option to be set/unset. + + + + + + + Exploitability requires a dependency that is not present. + + + + + + + Exploitability requires a certain environment which is not present. + + + + + + + Exploitability requires a compiler flag to be set/unset. + + + + + + + Exploits are prevented at runtime. + + + + + + + Attacks are blocked at physical, logical, or network perimeter. + + + + + + + Preventative measures have been implemented that reduce the likelihood and/or impact of the vulnerability. + + + + + + + + + + Specifies the severity or risk scoring methodology or standard used. + + + + + + + The rating is based on CVSS v2 standard + https://www.first.org/cvss/v2/ + + + + + + + The rating is based on CVSS v3.0 standard + https://www.first.org/cvss/v3-0/ + + + + + + + The rating is based on CVSS v3.1 standard + https://www.first.org/cvss/v3-1/ + + + + + + + The rating is based on OWASP Risk Rating + https://owasp.org/www-community/OWASP_Risk_Rating_Methodology + + + + + + + Use this if the risk scoring methodology is not based on any of the options above + + + + + + + + + + The rationale of why the impact analysis state was asserted. + + + + + + + + + + + + + + + The vulnerability status of a given version or range of versions of a product. The statuses + 'affected' and 'unaffected' indicate that the version is affected or unaffected by the vulnerability. + The status 'unknown' indicates that it is unknown or unspecified whether the given version is affected. + There can be many reasons for an 'unknown' status, including that an investigation has not been + undertaken or that a vendor has not disclosed the status. + + + + + + + + + + + + + + + + Provides additional information about a BOM. + + + + + A list of software and hardware components. + + + + + A list of services. This may include microservices, function-as-a-service, and other types of network or intra-process services. + + + + + Provides the ability to document external references related to the BOM or + to the project the BOM describes. + + + + + Provides the ability to document dependency relationships. + + + + + Compositions describe constituent parts (including components, services, and dependency relationships) and their completeness. + + + + + Provides the ability to document properties in a key/value store. + This provides flexibility to include data not officially supported in the standard + without having to use additional namespaces or create extensions. Property names + of interest to the general public are encouraged to be registered in the + CycloneDX Property Taxonomy - https://github.com/CycloneDX/cyclonedx-property-taxonomy. + Formal registration is OPTIONAL. + + + + + Vulnerabilities identified in components or services. + + + + + + Allows any undeclared elements as long as the elements are placed in a different namespace. + + + + + + + Whenever an existing BOM is modified, either manually or through automated + processes, the version of the BOM SHOULD be incremented by 1. When a system is presented with + multiple BOMs with identical serial numbers, the system SHOULD use the most recent version of the BOM. + The default version is '1'. + + + + + Every BOM generated SHOULD have a unique serial number, even if the contents of + the BOM have not changed over time. If specified, the serial number MUST conform to RFC-4122. + Use of serial numbers are RECOMMENDED. + + + + + User-defined attributes may be used on this element as long as they + do not have the same name as an existing attribute used by the schema. + + + + + + + + + diff --git a/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/spdx.xsd b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/spdx.xsd new file mode 100644 index 0000000000000000000000000000000000000000..66ba6f199e71d4871167eefab023463783b06308 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/cyclonedx/spdx.xsd @@ -0,0 +1,2639 @@ + + + + + + + + + Interbase Public License v1.0 + + + + + Mup License + + + + + GNU General Public License v2.0 w/Autoconf exception + + + + + Open LDAP Public License v2.1 + + + + + Creative Commons Attribution Non Commercial Share Alike 3.0 IGO + + + + + GNU Library General Public License v2 or later + + + + + XPP License + + + + + SIL Open Font License 1.1 + + + + + CNRI Python License + + + + + Linux man-pages Copyleft + + + + + Open LDAP Public License v2.2 + + + + + Open Software License 1.1 + + + + + Eclipse Public License 2.0 + + + + + Academic Free License v1.1 + + + + + Affero General Public License v1.0 or later + + + + + Good Luck With That Public License + + + + + MIT License Modern Variant + + + + + BSD 1-Clause License + + + + + SGI Free Software License B v1.0 + + + + + Open Market License + + + + + psfrag License + + + + + Artistic License 1.0 + + + + + Creative Commons Public Domain Dedication and Certification + + + + + eGenix.com Public License 1.1.0 + + + + + European Union Public License 1.1 + + + + + Sendmail License + + + + + Python Software Foundation License 2.0 + + + + + Open Government Licence v1.0 + + + + + Matrix Template Library License + + + + + Nara Institute of Science and Technology License (2003) + + + + + ANTLR Software Rights Notice with license fallback + + + + + PostgreSQL License + + + + + Open Software License 1.0 + + + + + Nethack General Public License + + + + + Creative Commons Attribution Non Commercial No Derivatives 4.0 International + + + + + Code Project Open License 1.02 + + + + + FSF Unlimited License (with License Retention) + + + + + GNU Free Documentation License v1.2 only - no invariants + + + + + Net-SNMP License + + + + + Amazon Digital Services License + + + + + Sendmail License 8.23 + + + + + CNRI Jython License + + + + + Reciprocal Public License 1.5 + + + + + BSD-2-Clause Plus Patent License + + + + + SIL Open Font License 1.1 with no Reserved Font Name + + + + + Apple Public Source License 1.2 + + + + + Open LDAP Public License v2.4 + + + + + Mozilla Public License 2.0 (no copyleft exception) + + + + + ISC License + + + + + Creative Commons Attribution Share Alike 2.5 Generic + + + + + Sleepycat License + + + + + CUA Office Public License v1.0 + + + + + Frameworx Open License 1.0 + + + + + Common Public Attribution License 1.0 + + + + + Norwegian Licence for Open Government Data (NLOD) 2.0 + + + + + Creative Commons Attribution Non Commercial 2.0 Generic + + + + + GNU Free Documentation License v1.1 or later - no invariants + + + + + Creative Commons Attribution 2.5 Generic + + + + + Newsletr License + + + + + The Parity Public License 7.0.0 + + + + + Leptonica License + + + + + CMU License + + + + + Adobe Postscript AFM License + + + + + Creative Commons Attribution Non Commercial 2.5 Generic + + + + + Cryptographic Autonomy License 1.0 (Combined Work Exception) + + + + + BSD 4 Clause Shortened + + + + + Netscape Public License v1.1 + + + + + Qhull License + + + + + CeCILL-C Free Software License Agreement + + + + + GNU General Public License v1.0 only + + + + + Creative Commons Attribution Non Commercial No Derivatives 3.0 Germany + + + + + Creative Commons Attribution Non Commercial Share Alike 3.0 Unported + + + + + Creative Commons Attribution Non Commercial Share Alike 1.0 Generic + + + + + MIT Open Group variant + + + + + Multics License + + + + + Scheme Widget Library (SWL) Software License Agreement + + + + + GNU General Public License v1.0 or later + + + + + GNU General Public License v3.0 or later + + + + + DOC License + + + + + PHP License v3.0 + + + + + Sun Industry Standards Source License v1.2 + + + + + Common Documentation License 1.0 + + + + + Lucent Public License Version 1.0 + + + + + Red Hat eCos Public License v1.1 + + + + + Licence Art Libre 1.3 + + + + + Creative Commons Attribution Share Alike 3.0 Germany + + + + + Community Data License Agreement Permissive 1.0 + + + + + gnuplot License + + + + + App::s2p License + + + + + iMatix Standard Function Library Agreement + + + + + Microsoft Public License + + + + + eCos license version 2.0 + + + + + BSD 3-Clause "New" or "Revised" License + + + + + Creative Commons Attribution Non Commercial No Derivatives 3.0 IGO + + + + + ICU License + + + + + GNU Affero General Public License v3.0 or later + + + + + Creative Commons Attribution Share Alike 2.1 Japan + + + + + Creative Commons Attribution Non Commercial Share Alike 4.0 International + + + + + The Unlicense + + + + + Creative Commons Attribution Non Commercial 3.0 Germany + + + + + Open LDAP Public License v1.4 + + + + + CERN Open Hardware Licence Version 2 - Weakly Reciprocal + + + + + SugarCRM Public License v1.1.3 + + + + + IPA Font License + + + + + Academic Free License v2.0 + + + + + Unicode License Agreement - Data Files and Software (2016) + + + + + Creative Commons Attribution Non Commercial No Derivatives 3.0 Unported + + + + + CERN Open Hardware Licence Version 2 - Permissive + + + + + Creative Commons Attribution Non Commercial 3.0 Unported + + + + + Copyfree Open Innovation License + + + + + Cryptographic Autonomy License 1.0 + + + + + Licence Libre du Québec – Permissive version 1.1 + + + + + SIL Open Font License 1.1 with Reserved Font Name + + + + + Lucent Public License v1.02 + + + + + Open LDAP Public License v1.3 + + + + + Taiwan Open Government Data License, version 1.0 + + + + + Creative Commons Attribution Non Commercial Share Alike 2.0 Generic + + + + + Python License 2.0 + + + + + NTP No Attribution + + + + + FSF All Permissive License + + + + + Erlang Public License v1.1 + + + + + Barr License + + + + + Creative Commons Attribution 3.0 United States + + + + + BSD 3-Clause No Nuclear License 2014 + + + + + No Limit Public License + + + + + BSD 3-Clause Clear License + + + + + SGI Free Software License B v1.1 + + + + + Open Data Commons Public Domain Dedication & License 1.0 + + + + + Common Development and Distribution License 1.0 + + + + + GNU Lesser General Public License v2.1 or later + + + + + Blue Oak Model License 1.0.0 + + + + + Creative Commons Attribution-NonCommercial-ShareAlike 2.0 France + + + + + Fraunhofer FDK AAC Codec Library + + + + + Standard ML of New Jersey License + + + + + Affero General Public License v1.0 only + + + + + CeCILL Free Software License Agreement v1.0 + + + + + Attribution Assurance License + + + + + GNU General Public License v2.0 w/Font exception + + + + + Info-ZIP License + + + + + SSH OpenSSH license + + + + + SSH short notice + + + + + GNU General Public License v2.0 or later + + + + + Clarified Artistic License + + + + + SNIA Public License 1.1 + + + + + GNU Free Documentation License v1.1 only - invariants + + + + + BSD 3-Clause No Military License + + + + + GNU Free Documentation License v1.1 + + + + + Mozilla Public License 1.1 + + + + + Open LDAP Public License v1.1 + + + + + JSON License + + + + + GNU Free Documentation License v1.3 only - no invariants + + + + + OCLC Research Public License 2.0 + + + + + Open LDAP Public License v2.0.1 + + + + + FreeBSD Documentation License + + + + + GNU General Public License v1.0 or later + + + + + Yahoo! Public License v1.1 + + + + + Common Public License 1.0 + + + + + Apache License 1.0 + + + + + SIL Open Font License 1.0 + + + + + Creative Commons Attribution 4.0 International + + + + + DSDP License + + + + + IBM PowerPC Initialization and Boot Software + + + + + MIT No Attribution + + + + + Detection Rule License 1.0 + + + + + zlib License + + + + + Adaptive Public License 1.0 + + + + + Sybase Open Watcom Public License 1.0 + + + + + GNU General Public License v2.0 w/GCC Runtime Library exception + + + + + European Union Public License 1.2 + + + + + FSF Unlimited License + + + + + NASA Open Source Agreement 1.3 + + + + + BSD 2-Clause "Simplified" License + + + + + XFree86 License 1.1 + + + + + Eurosym License + + + + + Open LDAP Public License v2.8 + + + + + dvipdfm License + + + + + NIST Public Domain Notice + + + + + Apache License 1.1 + + + + + The Parity Public License 6.0.0 + + + + + Creative Commons Attribution 2.0 Generic + + + + + GNU Lesser General Public License v3.0 or later + + + + + BSD 2-Clause with views sentence + + + + + GNU General Public License v2.0 w/Classpath exception + + + + + BSD 3-Clause No Nuclear Warranty + + + + + X11 License + + + + + Community Data License Agreement Permissive 2.0 + + + + + Haskell Language Report License + + + + + Artistic License 1.0 w/clause 8 + + + + + Apple Public Source License 2.0 + + + + + GNU General Public License v3.0 or later + + + + + Solderpad Hardware License v0.5 + + + + + CNRI Python Open Source GPL Compatible License Agreement + + + + + Condor Public License v1.1 + + + + + Open LDAP Public License v2.3 + + + + + GNU General Public License v2.0 only + + + + + Business Source License 1.1 + + + + + Licence Libre du Québec – Réciprocité version 1.1 + + + + + Academy of Motion Picture Arts and Sciences BSD + + + + + copyleft-next 0.3.1 + + + + + GNU Free Documentation License v1.3 or later - invariants + + + + + Open LDAP Public License v2.7 + + + + + Open Software License 2.0 + + + + + Unicode License Agreement - Data Files and Software (2015) + + + + + Computer Associates Trusted Open Source License 1.1 + + + + + Ricoh Source Code Public License + + + + + PNG Reference Library version 2 + + + + + LaTeX Project Public License v1.1 + + + + + Community Data License Agreement Sharing 1.0 + + + + + Glulxe License + + + + + GNU Free Documentation License v1.3 or later - no invariants + + + + + Open LDAP Public License v1.2 + + + + + Common Development and Distribution License 1.1 + + + + + CERN Open Hardware Licence v1.1 + + + + + BSD Source Code Attribution + + + + + Independent JPEG Group License + + + + + Zimbra Public License v1.4 + + + + + BSD Zero Clause License + + + + + Creative Commons Attribution 1.0 Generic + + + + + wxWindows Library License + + + + + Zope Public License 2.1 + + + + + NTP License + + + + + Artistic License 1.0 (Perl) + + + + + Creative Commons Attribution No Derivatives 2.0 Generic + + + + + Creative Commons Attribution No Derivatives 4.0 International + + + + + Adobe Systems Incorporated Source Code License Agreement + + + + + Eclipse Public License 1.0 + + + + + diffmark license + + + + + xinetd License + + + + + Plexus Classworlds License + + + + + Japan Network Information Center License + + + + + Adobe Glyph List License + + + + + Cube License + + + + + TCP Wrappers License + + + + + Creative Commons Attribution Share Alike 1.0 Generic + + + + + BSD 2-Clause FreeBSD License + + + + + Open Government Licence - Canada + + + + + ANTLR Software Rights Notice + + + + + GNU Library General Public License v2.1 or later + + + + + Open Software License 2.1 + + + + + psutils License + + + + + SCEA Shared Source License + + + + + The MirOS Licence + + + + + Hippocratic License 2.1 + + + + + GNU Free Documentation License v1.2 only - invariants + + + + + GNU Lesser General Public License v2.1 only + + + + + Entessa Public License v1.0 + + + + + Microsoft Reciprocal License + + + + + libselinux public domain notice + + + + + GNU Library General Public License v2 only + + + + + Open LDAP Public License v2.5 + + + + + Imlib2 License + + + + + libpng License + + + + + Scheme Language Report License + + + + + Mozilla Public License 1.0 + + + + + Sax Public Domain Notice + + + + + Norwegian Licence for Open Government Data (NLOD) 1.0 + + + + + Simple Public License 2.0 + + + + + Technische Universitaet Berlin License 1.0 + + + + + GNU Free Documentation License v1.1 only - no invariants + + + + + Creative Commons Attribution No Derivatives 3.0 Germany + + + + + MakeIndex License + + + + + EPICS Open License + + + + + GNU Free Documentation License v1.3 only - invariants + + + + + XSkat License + + + + + bzip2 and libbzip2 License v1.0.5 + + + + + Community Specification License 1.0 + + + + + GL2PS License + + + + + Historical Permission Notice and Disclaimer + + + + + bzip2 and libbzip2 License v1.0.6 + + + + + Creative Commons Attribution Non Commercial 1.0 Generic + + + + + Fair License + + + + + CeCILL-B Free Software License Agreement + + + + + 3dfx Glide License + + + + + Creative Commons Attribution Share Alike 4.0 International + + + + + Creative Commons Zero v1.0 Universal + + + + + enna License + + + + + Wsuipa License + + + + + RSA Message-Digest License + + + + + VOSTROM Public License for Open Source + + + + + Open Use of Data Agreement v1.0 + + + + + CERN Open Hardware Licence Version 2 - Strongly Reciprocal + + + + + X11 License Distribution Modification Variant + + + + + copyleft-next 0.3.0 + + + + + Zimbra Public License v1.3 + + + + + NIST Public Domain Notice with license fallback + + + + + Nokia Open Source License + + + + + Academic Free License v2.1 + + + + + Zope Public License 2.0 + + + + + Open Data Commons Open Database License v1.0 + + + + + zlib/libpng License with Acknowledgement + + + + + PHP License v3.01 + + + + + Afmparse License + + + + + Historical Permission Notice and Disclaimer - sell variant + + + + + PolyForm Small Business License 1.0.0 + + + + + IBM Public License v1.0 + + + + + CeCILL Free Software License Agreement v1.1 + + + + + feh License + + + + + SIL Open Font License 1.0 with Reserved Font Name + + + + + TMate Open Source License + + + + + BSD 3-Clause No Nuclear License + + + + + W3C Software Notice and License (1998-07-20) + + + + + Sun Public License v1.0 + + + + + NetCDF license + + + + + Aladdin Free Public License + + + + + AMD's plpa_map.c License + + + + + CrystalStacker License + + + + + Intel ACPI Software License Agreement + + + + + CERN Open Hardware Licence v1.2 + + + + + Creative Commons Attribution Non Commercial Share Alike 3.0 Germany + + + + + MIT License + + + + + Zed License + + + + + Open LDAP Public License v2.0 (or possibly 2.0A and 2.0B) + + + + + Mulan Permissive Software License, Version 1 + + + + + Eiffel Forum License v2.0 + + + + + Latex2e License + + + + + Spencer License 94 + + + + + Open Public License v1.0 + + + + + Creative Commons Attribution Non Commercial 4.0 International + + + + + GNU Lesser General Public License v3.0 or later + + + + + Universal Permissive License v1.0 + + + + + University of Illinois/NCSA Open Source License + + + + + SGI Free Software License B v2.0 + + + + + GNU General Public License v3.0 w/GCC Runtime Library exception + + + + + Zend License v2.0 + + + + + ImageMagick License + + + + + Open LDAP Public License v2.6 + + + + + Unicode Terms of Use + + + + + GNU General Public License v3.0 only + + + + + Artistic License 2.0 + + + + + SQLite Blessing + + + + + Etalab Open License 2.0 + + + + + GNU Free Documentation License v1.2 only + + + + + LaTeX Project Public License v1.0 + + + + + Rdisc License + + + + + BSD 3-Clause Modification + + + + + Xerox License + + + + + Mozilla Public License 2.0 + + + + + BitTorrent Open Source License v1.1 + + + + + Creative Commons Attribution Non Commercial No Derivatives 2.0 Generic + + + + + Sun Industry Standards Source License v1.1 + + + + + libtiff License + + + + + Creative Commons Attribution Non Commercial Share Alike 2.0 England and Wales + + + + + Deutsche Freie Software Lizenz + + + + + LaTeX Project Public License v1.2 + + + + + TAPR Open Hardware License v1.0 + + + + + European Union Public License 1.0 + + + + + Solderpad Hardware License, Version 0.51 + + + + + Freetype Project License + + + + + W3C Software Notice and Document License (2015-05-13) + + + + + OSET Public License version 2.1 + + + + + EU DataGrid Software License + + + + + Upstream Compatibility License v1.0 + + + + + Borceux license + + + + + Elastic License 2.0 + + + + + BSD 2-Clause NetBSD License + + + + + BSD 3-Clause Open MPI variant + + + + + Open Software License 3.0 + + + + + curl License + + + + + Spencer License 86 + + + + + Boost Software License 1.0 + + + + + Standard ML of New Jersey License + + + + + Trusster Open Source License + + + + + Netizen Open Source License + + + + + Academic Free License v1.2 + + + + + Mulan Permissive Software License, Version 2 + + + + + Motosoto License + + + + + Creative Commons Attribution Non Commercial Share Alike 2.5 Generic + + + + + JasPer License + + + + + BSD-4-Clause (University of California-Specific) + + + + + Bahyph License + + + + + Vovida Software License v1.0 + + + + + W3C Software Notice and License (2002-12-31) + + + + + Open Data Commons Attribution License v1.0 + + + + + BitTorrent Open Source License v1.0 + + + + + Open Government Licence v2.0 + + + + + GNU Lesser General Public License v3.0 only + + + + + X.Net License + + + + + Ruby License + + + + + GNU Free Documentation License v1.3 + + + + + Zope Public License 1.1 + + + + + Open CASCADE Technology Public License + + + + + LaTeX Project Public License v1.3c + + + + + Apache License 2.0 + + + + + GD License + + + + + Creative Commons Attribution 3.0 Netherlands + + + + + LaTeX Project Public License v1.3a + + + + + Creative Commons Attribution 2.5 Australia + + + + + GNU Free Documentation License v1.1 only + + + + + GNU Free Documentation License v1.1 or later + + + + + Open Government Licence v3.0 + + + + + Yahoo! Public License v1.0 + + + + + Reciprocal Public License 1.1 + + + + + GNU Library General Public License v2 or later + + + + + Open Publication License v1.0 + + + + + Noweb License + + + + + Academic Free License v3.0 + + + + + Nunit License + + + + + Creative Commons Attribution 3.0 Unported + + + + + Beerware License + + + + + Caldera License + + + + + GNU General Public License v1.0 only + + + + + GNU General Public License v2.0 or later + + + + + Non-Commercial Government Licence + + + + + Creative Commons Attribution No Derivatives 2.5 Generic + + + + + GNU General Public License v2.0 only + + + + + Intel Open Source License + + + + + Vim License + + + + + Creative Commons Attribution Share Alike 2.0 Generic + + + + + MIT +no-false-attribs license + + + + + Apple Public Source License 1.1 + + + + + GNU Free Documentation License v1.2 or later + + + + + BSD with attribution + + + + + SIL Open Font License 1.0 with no Reserved Font Name + + + + + Naumen Public License + + + + + Creative Commons Attribution Non Commercial No Derivatives 2.5 Generic + + + + + Computational Use of Data Agreement v1.0 + + + + + Lesser General Public License For Linguistic Resources + + + + + mpich2 License + + + + + Apple Public Source License 1.0 + + + + + Linux Kernel Variant of OpenIB.org license + + + + + Enlightenment License (e16) + + + + + GNU Free Documentation License v1.2 + + + + + Open Group Test Suite License + + + + + Dotseqn License + + + + + Data licence Germany – attribution – version 2.0 + + + + + Saxpath License + + + + + GNU Affero General Public License v3.0 + + + + + Abstyles License + + + + + Creative Commons Attribution Share Alike 3.0 Unported + + + + + Giftware License + + + + + FreeImage Public License v1.0 + + + + + CeCILL Free Software License Agreement v2.1 + + + + + RealNetworks Public Source License v1.0 + + + + + GNU Free Documentation License v1.3 or later + + + + + GNU Free Documentation License v1.1 or later - invariants + + + + + Educational Community License v2.0 + + + + + Licence Libre du Québec – Réciprocité forte version 1.1 + + + + + GNU General Public License v3.0 w/Autoconf exception + + + + + Jam License + + + + + GNU Free Documentation License v1.2 or later - no invariants + + + + + CeCILL Free Software License Agreement v2.0 + + + + + PolyForm Noncommercial License 1.0.0 + + + + + OGC Software License, Version 1.0 + + + + + Creative Commons Attribution No Derivatives 3.0 Unported + + + + + Q Public License 1.0 + + + + + Licence Art Libre 1.2 + + + + + Creative Commons Attribution 3.0 Germany + + + + + OpenSSL License + + + + + Spencer License 99 + + + + + Creative Commons Attribution Share Alike 3.0 Austria + + + + + BSD Protection License + + + + + Open LDAP Public License 2.2.2 + + + + + NRL License + + + + + TORQUE v2.5+ Software License v1.1 + + + + + HTML Tidy License + + + + + Server Side Public License, v 1 + + + + + Netscape Public License v1.0 + + + + + GNU Library General Public License v2 only + + + + + GNU Affero General Public License v3.0 only + + + + + GNU Free Documentation License v1.2 or later - invariants + + + + + GNU General Public License v2.0 w/Bison exception + + + + + Creative Commons Attribution Non Commercial No Derivatives 1.0 Generic + + + + + Educational Community License v1.0 + + + + + Do What The F*ck You Want To Public License + + + + + Creative Commons Attribution Share Alike 2.0 England and Wales + + + + + GNU General Public License v3.0 only + + + + + Open LDAP Public License v2.2.1 + + + + + Secure Messaging Protocol Public License + + + + + Creative Commons Attribution 3.0 Austria + + + + + Eiffel Forum License v1.0 + + + + + Net Boolean Public License v1 + + + + + Lawrence Berkeley National Labs BSD variant license + + + + + Affero General Public License v1.0 + + + + + Crossword License + + + + + TCL/TK License + + + + + Creative Commons Attribution No Derivatives 1.0 Generic + + + + + Apple MIT License + + + + + Technische Universitaet Berlin License 2.0 + + + + + GNU Free Documentation License v1.3 only + + + + + Non-Profit Open Software License 3.0 + + + + + BSD 4-Clause "Original" or "Old" License + + + + + gSOAP Public License v1.3b + + + + + GNU Lesser General Public License v2.1 only + + + + + GNU Lesser General Public License v3.0 only + + + + + + FreeRTOS Exception 2.0 + + + + + Swift Exception + + + + + Qt LGPL exception 1.1 + + + + + GNU JavaMail exception + + + + + CLISP exception 2.0 + + + + + eCos exception 2.0 + + + + + GPL Cooperation Commitment 1.0 + + + + + DigiRule FOSS License Exception + + + + + Font exception 2.0 + + + + + Qt GPL exception 1.0 + + + + + PS/PDF font exception (2017-08-17) + + + + + GPL-3.0 Linking Exception (with Corresponding Source) + + + + + Linux Syscall Note + + + + + GCC Runtime Library exception 2.0 + + + + + LZMA exception + + + + + Autoconf exception 3.0 + + + + + U-Boot exception 2.0 + + + + + LLVM Exception + + + + + OCaml LGPL Linking Exception + + + + + Autoconf exception 2.0 + + + + + Bootloader Distribution Exception + + + + + LGPL-3.0 Linking Exception + + + + + OpenVPN OpenSSL Exception + + + + + FLTK exception + + + + + Bison exception 2.2 + + + + + Open CASCADE Exception 1.0 + + + + + GCC Runtime Library exception 3.1 + + + + + OpenJDK Assembly exception 1.0 + + + + + WxWindows Library Exception 3.1 + + + + + Fawkes Runtime Exception + + + + + Nokia Qt LGPL exception 1.1 + + + + + Qwt exception 1.0 + + + + + Universal FOSS Exception, Version 1.0 + + + + + Classpath exception 2.0 + + + + + Solderpad Hardware License v2.0 + + + + + GPL-3.0 Linking Exception + + + + + Solderpad Hardware License v2.1 + + + + + Libtool Exception + + + + + Macros and Inline Functions Exception + + + + + 389 Directory Server Exception + + + + + i2p GPL+Java Exception + + + + + + diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/README.md b/ci/tools/openeuler-purl/syft-dev/schema/json/README.md new file mode 100644 index 0000000000000000000000000000000000000000..40af8b4cd44f008de7138ad7b649baeab22ec86c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/README.md @@ -0,0 +1,39 @@ +# JSON Schema + +This is the JSON schema for output from the JSON presenters (`syft packages -o json` and `syft power-user `). The required inputs for defining the JSON schema are as follows: + +- the value of `internal.JSONSchemaVersion` that governs the schema filename +- the `Document` struct definition within `internal/presenters/poweruser/json_document.go` that governs the overall document shape +- the `artifactMetadataContainer` struct definition within `schema/json/generate.go` that governs the allowable shapes of `pkg.Package.Metadata` + +With regard to testing the JSON schema, integration test cases provided by the developer are used as examples to validate that JSON output from Syft is always valid relative to the `schema/json/schema-$VERSION.json` file. + +## Versioning + +Versioning the JSON schema must be done manually by changing the `JSONSchemaVersion` constant within `internal/constants.go`. + +This schema is being versioned based off of the "SchemaVer" guidelines, which slightly diverges from Semantic Versioning to tailor for the purposes of data models. + +Given a version number format `MODEL.REVISION.ADDITION`: + +- `MODEL`: increment when you make a breaking schema change which will prevent interaction with any historical data +- `REVISION`: increment when you make a schema change which may prevent interaction with some historical data +- `ADDITION`: increment when you make a schema change that is compatible with all historical data + +## Adding a New `pkg.*Metadata` Type + +When adding a new `pkg.*Metadata` that is assigned to the `pkg.Package.Metadata` struct field it is important that a few things +are done: + +- a new integration test case is added to `test/integration/catalog_packages_cases_test.go` that exercises the new package type with the new metadata +- the new metadata struct is added to the `artifactMetadataContainer` struct within `schema/json/generate.go` + +## Generating a New Schema + +Create the new schema by running `cd schema/json && go run generate.go` (note you must be in the `schema/json` dir while running this): + +- If there is **not** an existing schema for the given version, then the new schema file will be written to `schema/json/schema-$VERSION.json` +- If there is an existing schema for the given version and the new schema matches the existing schema, no action is taken +- If there is an existing schema for the given version and the new schema **does not** match the existing schema, an error is shown indicating to increment the version appropriately (see the "Versioning" section) + +***Note: never delete a JSON schema and never change an existing JSON schema once it has been published in a release!*** Only add new schemas with a newly incremented version. All previous schema files must be stored in the `schema/json/` directory. diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/generate.go b/ci/tools/openeuler-purl/syft-dev/schema/json/generate.go new file mode 100644 index 0000000000000000000000000000000000000000..5bd99403cb8cbeac90095994143a909bd044dd95 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/generate.go @@ -0,0 +1,150 @@ +package main + +import ( + "bytes" + "encoding/json" + "fmt" + "io" + "os" + "reflect" + "sort" + "strings" + + "github.com/alecthomas/jsonschema" + "github.com/anchore/syft/internal" + syftjsonModel "github.com/anchore/syft/internal/formats/syftjson/model" + "github.com/anchore/syft/syft/pkg" +) + +/* +This method of creating the JSON schema only captures strongly typed fields for the purpose of integrations between syft +JSON output and integrations. The downside to this approach is that any values and types used on weakly typed fields +are not captured (empty interfaces). This means that pkg.Package.Metadata is not validated at this time. This approach +can be extended to include specific package metadata struct shapes in the future. +*/ + +// This should represent all possible metadatas represented in the pkg.Package.Metadata field (an interface{}). +// When a new package metadata definition is created it will need to be manually added here. The variable name does +// not matter as long as it is exported. +type artifactMetadataContainer struct { + Apk pkg.ApkMetadata + Alpm pkg.AlpmMetadata + Dpkg pkg.DpkgMetadata + Gem pkg.GemMetadata + Java pkg.JavaMetadata + Npm pkg.NpmPackageJSONMetadata + Python pkg.PythonPackageMetadata + Rpm pkg.RpmMetadata + Cargo pkg.CargoPackageMetadata + Go pkg.GolangBinMetadata + Php pkg.PhpComposerJSONMetadata + Dart pkg.DartPubMetadata + Dotnet pkg.DotnetDepsMetadata + Portage pkg.PortageMetadata +} + +func main() { + write(encode(build())) +} + +func build() *jsonschema.Schema { + reflector := &jsonschema.Reflector{ + AllowAdditionalProperties: true, + TypeNamer: func(r reflect.Type) string { + return strings.TrimPrefix(r.Name(), "JSON") + }, + } + documentSchema := reflector.ReflectFromType(reflect.TypeOf(&syftjsonModel.Document{})) + metadataSchema := reflector.ReflectFromType(reflect.TypeOf(&artifactMetadataContainer{})) + + // TODO: inject source definitions + + // inject the definitions of all metadatas into the schema definitions + + var metadataNames []string + for name, definition := range metadataSchema.Definitions { + if name == "artifactMetadataContainer" { + // ignore the definition for the fake container + continue + } + documentSchema.Definitions[name] = definition + if strings.HasSuffix(name, "Metadata") { + metadataNames = append(metadataNames, name) + } + } + + // ensure the generated list of names is stable between runs + sort.Strings(metadataNames) + + var metadataTypes = []map[string]string{ + // allow for no metadata to be provided + {"type": "null"}, + } + for _, name := range metadataNames { + metadataTypes = append(metadataTypes, map[string]string{ + "$ref": fmt.Sprintf("#/definitions/%s", name), + }) + } + + // set the "anyOf" field for Package.Metadata to be a conjunction of several types + documentSchema.Definitions["Package"].Properties.Set("metadata", map[string][]map[string]string{ + "anyOf": metadataTypes, + }) + + return documentSchema +} + +func encode(schema *jsonschema.Schema) []byte { + var newSchemaBuffer = new(bytes.Buffer) + enc := json.NewEncoder(newSchemaBuffer) + // prevent > and < from being escaped in the payload + enc.SetEscapeHTML(false) + enc.SetIndent("", " ") + err := enc.Encode(&schema) + if err != nil { + panic(err) + } + + return newSchemaBuffer.Bytes() +} + +func write(schema []byte) { + filename := fmt.Sprintf("schema-%s.json", internal.JSONSchemaVersion) + + if _, err := os.Stat(filename); !os.IsNotExist(err) { + // check if the schema is the same... + existingFh, err := os.Open(filename) + if err != nil { + panic(err) + } + + existingSchemaBytes, err := io.ReadAll(existingFh) + if err != nil { + panic(err) + } + + if bytes.Equal(existingSchemaBytes, schema) { + // the generated schema is the same, bail with no error :) + fmt.Println("No change to the existing schema!") + os.Exit(0) + } + + // the generated schema is different, bail with error :( + fmt.Printf("Cowardly refusing to overwrite existing schema (%s)!\nSee the scheam/json/README.md for how to increment\n", filename) + os.Exit(1) + } + + fh, err := os.Create(filename) + if err != nil { + panic(err) + } + + _, err = fh.Write(schema) + if err != nil { + panic(err) + } + + defer fh.Close() + + fmt.Printf("wrote new schema to %q\n", filename) +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.0.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.0.json new file mode 100644 index 0000000000000000000000000000000000000000..6f70a37ea9698e0278e334b3bc611df621690da4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.0.json @@ -0,0 +1,678 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "checksum": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Distribution": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distribution" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": false, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "md5" + ], + "properties": { + "path": { + "type": "string" + }, + "md5": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": false, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Location": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Package": { + "required": [ + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Location" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": false, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "sha256" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "sha256": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": false, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.1.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.1.json new file mode 100644 index 0000000000000000000000000000000000000000..558acfd19c1f4c6e9f4ee80494794f971d577ac2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.1.json @@ -0,0 +1,682 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "checksum": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Distribution": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distribution" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": false, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "md5" + ], + "properties": { + "path": { + "type": "string" + }, + "md5": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": false, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Location": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Package": { + "required": [ + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Location" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": false, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "sha256" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "sha256": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": false, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.2.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.2.json new file mode 100644 index 0000000000000000000000000000000000000000..640081d48ecacbdabc7e57445564560d9e165615 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.2.json @@ -0,0 +1,718 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "checksum": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Distribution": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "source", + "distro", + "descriptor", + "schema", + "artifactRelationships" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distribution" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "md5" + ], + "properties": { + "path": { + "type": "string" + }, + "md5": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": false, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Location": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Location" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": false, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type", + "metadata" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": false, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "sha256" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "sha256": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": false, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.3.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.3.json new file mode 100644 index 0000000000000000000000000000000000000000..108ba74799e657c106be0ee1ee59e892c777a0cc --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.3.json @@ -0,0 +1,752 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "checksum": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Distribution": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "source", + "distro", + "descriptor", + "schema", + "artifactRelationships" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distribution" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "md5" + ], + "properties": { + "path": { + "type": "string" + }, + "md5": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": false, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Location": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Location" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": false, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type", + "metadata" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": false, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "sha256" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "sha256": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": false, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": false, + "type": "object" + } + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.4.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.4.json new file mode 100644 index 0000000000000000000000000000000000000000..62719cdeb296021bbc35e05c4a1b0157d59fe2c0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.4.json @@ -0,0 +1,832 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "checksum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Distribution": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "fileMetadata": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadata" + }, + "type": "array" + }, + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distribution" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + }, + "artifacts.metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "md5" + ], + "properties": { + "path": { + "type": "string" + }, + "md5": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadata": { + "required": [ + "location", + "metadata" + ], + "properties": { + "location": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Location" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Location": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$ref": "#/definitions/Location" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type", + "metadata" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "sha256" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "sha256": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.5.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.5.json new file mode 100644 index 0000000000000000000000000000000000000000..33d1c592e42f2480b4735d51d74b7959b0a946de --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.0.5.json @@ -0,0 +1,890 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "checksum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Distribution": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "fileMetadata": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadata" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distribution" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + }, + "artifacts.metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "md5" + ], + "properties": { + "path": { + "type": "string" + }, + "md5": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadata": { + "required": [ + "location", + "metadata" + ], + "properties": { + "location": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Location" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Location": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$ref": "#/definitions/Location" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type", + "metadata" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "sha256" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "sha256": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Location" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.1.0.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.1.0.json new file mode 100644 index 0000000000000000000000000000000000000000..b3459bf62e301e623da3cf65bffb5290b074f4fc --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-1.1.0.json @@ -0,0 +1,971 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Distribution": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "fileClassifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileClassifications" + }, + "type": "array" + }, + "fileContents": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileContents" + }, + "type": "array" + }, + "fileMetadata": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadata" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distribution" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileClassifications": { + "required": [ + "location", + "classification" + ], + "properties": { + "location": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Location" + }, + "classification": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileContents": { + "required": [ + "location", + "contents" + ], + "properties": { + "location": { + "$ref": "#/definitions/Location" + }, + "contents": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadata": { + "required": [ + "location", + "metadata" + ], + "properties": { + "location": { + "$ref": "#/definitions/Location" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Location": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$ref": "#/definitions/Location" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type", + "metadata" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Location" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.0.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.0.json new file mode 100644 index 0000000000000000000000000000000000000000..e5cd95f61c6d2b60d31119156bdbb7f240a85a4e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.0.json @@ -0,0 +1,1002 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Distro": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distro" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.1.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.1.json new file mode 100644 index 0000000000000000000000000000000000000000..50242ba2ba9ae9d0b00adebf08b6f322c1499863 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.1.json @@ -0,0 +1,1025 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Distro": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distro" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture", + "h1Digest" + ], + "properties": { + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.2.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.2.json new file mode 100644 index 0000000000000000000000000000000000000000..b70e68213bce0ede8a0f0afcb4991618569a904f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-2.0.2.json @@ -0,0 +1,1047 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Distro": { + "required": [ + "name", + "version", + "idLike" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "idLike": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Distro" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture", + "h1Digest" + ], + "properties": { + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.0.0.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.0.0.json new file mode 100644 index 0000000000000000000000000000000000000000..bf90271a89d50ed8046a292c8bc9c45d64dd9373 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.0.0.json @@ -0,0 +1,1075 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Release" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture", + "h1Digest" + ], + "properties": { + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl", + "metadataType", + "metadata" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Release": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.0.1.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.0.1.json new file mode 100644 index 0000000000000000000000000000000000000000..7454f15640ac0792cf3883b2ff3ece9f3b28f430 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.0.1.json @@ -0,0 +1,1214 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture", + "h1Digest" + ], + "properties": { + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "type": "integer" + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.1.0.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.1.0.json new file mode 100644 index 0000000000000000000000000000000000000000..5b3fc79a4c34b2f83abd5a7c1e5990f72063d650 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.1.0.json @@ -0,0 +1,1229 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture", + "h1Digest" + ], + "properties": { + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.1.1.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.1.1.json new file mode 100644 index 0000000000000000000000000000000000000000..e23a86a0ce57d470bee896576ece749d343bb861 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.1.1.json @@ -0,0 +1,1237 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture", + "h1Digest" + ], + "properties": { + "goBuildSettings": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.1.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.1.json new file mode 100644 index 0000000000000000000000000000000000000000..b13bf68c4ff8ca2cbefd5227ded9c29e3fbc7f64 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.1.json @@ -0,0 +1,1236 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture" + ], + "properties": { + "goBuildSettings": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.2.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.2.json new file mode 100644 index 0000000000000000000000000000000000000000..d6649f6cfe506f984b0d4eb2af8bf320826ec300 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.2.json @@ -0,0 +1,1261 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DartPubMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "hosted_url": { + "type": "string" + }, + "vcs_url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture" + ], + "properties": { + "goBuildSettings": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DartPubMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.3.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.3.json new file mode 100644 index 0000000000000000000000000000000000000000..3018f70c97ffa277d9b54249558f32d3c43acdd3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.3.json @@ -0,0 +1,1298 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DartPubMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "hosted_url": { + "type": "string" + }, + "vcs_url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DotnetDepsMetadata": { + "required": [ + "name", + "version", + "path", + "sha512", + "hashPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "path": { + "type": "string" + }, + "sha512": { + "type": "string" + }, + "hashPath": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture" + ], + "properties": { + "goBuildSettings": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + }, + "digest": { + "items": { + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DartPubMetadata" + }, + { + "$ref": "#/definitions/DotnetDepsMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.4.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.4.json new file mode 100644 index 0000000000000000000000000000000000000000..6dc57418506a92240f78f95b00e4c367f0eb513b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.2.4.json @@ -0,0 +1,1301 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DartPubMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "hosted_url": { + "type": "string" + }, + "vcs_url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DotnetDepsMetadata": { + "required": [ + "name", + "version", + "path", + "sha512", + "hashPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "path": { + "type": "string" + }, + "sha512": { + "type": "string" + }, + "hashPath": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture" + ], + "properties": { + "goBuildSettings": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + }, + "mainModule": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + }, + "digest": { + "items": { + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DartPubMetadata" + }, + { + "$ref": "#/definitions/DotnetDepsMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.0.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.0.json new file mode 100644 index 0000000000000000000000000000000000000000..c70be390d0e5b8183f48eee694e76d8b88b09fc0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.0.json @@ -0,0 +1,1417 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "AlpmFileRecord": { + "properties": { + "path": { + "type": "string" + }, + "type": { + "type": "string" + }, + "uid": { + "type": "string" + }, + "gid": { + "type": "string" + }, + "time": { + "type": "string", + "format": "date-time" + }, + "size": { + "type": "string" + }, + "link": { + "type": "string" + }, + "digest": { + "items": { + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "AlpmMetadata": { + "required": [ + "basepackage", + "package", + "version", + "description", + "architecture", + "size", + "packager", + "license", + "url", + "validation", + "reason", + "files", + "backup" + ], + "properties": { + "basepackage": { + "type": "string" + }, + "package": { + "type": "string" + }, + "version": { + "type": "string" + }, + "description": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "packager": { + "type": "string" + }, + "license": { + "type": "string" + }, + "url": { + "type": "string" + }, + "validation": { + "type": "string" + }, + "reason": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/AlpmFileRecord" + }, + "type": "array" + }, + "backup": { + "items": { + "$ref": "#/definitions/AlpmFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DartPubMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "hosted_url": { + "type": "string" + }, + "vcs_url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DotnetDepsMetadata": { + "required": [ + "name", + "version", + "path", + "sha512", + "hashPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "path": { + "type": "string" + }, + "sha512": { + "type": "string" + }, + "hashPath": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture" + ], + "properties": { + "goBuildSettings": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + }, + "mainModule": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + }, + "digest": { + "items": { + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "versionCodename": { + "type": "string" + }, + "buildID": { + "type": "string" + }, + "imageID": { + "type": "string" + }, + "imageVersion": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/AlpmMetadata" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DartPubMetadata" + }, + { + "$ref": "#/definitions/DotnetDepsMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.1.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.1.json new file mode 100644 index 0000000000000000000000000000000000000000..1454a27697f6f8eb77dec851dd1f368d3131baf4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.1.json @@ -0,0 +1,1463 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "AlpmFileRecord": { + "properties": { + "path": { + "type": "string" + }, + "type": { + "type": "string" + }, + "uid": { + "type": "string" + }, + "gid": { + "type": "string" + }, + "time": { + "type": "string", + "format": "date-time" + }, + "size": { + "type": "string" + }, + "link": { + "type": "string" + }, + "digest": { + "items": { + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "AlpmMetadata": { + "required": [ + "basepackage", + "package", + "version", + "description", + "architecture", + "size", + "packager", + "license", + "url", + "validation", + "reason", + "files", + "backup" + ], + "properties": { + "basepackage": { + "type": "string" + }, + "package": { + "type": "string" + }, + "version": { + "type": "string" + }, + "description": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "packager": { + "type": "string" + }, + "license": { + "type": "string" + }, + "url": { + "type": "string" + }, + "validation": { + "type": "string" + }, + "reason": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/AlpmFileRecord" + }, + "type": "array" + }, + "backup": { + "items": { + "$ref": "#/definitions/AlpmFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DartPubMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "hosted_url": { + "type": "string" + }, + "vcs_url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DotnetDepsMetadata": { + "required": [ + "name", + "version", + "path", + "sha512", + "hashPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "path": { + "type": "string" + }, + "sha512": { + "type": "string" + }, + "hashPath": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture" + ], + "properties": { + "goBuildSettings": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + }, + "mainModule": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + }, + "digest": { + "items": { + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "versionCodename": { + "type": "string" + }, + "buildID": { + "type": "string" + }, + "imageID": { + "type": "string" + }, + "imageVersion": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/AlpmMetadata" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DartPubMetadata" + }, + { + "$ref": "#/definitions/DotnetDepsMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PortageMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PortageFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PortageMetadata": { + "required": [ + "package", + "version", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "version": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PortageFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.2.json b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.2.json new file mode 100644 index 0000000000000000000000000000000000000000..23bb52ca2c038c29d5b93f547cc50602d1306106 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/schema-3.3.2.json @@ -0,0 +1,1467 @@ +{ + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Document", + "definitions": { + "AlpmFileRecord": { + "properties": { + "path": { + "type": "string" + }, + "type": { + "type": "string" + }, + "uid": { + "type": "string" + }, + "gid": { + "type": "string" + }, + "time": { + "type": "string", + "format": "date-time" + }, + "size": { + "type": "string" + }, + "link": { + "type": "string" + }, + "digest": { + "items": { + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "AlpmMetadata": { + "required": [ + "basepackage", + "package", + "version", + "description", + "architecture", + "size", + "packager", + "license", + "url", + "validation", + "reason", + "files", + "backup" + ], + "properties": { + "basepackage": { + "type": "string" + }, + "package": { + "type": "string" + }, + "version": { + "type": "string" + }, + "description": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "packager": { + "type": "string" + }, + "license": { + "type": "string" + }, + "url": { + "type": "string" + }, + "validation": { + "type": "string" + }, + "reason": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/AlpmFileRecord" + }, + "type": "array" + }, + "backup": { + "items": { + "$ref": "#/definitions/AlpmFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "ownerUid": { + "type": "string" + }, + "ownerGid": { + "type": "string" + }, + "permissions": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "ApkMetadata": { + "required": [ + "package", + "originPackage", + "maintainer", + "version", + "license", + "architecture", + "url", + "description", + "size", + "installedSize", + "pullDependencies", + "pullChecksum", + "gitCommitOfApkPort", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "originPackage": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "url": { + "type": "string" + }, + "description": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "installedSize": { + "type": "integer" + }, + "pullDependencies": { + "type": "string" + }, + "pullChecksum": { + "type": "string" + }, + "gitCommitOfApkPort": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/ApkFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "CargoPackageMetadata": { + "required": [ + "name", + "version", + "source", + "checksum", + "dependencies" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "type": "string" + }, + "checksum": { + "type": "string" + }, + "dependencies": { + "items": { + "type": "string" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Classification": { + "required": [ + "class", + "metadata" + ], + "properties": { + "class": { + "type": "string" + }, + "metadata": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Coordinates": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "layerID": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DartPubMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "hosted_url": { + "type": "string" + }, + "vcs_url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Descriptor": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "configuration": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "Digest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Document": { + "required": [ + "artifacts", + "artifactRelationships", + "source", + "distro", + "descriptor", + "schema" + ], + "properties": { + "artifacts": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Package" + }, + "type": "array" + }, + "artifactRelationships": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Relationship" + }, + "type": "array" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/File" + }, + "type": "array" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Secrets" + }, + "type": "array" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Source" + }, + "distro": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/LinuxRelease" + }, + "descriptor": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Descriptor" + }, + "schema": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Schema" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DotnetDepsMetadata": { + "required": [ + "name", + "version", + "path", + "sha512", + "hashPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "path": { + "type": "string" + }, + "sha512": { + "type": "string" + }, + "hashPath": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgFileRecord": { + "required": [ + "path", + "isConfigFile" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "isConfigFile": { + "type": "boolean" + } + }, + "additionalProperties": true, + "type": "object" + }, + "DpkgMetadata": { + "required": [ + "package", + "source", + "version", + "sourceVersion", + "architecture", + "maintainer", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "source": { + "type": "string" + }, + "version": { + "type": "string" + }, + "sourceVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "maintainer": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/DpkgFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "File": { + "required": [ + "id", + "location" + ], + "properties": { + "id": { + "type": "string" + }, + "location": { + "$ref": "#/definitions/Coordinates" + }, + "metadata": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/FileMetadataEntry" + }, + "contents": { + "type": "string" + }, + "digests": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Digest" + }, + "type": "array" + }, + "classifications": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Classification" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "FileMetadataEntry": { + "required": [ + "mode", + "type", + "userID", + "groupID", + "mimeType" + ], + "properties": { + "mode": { + "type": "integer" + }, + "type": { + "type": "string" + }, + "linkDestination": { + "type": "string" + }, + "userID": { + "type": "integer" + }, + "groupID": { + "type": "integer" + }, + "mimeType": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GemMetadata": { + "required": [ + "name", + "version" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "type": "string" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "GolangBinMetadata": { + "required": [ + "goCompiledVersion", + "architecture" + ], + "properties": { + "goBuildSettings": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "goCompiledVersion": { + "type": "string" + }, + "architecture": { + "type": "string" + }, + "h1Digest": { + "type": "string" + }, + "mainModule": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaManifest": { + "properties": { + "main": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "namedSections": { + "patternProperties": { + ".*": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "JavaMetadata": { + "required": [ + "virtualPath" + ], + "properties": { + "virtualPath": { + "type": "string" + }, + "manifest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/JavaManifest" + }, + "pomProperties": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProperties" + }, + "pomProject": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomProject" + }, + "digest": { + "items": { + "$ref": "#/definitions/Digest" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "LinuxRelease": { + "properties": { + "prettyName": { + "type": "string" + }, + "name": { + "type": "string" + }, + "id": { + "type": "string" + }, + "idLike": { + "items": { + "type": "string" + }, + "type": "array" + }, + "version": { + "type": "string" + }, + "versionID": { + "type": "string" + }, + "versionCodename": { + "type": "string" + }, + "buildID": { + "type": "string" + }, + "imageID": { + "type": "string" + }, + "imageVersion": { + "type": "string" + }, + "variant": { + "type": "string" + }, + "variantID": { + "type": "string" + }, + "homeURL": { + "type": "string" + }, + "supportURL": { + "type": "string" + }, + "bugReportURL": { + "type": "string" + }, + "privacyPolicyURL": { + "type": "string" + }, + "cpeName": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "NpmPackageJSONMetadata": { + "required": [ + "name", + "version", + "author", + "licenses", + "homepage", + "description", + "url" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "files": { + "items": { + "type": "string" + }, + "type": "array" + }, + "author": { + "type": "string" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "homepage": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Package": { + "required": [ + "id", + "name", + "version", + "type", + "foundBy", + "locations", + "licenses", + "language", + "cpes", + "purl" + ], + "properties": { + "id": { + "type": "string" + }, + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "type": { + "type": "string" + }, + "foundBy": { + "type": "string" + }, + "locations": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/Coordinates" + }, + "type": "array" + }, + "licenses": { + "items": { + "type": "string" + }, + "type": "array" + }, + "language": { + "type": "string" + }, + "cpes": { + "items": { + "type": "string" + }, + "type": "array" + }, + "purl": { + "type": "string" + }, + "metadataType": { + "type": "string" + }, + "metadata": { + "anyOf": [ + { + "type": "null" + }, + { + "$ref": "#/definitions/AlpmMetadata" + }, + { + "$ref": "#/definitions/ApkMetadata" + }, + { + "$ref": "#/definitions/CargoPackageMetadata" + }, + { + "$ref": "#/definitions/DartPubMetadata" + }, + { + "$ref": "#/definitions/DotnetDepsMetadata" + }, + { + "$ref": "#/definitions/DpkgMetadata" + }, + { + "$ref": "#/definitions/GemMetadata" + }, + { + "$ref": "#/definitions/GolangBinMetadata" + }, + { + "$ref": "#/definitions/JavaMetadata" + }, + { + "$ref": "#/definitions/NpmPackageJSONMetadata" + }, + { + "$ref": "#/definitions/PhpComposerJSONMetadata" + }, + { + "$ref": "#/definitions/PortageMetadata" + }, + { + "$ref": "#/definitions/PythonPackageMetadata" + }, + { + "$ref": "#/definitions/RpmdbMetadata" + } + ] + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerAuthors": { + "required": [ + "name" + ], + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string" + }, + "homepage": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerExternalReference": { + "required": [ + "type", + "url", + "reference" + ], + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + }, + "reference": { + "type": "string" + }, + "shasum": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PhpComposerJSONMetadata": { + "required": [ + "name", + "version", + "source", + "dist" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "source": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "dist": { + "$ref": "#/definitions/PhpComposerExternalReference" + }, + "require": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "provide": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "require-dev": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "suggest": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + }, + "type": { + "type": "string" + }, + "notification-url": { + "type": "string" + }, + "bin": { + "items": { + "type": "string" + }, + "type": "array" + }, + "license": { + "items": { + "type": "string" + }, + "type": "array" + }, + "authors": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PhpComposerAuthors" + }, + "type": "array" + }, + "description": { + "type": "string" + }, + "homepage": { + "type": "string" + }, + "keywords": { + "items": { + "type": "string" + }, + "type": "array" + }, + "time": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomParent": { + "required": [ + "groupId", + "artifactId", + "version" + ], + "properties": { + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProject": { + "required": [ + "path", + "groupId", + "artifactId", + "version", + "name" + ], + "properties": { + "path": { + "type": "string" + }, + "parent": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PomParent" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "name": { + "type": "string" + }, + "description": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PomProperties": { + "required": [ + "path", + "name", + "groupId", + "artifactId", + "version", + "extraFields" + ], + "properties": { + "path": { + "type": "string" + }, + "name": { + "type": "string" + }, + "groupId": { + "type": "string" + }, + "artifactId": { + "type": "string" + }, + "version": { + "type": "string" + }, + "extraFields": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PortageFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$ref": "#/definitions/Digest" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PortageMetadata": { + "required": [ + "package", + "version", + "installedSize", + "files" + ], + "properties": { + "package": { + "type": "string" + }, + "version": { + "type": "string" + }, + "installedSize": { + "type": "integer" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PortageFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonDirectURLOriginInfo": { + "required": [ + "url" + ], + "properties": { + "url": { + "type": "string" + }, + "commitId": { + "type": "string" + }, + "vcs": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileDigest": { + "required": [ + "algorithm", + "value" + ], + "properties": { + "algorithm": { + "type": "string" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonFileRecord": { + "required": [ + "path" + ], + "properties": { + "path": { + "type": "string" + }, + "digest": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileDigest" + }, + "size": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "PythonPackageMetadata": { + "required": [ + "name", + "version", + "license", + "author", + "authorEmail", + "platform", + "sitePackagesRootPath" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "license": { + "type": "string" + }, + "author": { + "type": "string" + }, + "authorEmail": { + "type": "string" + }, + "platform": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonFileRecord" + }, + "type": "array" + }, + "sitePackagesRootPath": { + "type": "string" + }, + "topLevelPackages": { + "items": { + "type": "string" + }, + "type": "array" + }, + "directUrlOrigin": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/PythonDirectURLOriginInfo" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Relationship": { + "required": [ + "parent", + "child", + "type" + ], + "properties": { + "parent": { + "type": "string" + }, + "child": { + "type": "string" + }, + "type": { + "type": "string" + }, + "metadata": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbFileRecord": { + "required": [ + "path", + "mode", + "size", + "digest", + "userName", + "groupName", + "flags" + ], + "properties": { + "path": { + "type": "string" + }, + "mode": { + "type": "integer" + }, + "size": { + "type": "integer" + }, + "digest": { + "$ref": "#/definitions/Digest" + }, + "userName": { + "type": "string" + }, + "groupName": { + "type": "string" + }, + "flags": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "RpmdbMetadata": { + "required": [ + "name", + "version", + "epoch", + "architecture", + "release", + "sourceRpm", + "size", + "license", + "vendor", + "modularityLabel", + "files" + ], + "properties": { + "name": { + "type": "string" + }, + "version": { + "type": "string" + }, + "epoch": { + "oneOf": [ + { + "type": "integer" + }, + { + "type": "null" + } + ] + }, + "architecture": { + "type": "string" + }, + "release": { + "type": "string" + }, + "sourceRpm": { + "type": "string" + }, + "size": { + "type": "integer" + }, + "license": { + "type": "string" + }, + "vendor": { + "type": "string" + }, + "modularityLabel": { + "type": "string" + }, + "files": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/RpmdbFileRecord" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Schema": { + "required": [ + "version", + "url" + ], + "properties": { + "version": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "SearchResult": { + "required": [ + "classification", + "lineNumber", + "lineOffset", + "seekPosition", + "length" + ], + "properties": { + "classification": { + "type": "string" + }, + "lineNumber": { + "type": "integer" + }, + "lineOffset": { + "type": "integer" + }, + "seekPosition": { + "type": "integer" + }, + "length": { + "type": "integer" + }, + "value": { + "type": "string" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Secrets": { + "required": [ + "location", + "secrets" + ], + "properties": { + "location": { + "$ref": "#/definitions/Coordinates" + }, + "secrets": { + "items": { + "$schema": "http://json-schema.org/draft-04/schema#", + "$ref": "#/definitions/SearchResult" + }, + "type": "array" + } + }, + "additionalProperties": true, + "type": "object" + }, + "Source": { + "required": [ + "type", + "target" + ], + "properties": { + "type": { + "type": "string" + }, + "target": { + "additionalProperties": true + } + }, + "additionalProperties": true, + "type": "object" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/schema/json/vnd.syft+json b/ci/tools/openeuler-purl/syft-dev/schema/json/vnd.syft+json new file mode 100644 index 0000000000000000000000000000000000000000..2a318a57f62a56b5158d99a69e3c4dd5bf6d7222 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/json/vnd.syft+json @@ -0,0 +1,70 @@ +(registered 2021-11-05, last updated 2021-11-05) + +Media type name: application +Media subtype name: vnd.syft+json + +Required parameters: N/A + +Optional parameters: +version + +The version parameter refers to the Syft specification version in use. + +version = 1*DIGIT "." 1*DIGIT "." 1*DIGIT + +Encoding considerations: binary +This media type has all of the same encoding considerations of +application/json as described in [RFC8259] + + +Security considerations: +This media type has all of the same security +considerations of application/json as described in [RFC8259]. + +Depending on the operational context of the device or software being described by the SBOM there may be additional security requirements. These may include but are not limited to, encryption at rest, encryption in transit, and restrictions on the transmission of the SBOM to 3rd parties. These additional requirements are considered out of scope for the specification. They will typically be enforced by contract or copyright terms. + + +Interoperability considerations: +This media type has the same interoperability considerations of application/json as described in [RFC8259]. + +Published specification: +The specification can be found on the main Syft GitHub repository under the schema directory https://github.com/anchore/syft/blob/main/schema/json + +Applications which use this media: +This media type is used to specify a software bill of materials. +It will be used by tools that produce SBOMs either during the software build process or as a result of software composition analysis. + +It will also be used by tools that consume SBOMs for software +supply chain, component, supplier, license, and vulnerability +analysis. + +Fragment identifier considerations: +N/A + +Restrictions on usage: +N/A + +Provisional registration? (standards tree only): +N/A + +Additional information: + +1. Deprecated alias names for this type: N/A +2. Magic number(s): N/A +3. File extension(s): .syft.json +4. Macintosh file type code: N/A +5. Object Identifiers: N/A + +General Comments: + + +Person to contact for further information: + +1. Name: Dan Luhring +2. Email: dan.luhring@anchore.com + +Intended usage: Common +The Syft SBOM format is an open-source software bill of materials specification. It is intended to be exchanged between different parties of the software supply chain. + + +Author/Change controller: Dan Luhring, on behalf of Anchore diff --git a/ci/tools/openeuler-purl/syft-dev/schema/spdx-json/spdx-schema-2.2.json b/ci/tools/openeuler-purl/syft-dev/schema/spdx-json/spdx-schema-2.2.json new file mode 100644 index 0000000000000000000000000000000000000000..8279648c9980d38c53eb623fbf5f313e1818d89a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/schema/spdx-json/spdx-schema-2.2.json @@ -0,0 +1,610 @@ +{ + "$schema" : "http://json-schema.org/draft-07/schema#", + "$id" : "http://spdx.org/rdf/terms", + "title" : "SPDX 2.2", + "type" : "object", + "properties" : { + "Document" : { + "type" : "object", + "properties" : { + "revieweds" : { + "description" : "Reviewed", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "reviewer" : { + "description" : "The name and, optionally, contact information of the person who performed the review. Values of this property must conform to the agent and tool syntax.", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "reviewDate" : { + "description" : "The date and time at which the SpdxDocument was reviewed. This value must be in UTC and have 'Z' as its timezone indicator.", + "type" : "string" + } + } + } + }, + "hasExtractedLicensingInfos" : { + "description" : "Indicates that a particular ExtractedLicensingInfo was defined in the subject SpdxDocument.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "seeAlsos" : { + "type" : "array", + "items" : { + "type" : "string" + } + }, + "name" : { + "description" : "Identify name of this SpdxElement.", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "licenseId" : { + "description" : "A human readable short form license identifier for a license. The license ID is iether on the standard license oist or the form \"LicenseRef-\"[idString] where [idString] is a unique string containing letters, numbers, \".\", \"-\" or \"+\".", + "type" : "string" + }, + "extractedText" : { + "description" : "Verbatim license or licensing notice text that was discovered.", + "type" : "string" + } + }, + "description" : "An ExtractedLicensingInfo represents a license or licensing notice that was found in the package. Any license text that is recognized as a license may be represented as a License rather than an ExtractedLicensingInfo." + } + }, + "name" : { + "description" : "Identify name of this SpdxElement.", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "spdxVersion" : { + "description" : "Provide a reference number that can be used to understand how to parse and interpret the rest of the file. It will enable both future changes to the specification and to support backward compatibility. The version number consists of a major and minor version indicator. The major field will be incremented when incompatible changes between versions are made (one or more sections are created, modified or deleted). The minor field will be incremented when backwards compatible changes are made.", + "type" : "string" + }, + "annotations" : { + "description" : "Provide additional information about an SpdxElement.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "annotationDate" : { + "description" : "Identify when the comment was made. This is to be specified according to the combined date and time in the UTC format, as specified in the ISO 8601 standard.", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "annotator" : { + "description" : "This field identifies the person, organization or tool that has commented on a file, package, or the entire document.", + "type" : "string" + }, + "annotationType" : { + "description" : "Type of the annotation.", + "type" : "string", + "enum" : [ "OTHER", "REVIEW" ] + } + }, + "description" : "An Annotation is a comment on an SpdxItem by an agent." + } + }, + "describesPackages" : { + "description" : "The describesPackage property relates an SpdxDocument to the package which it describes.", + "type" : "array", + "items" : { + "description" : "SPDX ID for Package. The describesPackage property relates an SpdxDocument to the package which it describes.", + "type" : "string" + } + }, + "dataLicense" : { + "description" : "License expression for dataLicense. Compliance with the SPDX specification includes populating the SPDX fields therein with data related to such fields (\"SPDX-Metadata\"). The SPDX specification contains numerous fields where an SPDX document creator may provide relevant explanatory text in SPDX-Metadata. Without opining on the lawfulness of \"database rights\" (in jurisdictions where applicable), such explanatory text is copyrightable subject matter in most Berne Convention countries. By using the SPDX specification, or any portion hereof, you hereby agree that any copyright rights (as determined by your jurisdiction) in any SPDX-Metadata, including without limitation explanatory text, shall be subject to the terms of the Creative Commons CC0 1.0 Universal license. For SPDX-Metadata not containing any copyright rights, you hereby agree and acknowledge that the SPDX-Metadata is provided to you \"as-is\" and without any representations or warranties of any kind concerning the SPDX-Metadata, express, implied, statutory or otherwise, including without limitation warranties of title, merchantability, fitness for a particular purpose, non-infringement, or the absence of latent or other defects, accuracy, or the presence or absence of errors, whether or not discoverable, all to the greatest extent permissible under applicable law.", + "type" : "string" + }, + "externalDocumentRefs" : { + "description" : "Identify any external SPDX documents referenced within this SPDX document.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "externalDocumentId" : { + "description" : "externalDocumentId is a string containing letters, numbers, ., - and/or + which uniquely identifies an external document within this document.", + "type" : "string" + }, + "checksum" : { + "type" : "object", + "properties" : { + "algorithm" : { + "description" : "Identifies the algorithm used to produce the subject Checksum. Currently, SHA-1 is the only supported algorithm. It is anticipated that other algorithms will be supported at a later time.", + "type" : "string", + "enum" : [ "SHA256", "SHA1", "SHA384", "MD2", "MD4", "SHA512", "MD6", "MD5", "SHA224" ] + }, + "checksumValue" : { + "description" : "The checksumValue property provides a lower case hexidecimal encoded digest value produced using a specific algorithm.", + "type" : "string" + } + }, + "description" : "A Checksum is value that allows the contents of a file to be authenticated. Even small changes to the content of the file will change its checksum. This class allows the results of a variety of checksum and cryptographic message digest algorithms to be represented." + }, + "spdxDocument" : { + "description" : "SPDX ID for SpdxDocument. A propoerty containing an SPDX document.", + "type" : "string" + } + }, + "description" : "Information about an external SPDX document reference including the checksum. This allows for verification of the external references." + } + }, + "creationInfo" : { + "type" : "object", + "properties" : { + "comment" : { + "type" : "string" + }, + "created" : { + "description" : "Identify when the SPDX file was originally created. The date is to be specified according to combined date and time in UTC format as specified in ISO 8601 standard. This field is distinct from the fields in section 8, which involves the addition of information during a subsequent review.", + "type" : "string" + }, + "creators" : { + "description" : "Identify who (or what, in the case of a tool) created the SPDX file. If the SPDX file was created by an individual, indicate the person's name. If the SPDX file was created on behalf of a company or organization, indicate the entity name. If the SPDX file was created using a software tool, indicate the name and version for that tool. If multiple participants or tools were involved, use multiple instances of this field. Person name or organization name may be designated as “anonymous” if appropriate.", + "type" : "array", + "items" : { + "description" : "Identify who (or what, in the case of a tool) created the SPDX file. If the SPDX file was created by an individual, indicate the person's name. If the SPDX file was created on behalf of a company or organization, indicate the entity name. If the SPDX file was created using a software tool, indicate the name and version for that tool. If multiple participants or tools were involved, use multiple instances of this field. Person name or organization name may be designated as “anonymous” if appropriate.", + "type" : "string" + }, + "minItems" : 1 + }, + "licenseListVersion" : { + "description" : "An optional field for creators of the SPDX file to provide the version of the SPDX License List used when the SPDX file was created.", + "type" : "string" + } + }, + "description" : "One instance is required for each SPDX file produced. It provides the necessary information for forward and backward compatibility for processing tools." + }, + "packages" : { + "description" : "Packages referenced in the SPDX document", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "attributionTexts" : { + "description" : "This field provides a place for the SPDX data creator to record acknowledgements that may be required to be communicated in some contexts. This is not meant to include theactual complete license text (see licenseConculded and licenseDeclared), and may or may not include copyright notices (see also copyrightText). The SPDX data creator may use this field to record other acknowledgements, such as particular clauses from license texts, which may be necessary or desirable to reproduce.", + "type" : "array", + "items" : { + "description" : "This field provides a place for the SPDX data creator to record acknowledgements that may be required to be communicated in some contexts. This is not meant to include theactual complete license text (see licenseConculded and licenseDeclared), and may or may not include copyright notices (see also copyrightText). The SPDX data creator may use this field to record other acknowledgements, such as particular clauses from license texts, which may be necessary or desirable to reproduce.", + "type" : "string" + } + }, + "annotations" : { + "description" : "Provide additional information about an SpdxElement.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "annotationDate" : { + "description" : "Identify when the comment was made. This is to be specified according to the combined date and time in the UTC format, as specified in the ISO 8601 standard.", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "annotator" : { + "description" : "This field identifies the person, organization or tool that has commented on a file, package, or the entire document.", + "type" : "string" + }, + "annotationType" : { + "description" : "Type of the annotation.", + "type" : "string", + "enum" : [ "OTHER", "REVIEW" ] + } + }, + "description" : "An Annotation is a comment on an SpdxItem by an agent." + } + }, + "supplier" : { + "description" : "The name and, optionally, contact information of the person or organization who was the immediate supplier of this package to the recipient. The supplier may be different than originator when the software has been repackaged. Values of this property must conform to the agent and tool syntax.", + "type" : "string" + }, + "homepage" : { + "type" : "string" + }, + "packageVerificationCode" : { + "type" : "object", + "properties" : { + "packageVerificationCodeValue" : { + "description" : "The actual package verification code as a hex encoded value.", + "type" : "string" + }, + "packageVerificationCodeExcludedFiles" : { + "description" : "A file that was excluded when calculating the package verification code. This is usually a file containing SPDX data regarding the package. If a package contains more than one SPDX file all SPDX files must be excluded from the package verification code. If this is not done it would be impossible to correctly calculate the verification codes in both files.", + "type" : "array", + "items" : { + "description" : "A file that was excluded when calculating the package verification code. This is usually a file containing SPDX data regarding the package. If a package contains more than one SPDX file all SPDX files must be excluded from the package verification code. If this is not done it would be impossible to correctly calculate the verification codes in both files.", + "type" : "string" + } + } + }, + "description" : "A manifest based verification code (the algorithm is defined in section 4.7 of the full specification) of the SPDX Item. This allows consumers of this data and/or database to determine if an SPDX item they have in hand is identical to the SPDX item from which the data was produced. This algorithm works even if the SPDX document is included in the SPDX item." + }, + "checksums" : { + "description" : "The checksum property provides a mechanism that can be used to verify that the contents of a File or Package have not changed.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "algorithm" : { + "description" : "Identifies the algorithm used to produce the subject Checksum. Currently, SHA-1 is the only supported algorithm. It is anticipated that other algorithms will be supported at a later time.", + "type" : "string", + "enum" : [ "SHA256", "SHA1", "SHA384", "MD2", "MD4", "SHA512", "MD6", "MD5", "SHA224" ] + }, + "checksumValue" : { + "description" : "The checksumValue property provides a lower case hexidecimal encoded digest value produced using a specific algorithm.", + "type" : "string" + } + }, + "description" : "A Checksum is value that allows the contents of a file to be authenticated. Even small changes to the content of the file will change its checksum. This class allows the results of a variety of checksum and cryptographic message digest algorithms to be represented." + } + }, + "downloadLocation" : { + "description" : "The URI at which this package is available for download. Private (i.e., not publicly reachable) URIs are acceptable as values of this property. The values http://spdx.org/rdf/terms#none and http://spdx.org/rdf/terms#noassertion may be used to specify that the package is not downloadable or that no attempt was made to determine its download location, respectively.", + "type" : "string" + }, + "filesAnalyzed" : { + "description" : "Indicates whether the file content of this package has been available for or subjected to analysis when creating the SPDX document. If false indicates packages that represent metadata or URI references to a project, product, artifact, distribution or a component. If set to false, the package must not contain any files.", + "type" : "boolean" + }, + "externalRefs" : { + "description" : "An External Reference allows a Package to reference an external source of additional information, metadata, enumerations, asset identifiers, or downloadable content believed to be relevant to the Package.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "comment" : { + "type" : "string" + }, + "referenceCategory" : { + "description" : "Category for the external reference", + "type" : "string", + "enum" : [ "OTHER", "SECURITY", "PACKAGE_MANAGER" ] + }, + "referenceLocator" : { + "description" : "The unique string with no spaces necessary to access the package-specific information, metadata, or content within the target location. The format of the locator is subject to constraints defined by the .", + "type" : "string" + }, + "referenceType" : { + "description" : "Type of the external reference. These are definined in an appendix in the SPDX specification.", + "type" : "string" + } + }, + "description" : "An External Reference allows a Package to reference an external source of additional information, metadata, enumerations, asset identifiers, or downloadable content believed to be relevant to the Package." + } + }, + "licenseComments" : { + "description" : "The licenseComments property allows the preparer of the SPDX document to describe why the licensing in spdx:licenseConcluded was chosen.", + "type" : "string" + }, + "name" : { + "description" : "Identify name of this SpdxElement.", + "type" : "string" + }, + "hasFiles" : { + "description" : "Indicates that a particular file belongs to a package.", + "type" : "array", + "items" : { + "description" : "SPDX ID for File. Indicates that a particular file belongs to a package.", + "type" : "string" + } + }, + "comment" : { + "type" : "string" + }, + "summary" : { + "description" : "Provides a short description of the package.", + "type" : "string" + }, + "copyrightText" : { + "description" : "The text of copyright declarations recited in the Package or File.", + "type" : "string" + }, + "originator" : { + "description" : "The name and, optionally, contact information of the person or organization that originally created the package. Values of this property must conform to the agent and tool syntax.", + "type" : "string" + }, + "packageFileName" : { + "description" : "The base name of the package file name. For example, zlib-1.2.5.tar.gz.", + "type" : "string" + }, + "licenseInfoFromFiles" : { + "description" : "The licensing information that was discovered directly within the package. There will be an instance of this property for each distinct value of alllicenseInfoInFile properties of all files contained in the package.", + "type" : "array", + "items" : { + "description" : "License expression for licenseInfoFromFiles. The licensing information that was discovered directly within the package. There will be an instance of this property for each distinct value of alllicenseInfoInFile properties of all files contained in the package.", + "type" : "string" + } + }, + "versionInfo" : { + "description" : "Provides an indication of the version of the package that is described by this SpdxDocument.", + "type" : "string" + }, + "sourceInfo" : { + "description" : "Allows the producer(s) of the SPDX document to describe how the package was acquired and/or changed from the original source.", + "type" : "string" + }, + "description" : { + "description" : "Provides a detailed description of the package.", + "type" : "string" + } + } + } + }, + "files" : { + "description" : "Files referenced in the SPDX document", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "fileTypes" : { + "description" : "The type of the file.", + "type" : "array", + "items" : { + "description" : "The type of the file.", + "type" : "string", + "enum" : [ "OTHER", "DOCUMENTATION", "IMAGE", "VIDEO", "ARCHIVE", "SPDX", "APPLICATION", "SOURCE", "BINARY", "TEXT", "AUDIO" ] + } + }, + "attributionTexts" : { + "description" : "This field provides a place for the SPDX data creator to record acknowledgements that may be required to be communicated in some contexts. This is not meant to include theactual complete license text (see licenseConculded and licenseDeclared), and may or may not include copyright notices (see also copyrightText). The SPDX data creator may use this field to record other acknowledgements, such as particular clauses from license texts, which may be necessary or desirable to reproduce.", + "type" : "array", + "items" : { + "description" : "This field provides a place for the SPDX data creator to record acknowledgements that may be required to be communicated in some contexts. This is not meant to include theactual complete license text (see licenseConculded and licenseDeclared), and may or may not include copyright notices (see also copyrightText). The SPDX data creator may use this field to record other acknowledgements, such as particular clauses from license texts, which may be necessary or desirable to reproduce.", + "type" : "string" + } + }, + "annotations" : { + "description" : "Provide additional information about an SpdxElement.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "annotationDate" : { + "description" : "Identify when the comment was made. This is to be specified according to the combined date and time in the UTC format, as specified in the ISO 8601 standard.", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "annotator" : { + "description" : "This field identifies the person, organization or tool that has commented on a file, package, or the entire document.", + "type" : "string" + }, + "annotationType" : { + "description" : "Type of the annotation.", + "type" : "string", + "enum" : [ "OTHER", "REVIEW" ] + } + }, + "description" : "An Annotation is a comment on an SpdxItem by an agent." + } + }, + "checksums" : { + "description" : "The checksum property provides a mechanism that can be used to verify that the contents of a File or Package have not changed.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "algorithm" : { + "description" : "Identifies the algorithm used to produce the subject Checksum. Currently, SHA-1 is the only supported algorithm. It is anticipated that other algorithms will be supported at a later time.", + "type" : "string", + "enum" : [ "SHA256", "SHA1", "SHA384", "MD2", "MD4", "SHA512", "MD6", "MD5", "SHA224" ] + }, + "checksumValue" : { + "description" : "The checksumValue property provides a lower case hexidecimal encoded digest value produced using a specific algorithm.", + "type" : "string" + } + }, + "description" : "A Checksum is value that allows the contents of a file to be authenticated. Even small changes to the content of the file will change its checksum. This class allows the results of a variety of checksum and cryptographic message digest algorithms to be represented." + }, + "minItems" : 1 + }, + "noticeText" : { + "description" : "This field provides a place for the SPDX file creator to record potential legal notices found in the file. This may or may not include copyright statements.", + "type" : "string" + }, + "artifactOfs" : { + "description" : "Indicates the project in which the SpdxElement originated. Tools must preserve doap:homepage and doap:name properties and the URI (if one is known) of doap:Project resources that are values of this property. All other properties of doap:Projects are not directly supported by SPDX and may be dropped when translating to or from some SPDX formats.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { } + } + }, + "licenseComments" : { + "description" : "The licenseComments property allows the preparer of the SPDX document to describe why the licensing in spdx:licenseConcluded was chosen.", + "type" : "string" + }, + "fileName" : { + "description" : "The name of the file relative to the root of the package.", + "type" : "string" + }, + "name" : { + "description" : "Identify name of this SpdxElement.", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "copyrightText" : { + "description" : "The text of copyright declarations recited in the Package or File.", + "type" : "string" + }, + "fileContributors" : { + "description" : "This field provides a place for the SPDX file creator to record file contributors. Contributors could include names of copyright holders and/or authors who may not be copyright holders yet contributed to the file content.", + "type" : "array", + "items" : { + "description" : "This field provides a place for the SPDX file creator to record file contributors. Contributors could include names of copyright holders and/or authors who may not be copyright holders yet contributed to the file content.", + "type" : "string" + } + }, + "licenseInfoInFiles" : { + "description" : "Licensing information that was discovered directly in the subject file. This is also considered a declared license for the file.", + "type" : "array", + "items" : { + "description" : "License expression for licenseInfoInFile. Licensing information that was discovered directly in the subject file. This is also considered a declared license for the file.", + "type" : "string" + }, + "minItems" : 1 + }, + "licenseInfoFromFiles" : { + "description" : "The licensing information that was discovered directly within the package. There will be an instance of this property for each distinct value of alllicenseInfoInFile properties of all files contained in the package.", + "type" : "array", + "items" : { + "description" : "License expression for licenseInfoFromFiles. The licensing information that was discovered directly within the package. There will be an instance of this property for each distinct value of alllicenseInfoInFile properties of all files contained in the package.", + "type" : "string" + } + }, + "fileDependencies" : { + "type" : "array", + "items" : { + "description" : "SPDX ID for File", + "type" : "string" + } + } + } + } + }, + "snippets" : { + "description" : "Snippets referenced in the SPDX document", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "ranges" : { + "description" : "This field defines the byte range in the original host file (in X.2) that the snippet information applies to", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "startPointer" : { + "type" : "object", + "properties" : { + "reference" : { + "description" : "SPDX ID for File", + "type" : "string" + } + } + }, + "endPointer" : { + "type" : "object", + "properties" : { + "reference" : { + "description" : "SPDX ID for File", + "type" : "string" + } + } + } + } + }, + "minItems" : 1 + }, + "licenseComments" : { + "description" : "The licenseComments property allows the preparer of the SPDX document to describe why the licensing in spdx:licenseConcluded was chosen.", + "type" : "string" + }, + "attributionTexts" : { + "description" : "This field provides a place for the SPDX data creator to record acknowledgements that may be required to be communicated in some contexts. This is not meant to include theactual complete license text (see licenseConculded and licenseDeclared), and may or may not include copyright notices (see also copyrightText). The SPDX data creator may use this field to record other acknowledgements, such as particular clauses from license texts, which may be necessary or desirable to reproduce.", + "type" : "array", + "items" : { + "description" : "This field provides a place for the SPDX data creator to record acknowledgements that may be required to be communicated in some contexts. This is not meant to include theactual complete license text (see licenseConculded and licenseDeclared), and may or may not include copyright notices (see also copyrightText). The SPDX data creator may use this field to record other acknowledgements, such as particular clauses from license texts, which may be necessary or desirable to reproduce.", + "type" : "string" + } + }, + "name" : { + "description" : "Identify name of this SpdxElement.", + "type" : "string" + }, + "snippetFromFile" : { + "description" : "SPDX ID for File. File containing the SPDX element (e.g. the file contaning a snippet).", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "copyrightText" : { + "description" : "The text of copyright declarations recited in the Package or File.", + "type" : "string" + }, + "licenseInfoInSnippets" : { + "description" : "Licensing information that was discovered directly in the subject snippet. This is also considered a declared license for the snippet.", + "type" : "array", + "items" : { + "description" : "License expression for licenseInfoInSnippet. Licensing information that was discovered directly in the subject snippet. This is also considered a declared license for the snippet.", + "type" : "string" + } + }, + "annotations" : { + "description" : "Provide additional information about an SpdxElement.", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "annotationDate" : { + "description" : "Identify when the comment was made. This is to be specified according to the combined date and time in the UTC format, as specified in the ISO 8601 standard.", + "type" : "string" + }, + "comment" : { + "type" : "string" + }, + "annotator" : { + "description" : "This field identifies the person, organization or tool that has commented on a file, package, or the entire document.", + "type" : "string" + }, + "annotationType" : { + "description" : "Type of the annotation.", + "type" : "string", + "enum" : [ "OTHER", "REVIEW" ] + } + }, + "description" : "An Annotation is a comment on an SpdxItem by an agent." + } + }, + "licenseInfoFromFiles" : { + "description" : "The licensing information that was discovered directly within the package. There will be an instance of this property for each distinct value of alllicenseInfoInFile properties of all files contained in the package.", + "type" : "array", + "items" : { + "description" : "License expression for licenseInfoFromFiles. The licensing information that was discovered directly within the package. There will be an instance of this property for each distinct value of alllicenseInfoInFile properties of all files contained in the package.", + "type" : "string" + } + } + } + } + }, + "relationships" : { + "description" : "Relationships referenced in the SPDX document", + "type" : "array", + "items" : { + "type" : "object", + "properties" : { + "comment" : { + "type" : "string" + }, + "relationshipType" : { + "description" : "Describes the type of relationship between two SPDX elements.", + "type" : "string", + "enum" : [ "VARIANT_OF", "COPY_OF", "PATCH_FOR", "TEST_DEPENDENCY_OF", "CONTAINED_BY", "DATA_FILE_OF", "OPTIONAL_COMPONENT_OF", "ANCESTOR_OF", "GENERATES", "CONTAINS", "OPTIONAL_DEPENDENCY_OF", "FILE_ADDED", "DEV_DEPENDENCY_OF", "DEPENDENCY_OF", "BUILD_DEPENDENCY_OF", "DESCRIBES", "PREREQUISITE_FOR", "HAS_PREREQUISITE", "PROVIDED_DEPENDENCY_OF", "DYNAMIC_LINK", "DESCRIBED_BY", "METAFILE_OF", "DEPENDENCY_MANIFEST_OF", "PATCH_APPLIED", "RUNTIME_DEPENDENCY_OF", "TEST_OF", "TEST_TOOL_OF", "DEPENDS_ON", "FILE_MODIFIED", "DISTRIBUTION_ARTIFACT", "DOCUMENTATION_OF", "GENERATED_FROM", "STATIC_LINK", "OTHER", "BUILD_TOOL_OF", "TEST_CASE_OF", "PACKAGE_OF", "DESCENDANT_OF", "FILE_DELETED", "EXPANDED_FROM_ARCHIVE", "DEV_TOOL_OF", "EXAMPLE_OF" ] + }, + "relatedSpdxElement" : { + "description" : "SPDX ID for SpdxElement. A related SpdxElement.", + "type" : "string" + } + } + } + } + } + } + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/artifact/id.go b/ci/tools/openeuler-purl/syft-dev/syft/artifact/id.go new file mode 100644 index 0000000000000000000000000000000000000000..fc624a7eb109a26e0c794239e26937e881c09096 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/artifact/id.go @@ -0,0 +1,26 @@ +package artifact + +import ( + "fmt" + + "github.com/mitchellh/hashstructure/v2" +) + +// ID represents a unique value for each package added to a package catalog. +type ID string + +type Identifiable interface { + ID() ID +} + +func IDByHash(obj interface{}) (ID, error) { + f, err := hashstructure.Hash(obj, hashstructure.FormatV2, &hashstructure.HashOptions{ + ZeroNil: true, + SlicesAsSets: true, + }) + if err != nil { + return "", fmt.Errorf("could not build ID for object=%+v: %+v", obj, err) + } + + return ID(fmt.Sprintf("%x", f)), nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/artifact/relationship.go b/ci/tools/openeuler-purl/syft-dev/syft/artifact/relationship.go new file mode 100644 index 0000000000000000000000000000000000000000..4c2fadfab0209b07373eee61cb887952f01ec4a4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/artifact/relationship.go @@ -0,0 +1,33 @@ +package artifact + +const ( + // OwnershipByFileOverlapRelationship (supports package-to-package linkages) indicates that the parent package + // claims ownership of a child package since the parent metadata indicates overlap with a location that a + // cataloger found the child package by. This relationship must be created only after all package cataloging + // has been completed. + OwnershipByFileOverlapRelationship RelationshipType = "ownership-by-file-overlap" + + // ContainsRelationship (supports any-to-any linkages) is a proxy for the SPDX 2.2 CONTAINS relationship. + ContainsRelationship RelationshipType = "contains" + + // RuntimeDependencyOfRelationship is a proxy for the SPDX 2.2.1 RUNTIME_DEPENDENCY_OF relationship. + RuntimeDependencyOfRelationship RelationshipType = "runtime-dependency-of" + + // DevDependencyOfRelationship is a proxy for the SPDX 2.2.1 DEV_DEPENDENCY_OF relationship. + DevDependencyOfRelationship RelationshipType = "dev-dependency-of" + + // BuildDependencyOfRelationship is a proxy for the SPDX 2.2.1 BUILD_DEPENDENCY_OF relationship. + BuildDependencyOfRelationship RelationshipType = "build-dependency-of" + + // DependencyOfRelationship is a proxy for the SPDX 2.2.1 DEPENDENCY_OF relationship. + DependencyOfRelationship RelationshipType = "dependency-of" +) + +type RelationshipType string + +type Relationship struct { + From Identifiable + To Identifiable + Type RelationshipType + Data interface{} +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/encode_decode.go b/ci/tools/openeuler-purl/syft-dev/syft/encode_decode.go new file mode 100644 index 0000000000000000000000000000000000000000..0b54a5d568cc7e5c2507f5aa0f973a83568873f4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/encode_decode.go @@ -0,0 +1,36 @@ +package syft + +import ( + "bytes" + "fmt" + "io" + + "github.com/anchore/syft/syft/sbom" +) + +// Encode takes all SBOM elements and a format option and encodes an SBOM document. +func Encode(s sbom.SBOM, f sbom.Format) ([]byte, error) { + buff := bytes.Buffer{} + + if err := f.Encode(&buff, s); err != nil { + return nil, fmt.Errorf("unable to encode sbom: %w", err) + } + + return buff.Bytes(), nil +} + +// Decode takes a reader for an SBOM and generates all internal SBOM elements. +func Decode(reader io.Reader) (*sbom.SBOM, sbom.Format, error) { + by, err := io.ReadAll(reader) + if err != nil { + return nil, nil, fmt.Errorf("unable to read sbom: %w", err) + } + + f := IdentifyFormat(by) + if f == nil { + return nil, nil, fmt.Errorf("unable to identify format") + } + + s, err := f.Decode(bytes.NewReader(by)) + return s, f, err +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/event/event.go b/ci/tools/openeuler-purl/syft-dev/syft/event/event.go new file mode 100644 index 0000000000000000000000000000000000000000..e42cfae7dad259b331845b187f213f6af43a6430 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/event/event.go @@ -0,0 +1,37 @@ +/* +Package event provides event types for all events that the syft library published onto the event bus. By convention, for each event +defined here there should be a corresponding event parser defined in the parsers/ child package. +*/ +package event + +import "github.com/wagoodman/go-partybus" + +const ( + // AppUpdateAvailable is a partybus event that occurs when an application update is available + AppUpdateAvailable partybus.EventType = "syft-app-update-available" + + // PackageCatalogerStarted is a partybus event that occurs when the package cataloging has begun + PackageCatalogerStarted partybus.EventType = "syft-package-cataloger-started-event" + + //nolint:gosec + // SecretsCatalogerStarted is a partybus event that occurs when the secrets cataloging has begun + SecretsCatalogerStarted partybus.EventType = "syft-secrets-cataloger-started-event" + + // FileMetadataCatalogerStarted is a partybus event that occurs when the file metadata cataloging has begun + FileMetadataCatalogerStarted partybus.EventType = "syft-file-metadata-cataloger-started-event" + + // FileDigestsCatalogerStarted is a partybus event that occurs when the file digests cataloging has begun + FileDigestsCatalogerStarted partybus.EventType = "syft-file-digests-cataloger-started-event" + + // FileIndexingStarted is a partybus event that occurs when the directory resolver begins indexing a filesystem + FileIndexingStarted partybus.EventType = "syft-file-indexing-started-event" + + // Exit is a partybus event that occurs when an analysis result is ready for final presentation + Exit partybus.EventType = "syft-exit-event" + + // ImportStarted is a partybus event that occurs when an SBOM upload process has begun + ImportStarted partybus.EventType = "syft-import-started-event" + + // UploadAttestation is a partybus event that occurs when syft uploads an attestation to an OCI registry (+ any transparency log) + UploadAttestation partybus.EventType = "syft-upload-attestation" +) diff --git a/ci/tools/openeuler-purl/syft-dev/syft/event/parsers/parsers.go b/ci/tools/openeuler-purl/syft-dev/syft/event/parsers/parsers.go new file mode 100644 index 0000000000000000000000000000000000000000..f384044cd5212f20c5e8287d81d052c3d027a645 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/event/parsers/parsers.go @@ -0,0 +1,166 @@ +/* +Package parsers provides parser helpers to extract payloads for each event type that the syft library publishes onto the event bus. +*/ +package parsers + +import ( + "fmt" + + "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg/cataloger" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/go-progress" +) + +type ErrBadPayload struct { + Type partybus.EventType + Field string + Value interface{} +} + +func (e *ErrBadPayload) Error() string { + return fmt.Sprintf("event='%s' has bad event payload field='%v': '%+v'", string(e.Type), e.Field, e.Value) +} + +func newPayloadErr(t partybus.EventType, field string, value interface{}) error { + return &ErrBadPayload{ + Type: t, + Field: field, + Value: value, + } +} + +func checkEventType(actual, expected partybus.EventType) error { + if actual != expected { + return newPayloadErr(expected, "Type", actual) + } + return nil +} + +func ParsePackageCatalogerStarted(e partybus.Event) (*cataloger.Monitor, error) { + if err := checkEventType(e.Type, event.PackageCatalogerStarted); err != nil { + return nil, err + } + + monitor, ok := e.Value.(cataloger.Monitor) + if !ok { + return nil, newPayloadErr(e.Type, "Value", e.Value) + } + + return &monitor, nil +} + +func ParseSecretsCatalogingStarted(e partybus.Event) (*file.SecretsMonitor, error) { + if err := checkEventType(e.Type, event.SecretsCatalogerStarted); err != nil { + return nil, err + } + + monitor, ok := e.Value.(file.SecretsMonitor) + if !ok { + return nil, newPayloadErr(e.Type, "Value", e.Value) + } + + return &monitor, nil +} + +func ParseFileMetadataCatalogingStarted(e partybus.Event) (progress.StagedProgressable, error) { + if err := checkEventType(e.Type, event.FileMetadataCatalogerStarted); err != nil { + return nil, err + } + + prog, ok := e.Value.(progress.StagedProgressable) + if !ok { + return nil, newPayloadErr(e.Type, "Value", e.Value) + } + + return prog, nil +} + +func ParseFileDigestsCatalogingStarted(e partybus.Event) (progress.StagedProgressable, error) { + if err := checkEventType(e.Type, event.FileDigestsCatalogerStarted); err != nil { + return nil, err + } + + prog, ok := e.Value.(progress.StagedProgressable) + if !ok { + return nil, newPayloadErr(e.Type, "Value", e.Value) + } + + return prog, nil +} + +func ParseFileIndexingStarted(e partybus.Event) (string, progress.StagedProgressable, error) { + if err := checkEventType(e.Type, event.FileIndexingStarted); err != nil { + return "", nil, err + } + + path, ok := e.Source.(string) + if !ok { + return "", nil, newPayloadErr(e.Type, "Source", e.Source) + } + + prog, ok := e.Value.(progress.StagedProgressable) + if !ok { + return "", nil, newPayloadErr(e.Type, "Value", e.Value) + } + + return path, prog, nil +} + +func ParseExit(e partybus.Event) (func() error, error) { + if err := checkEventType(e.Type, event.Exit); err != nil { + return nil, err + } + + fn, ok := e.Value.(func() error) + if !ok { + return nil, newPayloadErr(e.Type, "Value", e.Value) + } + + return fn, nil +} + +func ParseAppUpdateAvailable(e partybus.Event) (string, error) { + if err := checkEventType(e.Type, event.AppUpdateAvailable); err != nil { + return "", err + } + + newVersion, ok := e.Value.(string) + if !ok { + return "", newPayloadErr(e.Type, "Value", e.Value) + } + + return newVersion, nil +} + +func ParseImportStarted(e partybus.Event) (string, progress.StagedProgressable, error) { + if err := checkEventType(e.Type, event.ImportStarted); err != nil { + return "", nil, err + } + + host, ok := e.Source.(string) + if !ok { + return "", nil, newPayloadErr(e.Type, "Source", e.Source) + } + + prog, ok := e.Value.(progress.StagedProgressable) + if !ok { + return "", nil, newPayloadErr(e.Type, "Value", e.Value) + } + + return host, prog, nil +} + +func ParseUploadAttestation(e partybus.Event) (progress.StagedProgressable, error) { + if err := checkEventType(e.Type, event.UploadAttestation); err != nil { + return nil, err + } + + prog, ok := e.Value.(progress.StagedProgressable) + if !ok { + return nil, newPayloadErr(e.Type, "Value", e.Value) + } + + return prog, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/all_regular_files.go b/ci/tools/openeuler-purl/syft-dev/syft/file/all_regular_files.go new file mode 100644 index 0000000000000000000000000000000000000000..e7612c8b2420c48dc04e4935f96a5566329d47b3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/all_regular_files.go @@ -0,0 +1,30 @@ +package file + +import ( + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/source" +) + +func allRegularFiles(resolver source.FileResolver) (locations []source.Location) { + for location := range resolver.AllLocations() { + resolvedLocations, err := resolver.FilesByPath(location.RealPath) + if err != nil { + log.Warnf("unable to resolve %+v: %+v", location, err) + continue + } + + for _, resolvedLocation := range resolvedLocations { + metadata, err := resolver.FileMetadataByLocation(resolvedLocation) + if err != nil { + log.Warnf("unable to get metadata for %+v: %+v", location, err) + continue + } + + if metadata.Type != source.RegularFile { + continue + } + locations = append(locations, resolvedLocation) + } + } + return locations +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/all_regular_files_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/all_regular_files_test.go new file mode 100644 index 0000000000000000000000000000000000000000..aad33b3487bb62ca4d49ccd52caa7c02d6f12352 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/all_regular_files_test.go @@ -0,0 +1,74 @@ +package file + +import ( + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/anchore/syft/syft/source" + "github.com/scylladb/go-set/strset" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + "testing" +) + +func Test_allRegularFiles(t *testing.T) { + type access struct { + realPath string + virtualPath string + } + tests := []struct { + name string + setup func() source.FileResolver + wantRealPaths *strset.Set + wantVirtualPaths *strset.Set + }{ + { + name: "image", + setup: func() source.FileResolver { + testImage := "image-file-type-mix" + + if *updateImageGoldenFiles { + imagetest.UpdateGoldenFixtureImage(t, testImage) + } + + img := imagetest.GetGoldenFixtureImage(t, testImage) + + s, err := source.NewFromImage(img, "---") + require.NoError(t, err) + + r, err := s.FileResolver(source.SquashedScope) + require.NoError(t, err) + + return r + }, + wantRealPaths: strset.New("/file-1.txt"), + wantVirtualPaths: strset.New("/file-1.txt", "/symlink-1", "/hardlink-1"), + }, + { + name: "directory", + setup: func() source.FileResolver { + s, err := source.NewFromDirectory("test-fixtures/symlinked-root/nested/link-root") + require.NoError(t, err) + r, err := s.FileResolver(source.SquashedScope) + require.NoError(t, err) + return r + }, + wantRealPaths: strset.New("file1.txt", "nested/file2.txt"), + wantVirtualPaths: strset.New("nested/linked-file1.txt"), + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + resolver := tt.setup() + locations := allRegularFiles(resolver) + realLocations := strset.New() + virtualLocations := strset.New() + for _, l := range locations { + realLocations.Add(l.RealPath) + if l.VirtualPath != "" { + virtualLocations.Add(l.VirtualPath) + } + } + assert.ElementsMatch(t, tt.wantRealPaths.List(), realLocations.List(), "mismatched real paths") + assert.ElementsMatch(t, tt.wantVirtualPaths.List(), virtualLocations.List(), "mismatched virtual paths") + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/classification_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/file/classification_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..01a0685efe234df12e3bb42c33bad3ab4fa0e20b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/classification_cataloger.go @@ -0,0 +1,38 @@ +package file + +import ( + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/source" +) + +type ClassificationCataloger struct { + classifiers []Classifier +} + +func NewClassificationCataloger(classifiers []Classifier) (*ClassificationCataloger, error) { + return &ClassificationCataloger{ + classifiers: classifiers, + }, nil +} + +func (i *ClassificationCataloger) Catalog(resolver source.FileResolver) (map[source.Coordinates][]Classification, error) { + results := make(map[source.Coordinates][]Classification) + + numResults := 0 + for _, location := range allRegularFiles(resolver) { + for _, classifier := range i.classifiers { + result, err := classifier.Classify(resolver, location) + if err != nil { + log.Warnf("file classification cataloger failed with class=%q at location=%+v: %+v", classifier.Class, location, err) + continue + } + if result != nil { + results[location.Coordinates] = append(results[location.Coordinates], *result) + numResults++ + } + } + } + log.Debugf("file classifier discovered %d results", numResults) + + return results, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/classification_cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/classification_cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..da6fb37cb7bb2842158682a68bf66412cd7d49e3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/classification_cataloger_test.go @@ -0,0 +1,207 @@ +package file + +import ( + "github.com/anchore/stereoscope/pkg/imagetest" + "testing" + + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" +) + +func TestClassifierCataloger_DefaultClassifiers_PositiveCases(t *testing.T) { + tests := []struct { + name string + fixtureDir string + location string + expected []Classification + expectedErr func(assert.TestingT, error, ...interface{}) bool + }{ + { + name: "positive-libpython3.7.so", + fixtureDir: "test-fixtures/classifiers/positive", + location: "libpython3.7.so", + expected: []Classification{ + { + Class: "python-binary", + Metadata: map[string]string{ + "version": "3.7.4a-vZ9", + }, + }, + }, + expectedErr: assert.NoError, + }, + { + name: "positive-python3.6", + fixtureDir: "test-fixtures/classifiers/positive", + location: "python3.6", + expected: []Classification{ + { + Class: "python-binary", + Metadata: map[string]string{ + "version": "3.6.3a-vZ9", + }, + }, + }, + expectedErr: assert.NoError, + }, + { + name: "positive-patchlevel.h", + fixtureDir: "test-fixtures/classifiers/positive", + location: "patchlevel.h", + expected: []Classification{ + { + Class: "cpython-source", + Metadata: map[string]string{ + "version": "3.9-aZ5", + }, + }, + }, + expectedErr: assert.NoError, + }, + { + name: "positive-go", + fixtureDir: "test-fixtures/classifiers/positive", + location: "go", + expected: []Classification{ + { + Class: "go-binary", + Metadata: map[string]string{ + "version": "1.14", + }, + }, + }, + expectedErr: assert.NoError, + }, + { + name: "positive-go-hint", + fixtureDir: "test-fixtures/classifiers/positive", + location: "VERSION", + expected: []Classification{ + { + Class: "go-binary-hint", + Metadata: map[string]string{ + "version": "1.15", + }, + }, + }, + expectedErr: assert.NoError, + }, + { + name: "positive-busybox", + fixtureDir: "test-fixtures/classifiers/positive", + location: "[", // note: busybox is a link to [ + expected: []Classification{ + { + Class: "busybox-binary", + Metadata: map[string]string{ + "version": "3.33.3", + }, + }, + }, + expectedErr: assert.NoError, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + c, err := NewClassificationCataloger(DefaultClassifiers) + test.expectedErr(t, err) + + src, err := source.NewFromDirectory(test.fixtureDir) + test.expectedErr(t, err) + + resolver, err := src.FileResolver(source.SquashedScope) + test.expectedErr(t, err) + + actualResults, err := c.Catalog(resolver) + test.expectedErr(t, err) + + ok := false + for actualLoc, actualClassification := range actualResults { + if test.location == actualLoc.RealPath { + ok = true + assert.Equal(t, test.expected, actualClassification) + } + } + + if !ok { + t.Fatalf("could not find test location=%q", test.location) + } + + }) + } +} + +func TestClassifierCataloger_DefaultClassifiers_PositiveCases_Image(t *testing.T) { + tests := []struct { + name string + fixtureImage string + location string + expected []Classification + expectedErr func(assert.TestingT, error, ...interface{}) bool + }{ + { + name: "busybox-regression", + fixtureImage: "image-busybox", + location: "/bin/[", + expected: []Classification{ + { + Class: "busybox-binary", + Metadata: map[string]string{ + "version": "1.35.0", + }, + }, + }, + expectedErr: assert.NoError, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + c, err := NewClassificationCataloger(DefaultClassifiers) + test.expectedErr(t, err) + + img := imagetest.GetFixtureImage(t, "docker-archive", test.fixtureImage) + src, err := source.NewFromImage(img, "test-img") + test.expectedErr(t, err) + + resolver, err := src.FileResolver(source.SquashedScope) + test.expectedErr(t, err) + + actualResults, err := c.Catalog(resolver) + test.expectedErr(t, err) + + ok := false + for actuaLoc, actualClassification := range actualResults { + if actuaLoc.RealPath == test.location { + ok = true + assert.Equal(t, test.expected, actualClassification) + } + } + + if !ok { + t.Fatalf("could not find test location=%q", test.location) + } + + }) + } +} + +func TestClassifierCataloger_DefaultClassifiers_NegativeCases(t *testing.T) { + + c, err := NewClassificationCataloger(DefaultClassifiers) + assert.NoError(t, err) + + src, err := source.NewFromDirectory("test-fixtures/classifiers/negative") + assert.NoError(t, err) + + resolver, err := src.FileResolver(source.SquashedScope) + assert.NoError(t, err) + + actualResults, err := c.Catalog(resolver) + assert.NoError(t, err) + assert.Equal(t, 0, len(actualResults)) + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/classifier.go b/ci/tools/openeuler-purl/syft-dev/syft/file/classifier.go new file mode 100644 index 0000000000000000000000000000000000000000..d4efa538a1e8474f0a59f80782e597c596fc4d35 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/classifier.go @@ -0,0 +1,141 @@ +package file + +import ( + "bytes" + "fmt" + "io/ioutil" + "regexp" + "text/template" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/source" +) + +var DefaultClassifiers = []Classifier{ + { + Class: "python-binary", + FilepathPatterns: []*regexp.Regexp{ + regexp.MustCompile(`(.*/|^)python(?P[0-9]+\.[0-9]+)$`), + regexp.MustCompile(`(.*/|^)libpython(?P[0-9]+\.[0-9]+).so.*$`), + }, + EvidencePatternTemplates: []string{ + `(?m)(?P{{ .version }}\.[0-9]+[-_a-zA-Z0-9]*)`, + }, + }, + { + Class: "cpython-source", + FilepathPatterns: []*regexp.Regexp{ + regexp.MustCompile(`(.*/|^)patchlevel.h$`), + }, + EvidencePatternTemplates: []string{ + `(?m)#define\s+PY_VERSION\s+"?(?P[0-9\.\-_a-zA-Z]+)"?`, + }, + }, + { + Class: "go-binary", + FilepathPatterns: []*regexp.Regexp{ + regexp.MustCompile(`(.*/|^)go$`), + }, + EvidencePatternTemplates: []string{ + `(?m)go(?P[0-9]+\.[0-9]+(\.[0-9]+|beta[0-9]+|alpha[0-9]+|rc[0-9]+)?)`, + }, + }, + { + Class: "go-binary-hint", + FilepathPatterns: []*regexp.Regexp{ + regexp.MustCompile(`(.*/|^)VERSION$`), + }, + EvidencePatternTemplates: []string{ + `(?m)go(?P[0-9]+\.[0-9]+(\.[0-9]+|beta[0-9]+|alpha[0-9]+|rc[0-9]+)?)`, + }, + }, + { + Class: "busybox-binary", + FilepathPatterns: []*regexp.Regexp{ + regexp.MustCompile(`(.*/|^)busybox$`), + }, + EvidencePatternTemplates: []string{ + `(?m)BusyBox\s+v(?P[0-9]+\.[0-9]+\.[0-9]+)`, + }, + }, +} + +type Classifier struct { + Class string + FilepathPatterns []*regexp.Regexp + EvidencePatternTemplates []string +} + +type Classification struct { + Class string `json:"class"` + Metadata map[string]string `json:"metadata"` +} + +func (c Classifier) Classify(resolver source.FileResolver, location source.Location) (*Classification, error) { + doesFilepathMatch, filepathNamedGroupValues := filepathMatches(c.FilepathPatterns, location) + if !doesFilepathMatch { + return nil, nil + } + + contentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + return nil, err + } + defer internal.CloseAndLogError(contentReader, location.VirtualPath) + + // TODO: there is room for improvement here, as this may use an excessive amount of memory. Alternate approach is to leverage a RuneReader. + contents, err := ioutil.ReadAll(contentReader) + if err != nil { + return nil, err + } + + var result *Classification + for _, patternTemplate := range c.EvidencePatternTemplates { + tmpl, err := template.New("").Parse(patternTemplate) + if err != nil { + return nil, fmt.Errorf("unable to parse classifier template=%q : %w", patternTemplate, err) + } + + patternBuf := &bytes.Buffer{} + err = tmpl.Execute(patternBuf, filepathNamedGroupValues) + if err != nil { + return nil, fmt.Errorf("unable to render template: %w", err) + } + + pattern, err := regexp.Compile(patternBuf.String()) + if err != nil { + return nil, fmt.Errorf("unable to compile rendered regex=%q: %w", patternBuf.String(), err) + } + + if !pattern.Match(contents) { + continue + } + + matchMetadata := internal.MatchNamedCaptureGroups(pattern, string(contents)) + if result == nil { + result = &Classification{ + Class: c.Class, + Metadata: matchMetadata, + } + } else { + for key, value := range matchMetadata { + result.Metadata[key] = value + } + } + } + return result, nil +} + +func filepathMatches(patterns []*regexp.Regexp, location source.Location) (bool, map[string]string) { + for _, path := range []string{location.RealPath, location.VirtualPath} { + if path == "" { + continue + } + for _, pattern := range patterns { + if pattern.MatchString(path) { + return true, internal.MatchNamedCaptureGroups(pattern, path) + } + } + } + return false, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/classifier_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/classifier_test.go new file mode 100644 index 0000000000000000000000000000000000000000..9151f3f5bb520f5519377d289991b7ba4b013df5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/classifier_test.go @@ -0,0 +1,96 @@ +package file + +import ( + "regexp" + "testing" + + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" +) + +func TestFilepathMatches(t *testing.T) { + tests := []struct { + name string + location source.Location + patterns []string + expectedMatches bool + expectedNamedGroups map[string]string + }{ + { + name: "simple-filename-match", + location: source.Location{ + Coordinates: source.Coordinates{ + RealPath: "python2.7", + }, + }, + patterns: []string{ + `python([0-9]+\.[0-9]+)$`, + }, + expectedMatches: true, + }, + { + name: "filepath-match", + location: source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/usr/bin/python2.7", + }, + }, + patterns: []string{ + `python([0-9]+\.[0-9]+)$`, + }, + expectedMatches: true, + }, + { + name: "virtual-filepath-match", + location: source.Location{ + VirtualPath: "/usr/bin/python2.7", + }, + patterns: []string{ + `python([0-9]+\.[0-9]+)$`, + }, + expectedMatches: true, + }, + { + name: "full-filepath-match", + location: source.Location{ + VirtualPath: "/usr/bin/python2.7", + }, + patterns: []string{ + `.*/bin/python([0-9]+\.[0-9]+)$`, + }, + expectedMatches: true, + }, + { + name: "anchored-filename-match-FAILS", + location: source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/usr/bin/python2.7", + }, + }, + patterns: []string{ + `^python([0-9]+\.[0-9]+)$`, + }, + expectedMatches: false, + }, + { + name: "empty-filename-match-FAILS", + location: source.Location{}, + patterns: []string{ + `^python([0-9]+\.[0-9]+)$`, + }, + expectedMatches: false, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + var patterns []*regexp.Regexp + for _, p := range test.patterns { + patterns = append(patterns, regexp.MustCompile(p)) + } + actualMatches, actualNamedGroups := filepathMatches(patterns, test.location) + assert.Equal(t, test.expectedMatches, actualMatches) + assert.Equal(t, test.expectedNamedGroups, actualNamedGroups) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/contents_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/file/contents_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..b65a042841c4257f88671cf085bf4aede819af69 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/contents_cataloger.go @@ -0,0 +1,78 @@ +package file + +import ( + "bytes" + "encoding/base64" + "fmt" + "io" + + "github.com/anchore/syft/internal" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/source" +) + +type ContentsCataloger struct { + globs []string + skipFilesAboveSizeInBytes int64 +} + +func NewContentsCataloger(globs []string, skipFilesAboveSize int64) (*ContentsCataloger, error) { + return &ContentsCataloger{ + globs: globs, + skipFilesAboveSizeInBytes: skipFilesAboveSize, + }, nil +} + +func (i *ContentsCataloger) Catalog(resolver source.FileResolver) (map[source.Coordinates]string, error) { + results := make(map[source.Coordinates]string) + var locations []source.Location + + locations, err := resolver.FilesByGlob(i.globs...) + if err != nil { + return nil, err + } + for _, location := range locations { + metadata, err := resolver.FileMetadataByLocation(location) + if err != nil { + return nil, err + } + + if i.skipFilesAboveSizeInBytes > 0 && metadata.Size > i.skipFilesAboveSizeInBytes { + continue + } + + result, err := i.catalogLocation(resolver, location) + if internal.IsErrPathPermission(err) { + log.Debugf("file contents cataloger skipping - %+v", err) + continue + } + if err != nil { + return nil, err + } + results[location.Coordinates] = result + } + log.Debugf("file contents cataloger processed %d files", len(results)) + + return results, nil +} + +func (i *ContentsCataloger) catalogLocation(resolver source.FileResolver, location source.Location) (string, error) { + contentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + return "", err + } + defer internal.CloseAndLogError(contentReader, location.VirtualPath) + + buf := &bytes.Buffer{} + encoder := base64.NewEncoder(base64.StdEncoding, buf) + if _, err = io.Copy(encoder, contentReader); err != nil { + return "", internal.ErrPath{Context: "contents-cataloger", Path: location.RealPath, Err: err} + } + // note: it's important to close the reader before reading from the buffer since closing will flush the remaining bytes + if err := encoder.Close(); err != nil { + return "", fmt.Errorf("unable to close base64 encoder: %w", err) + } + + return buf.String(), nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/contents_cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/contents_cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d13025c4c8313dd9c69a962fbb27824008f84f42 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/contents_cataloger_test.go @@ -0,0 +1,79 @@ +package file + +import ( + "testing" + + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" +) + +func TestContentsCataloger(t *testing.T) { + allFiles := []string{"test-fixtures/last/path.txt", "test-fixtures/another-path.txt", "test-fixtures/a-path.txt"} + + tests := []struct { + name string + globs []string + maxSize int64 + files []string + expected map[source.Coordinates]string + }{ + { + name: "multi-pattern", + globs: []string{"test-fixtures/last/*.txt", "test-fixtures/*.txt"}, + files: allFiles, + expected: map[source.Coordinates]string{ + source.NewLocation("test-fixtures/last/path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9sYXN0L3BhdGgudHh0IGZpbGUgY29udGVudHMh", + source.NewLocation("test-fixtures/another-path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9hbm90aGVyLXBhdGgudHh0IGZpbGUgY29udGVudHMh", + source.NewLocation("test-fixtures/a-path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9hLXBhdGgudHh0IGZpbGUgY29udGVudHMh", + }, + }, + { + name: "no-patterns", + globs: []string{}, + files: []string{"test-fixtures/last/path.txt", "test-fixtures/another-path.txt", "test-fixtures/a-path.txt"}, + expected: map[source.Coordinates]string{}, + }, + { + name: "all-txt", + globs: []string{"**/*.txt"}, + files: allFiles, + expected: map[source.Coordinates]string{ + source.NewLocation("test-fixtures/last/path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9sYXN0L3BhdGgudHh0IGZpbGUgY29udGVudHMh", + source.NewLocation("test-fixtures/another-path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9hbm90aGVyLXBhdGgudHh0IGZpbGUgY29udGVudHMh", + source.NewLocation("test-fixtures/a-path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9hLXBhdGgudHh0IGZpbGUgY29udGVudHMh", + }, + }, + { + name: "subpath", + globs: []string{"test-fixtures/*.txt"}, + files: allFiles, + expected: map[source.Coordinates]string{ + source.NewLocation("test-fixtures/another-path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9hbm90aGVyLXBhdGgudHh0IGZpbGUgY29udGVudHMh", + source.NewLocation("test-fixtures/a-path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9hLXBhdGgudHh0IGZpbGUgY29udGVudHMh", + }, + }, + { + name: "size-filter", + maxSize: 42, + globs: []string{"**/*.txt"}, + files: allFiles, + expected: map[source.Coordinates]string{ + source.NewLocation("test-fixtures/last/path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9sYXN0L3BhdGgudHh0IGZpbGUgY29udGVudHMh", + source.NewLocation("test-fixtures/a-path.txt").Coordinates: "dGVzdC1maXh0dXJlcy9hLXBhdGgudHh0IGZpbGUgY29udGVudHMh", + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + c, err := NewContentsCataloger(test.globs, test.maxSize) + assert.NoError(t, err) + + resolver := source.NewMockResolverForPaths(test.files...) + actual, err := c.Catalog(resolver) + assert.NoError(t, err) + assert.Equal(t, test.expected, actual, "mismatched contents") + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/digest.go b/ci/tools/openeuler-purl/syft-dev/syft/file/digest.go new file mode 100644 index 0000000000000000000000000000000000000000..87b53dbb8335caee5e44af9c26b7fa0e8478c2f0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/digest.go @@ -0,0 +1,6 @@ +package file + +type Digest struct { + Algorithm string `json:"algorithm"` + Value string `json:"value"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/digest_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/file/digest_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..edc096c16b148df1490a019dfb54a224640409f3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/digest_cataloger.go @@ -0,0 +1,147 @@ +package file + +import ( + "crypto" + "errors" + "fmt" + "hash" + "io" + "strings" + + "github.com/anchore/syft/internal" + + "github.com/anchore/syft/internal/log" + + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/syft/event" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/go-progress" + + "github.com/anchore/syft/syft/source" +) + +var errUndigestableFile = errors.New("undigestable file") + +type DigestsCataloger struct { + hashes []crypto.Hash +} + +func NewDigestsCataloger(hashes []crypto.Hash) (*DigestsCataloger, error) { + return &DigestsCataloger{ + hashes: hashes, + }, nil +} + +func (i *DigestsCataloger) Catalog(resolver source.FileResolver) (map[source.Coordinates][]Digest, error) { + results := make(map[source.Coordinates][]Digest) + locations := allRegularFiles(resolver) + stage, prog := digestsCatalogingProgress(int64(len(locations))) + for _, location := range locations { + stage.Current = location.RealPath + result, err := i.catalogLocation(resolver, location) + + if errors.Is(err, errUndigestableFile) { + continue + } + + if internal.IsErrPathPermission(err) { + log.Debugf("file digests cataloger skipping %q: %+v", location.RealPath, err) + continue + } + + if err != nil { + return nil, err + } + prog.N++ + results[location.Coordinates] = result + } + log.Debugf("file digests cataloger processed %d files", prog.N) + prog.SetCompleted() + return results, nil +} + +func (i *DigestsCataloger) catalogLocation(resolver source.FileResolver, location source.Location) ([]Digest, error) { + meta, err := resolver.FileMetadataByLocation(location) + if err != nil { + return nil, err + } + + // we should only attempt to report digests for files that are regular files (don't attempt to resolve links) + if meta.Type != source.RegularFile { + return nil, errUndigestableFile + } + + contentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + return nil, err + } + defer internal.CloseAndLogError(contentReader, location.VirtualPath) + + digests, err := DigestsFromFile(contentReader, i.hashes) + if err != nil { + return nil, internal.ErrPath{Context: "digests-cataloger", Path: location.RealPath, Err: err} + } + + return digests, nil +} + +func DigestsFromFile(closer io.ReadCloser, hashes []crypto.Hash) ([]Digest, error) { + // create a set of hasher objects tied together with a single writer to feed content into + hashers := make([]hash.Hash, len(hashes)) + writers := make([]io.Writer, len(hashes)) + for idx, hashObj := range hashes { + hashers[idx] = hashObj.New() + writers[idx] = hashers[idx] + } + + size, err := io.Copy(io.MultiWriter(writers...), closer) + if err != nil { + return nil, err + } + + if size == 0 { + return make([]Digest, 0), nil + } + + result := make([]Digest, len(hashes)) + // only capture digests when there is content. It is important to do this based on SIZE and not + // FILE TYPE. The reasoning is that it is possible for a tar to be crafted with a header-only + // file type but a body is still allowed. + for idx, hasher := range hashers { + result[idx] = Digest{ + Algorithm: DigestAlgorithmName(hashes[idx]), + Value: fmt.Sprintf("%+x", hasher.Sum(nil)), + } + } + + return result, nil +} + +func DigestAlgorithmName(hash crypto.Hash) string { + return CleanDigestAlgorithmName(hash.String()) +} + +func CleanDigestAlgorithmName(name string) string { + lower := strings.ToLower(name) + return strings.ReplaceAll(lower, "-", "") +} + +func digestsCatalogingProgress(locations int64) (*progress.Stage, *progress.Manual) { + stage := &progress.Stage{} + prog := &progress.Manual{ + Total: locations, + } + + bus.Publish(partybus.Event{ + Type: event.FileDigestsCatalogerStarted, + Value: struct { + progress.Stager + progress.Progressable + }{ + Stager: progress.Stager(stage), + Progressable: prog, + }, + }) + + return stage, prog +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/digest_cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/digest_cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..2779215089d2e5d49a65f11067a376fe2a6eb40b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/digest_cataloger_test.go @@ -0,0 +1,169 @@ +package file + +import ( + "crypto" + "fmt" + "github.com/stretchr/testify/require" + "io/ioutil" + "os" + "path/filepath" + "testing" + + "github.com/anchore/stereoscope/pkg/file" + + "github.com/anchore/stereoscope/pkg/imagetest" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/source" +) + +func testDigests(t testing.TB, root string, files []string, hashes ...crypto.Hash) map[source.Coordinates][]Digest { + digests := make(map[source.Coordinates][]Digest) + + for _, f := range files { + fh, err := os.Open(filepath.Join(root, f)) + if err != nil { + t.Fatalf("could not open %q : %+v", f, err) + } + b, err := ioutil.ReadAll(fh) + if err != nil { + t.Fatalf("could not read %q : %+v", f, err) + } + + if len(b) == 0 { + // we don't keep digests for empty files + digests[source.NewLocation(f).Coordinates] = []Digest{} + continue + } + + for _, hash := range hashes { + h := hash.New() + h.Write(b) + digests[source.NewLocation(f).Coordinates] = append(digests[source.NewLocation(f).Coordinates], Digest{ + Algorithm: CleanDigestAlgorithmName(hash.String()), + Value: fmt.Sprintf("%x", h.Sum(nil)), + }) + } + } + + return digests +} + +func TestDigestsCataloger(t *testing.T) { + + tests := []struct { + name string + digests []crypto.Hash + files []string + expected map[source.Coordinates][]Digest + }{ + { + name: "md5", + digests: []crypto.Hash{crypto.MD5}, + files: []string{"test-fixtures/last/empty/empty", "test-fixtures/last/path.txt"}, + expected: testDigests(t, "test-fixtures/last", []string{"empty/empty", "path.txt"}, crypto.MD5), + }, + { + name: "md5-sha1-sha256", + digests: []crypto.Hash{crypto.MD5, crypto.SHA1, crypto.SHA256}, + files: []string{"test-fixtures/last/empty/empty", "test-fixtures/last/path.txt"}, + expected: testDigests(t, "test-fixtures/last", []string{"empty/empty", "path.txt"}, crypto.MD5, crypto.SHA1, crypto.SHA256), + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + c, err := NewDigestsCataloger(test.digests) + require.NoError(t, err) + + src, err := source.NewFromDirectory("test-fixtures/last/") + require.NoError(t, err) + + resolver, err := src.FileResolver(source.SquashedScope) + require.NoError(t, err) + + actual, err := c.Catalog(resolver) + require.NoError(t, err) + + assert.Equal(t, test.expected, actual, "mismatched digests") + }) + } +} + +func TestDigestsCataloger_MixFileTypes(t *testing.T) { + testImage := "image-file-type-mix" + + if *updateImageGoldenFiles { + imagetest.UpdateGoldenFixtureImage(t, testImage) + } + + img := imagetest.GetGoldenFixtureImage(t, testImage) + + src, err := source.NewFromImage(img, "---") + if err != nil { + t.Fatalf("could not create source: %+v", err) + } + + resolver, err := src.FileResolver(source.SquashedScope) + if err != nil { + t.Fatalf("could not create resolver: %+v", err) + } + + tests := []struct { + path string + expected string + }{ + { + path: "/file-1.txt", + expected: "888c139e550867814eb7c33b84d76e4d", + }, + { + path: "/hardlink-1", + }, + { + path: "/symlink-1", + }, + { + path: "/char-device-1", + }, + { + path: "/block-device-1", + }, + { + path: "/fifo-1", + }, + { + path: "/bin", + }, + } + + for _, test := range tests { + t.Run(test.path, func(t *testing.T) { + c, err := NewDigestsCataloger([]crypto.Hash{crypto.MD5}) + if err != nil { + t.Fatalf("unable to get cataloger: %+v", err) + } + + actual, err := c.Catalog(resolver) + if err != nil { + t.Fatalf("could not catalog: %+v", err) + } + + _, ref, err := img.SquashedTree().File(file.Path(test.path)) + if err != nil { + t.Fatalf("unable to get file=%q : %+v", test.path, err) + } + l := source.NewLocationFromImage(test.path, *ref, img) + + if len(actual[l.Coordinates]) == 0 { + if test.expected != "" { + t.Fatalf("no digest found, but expected one") + } + + } else { + assert.Equal(t, actual[l.Coordinates][0].Value, test.expected, "mismatched digests") + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/generate_search_patterns.go b/ci/tools/openeuler-purl/syft-dev/syft/file/generate_search_patterns.go new file mode 100644 index 0000000000000000000000000000000000000000..5e2c074dc356b891d1cf5c80d665e2f58725ddfd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/generate_search_patterns.go @@ -0,0 +1,56 @@ +package file + +import ( + "fmt" + "regexp" + + "github.com/bmatcuk/doublestar/v4" + "github.com/hashicorp/go-multierror" +) + +// GenerateSearchPatterns takes a set of named base patterns, a set of additional named patterns and an name exclusion list and generates a final +// set of regular expressions (indexed by name). The sets are aggregated roughly as such: (base - excluded) + additional. +func GenerateSearchPatterns(basePatterns map[string]string, additionalPatterns map[string]string, excludePatternNames []string) (map[string]*regexp.Regexp, error) { + var regexObjs = make(map[string]*regexp.Regexp) + var errs error + + addFn := func(name, pattern string) { + // always enable multiline search option for extracting secrets with multiline values + obj, err := regexp.Compile(`(?m)` + pattern) + if err != nil { + errs = multierror.Append(errs, fmt.Errorf("unable to parse %q regular expression: %w", name, err)) + } + regexObjs[name] = obj + } + + // add all base cases... unless that base case was asked to be excluded + for name, pattern := range basePatterns { + if !matchesExclusion(excludePatternNames, name) { + addFn(name, pattern) + } + } + + // add all additional cases + for name, pattern := range additionalPatterns { + addFn(name, pattern) + } + + if errs != nil { + return nil, errs + } + + return regexObjs, nil +} + +func matchesExclusion(excludePatternNames []string, name string) bool { + for _, exclude := range excludePatternNames { + matches, err := doublestar.Match(exclude, name) + if err != nil { + return false + } + if matches { + return true + } + } + return false +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/generate_search_patterns_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/generate_search_patterns_test.go new file mode 100644 index 0000000000000000000000000000000000000000..bdd6d422bdfacd2c324bfd4721da54ff17e0cef3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/generate_search_patterns_test.go @@ -0,0 +1,125 @@ +package file + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestGenerateSearchPatterns(t *testing.T) { + tests := []struct { + name string + base map[string]string + additional map[string]string + exclude []string + expected map[string]string + }{ + { + name: "use-base-set", + base: map[string]string{ + "in-default": `^secret_key=.*`, + }, + expected: map[string]string{ + "in-default": `(?m)^secret_key=.*`, + }, + }, + { + name: "exclude-from-base-set", + base: map[string]string{ + "in-default": `^secret_key=.*`, + "also-in-default": `^also-in-default=.*`, + }, + exclude: []string{"also-in-default"}, + expected: map[string]string{ + "in-default": `(?m)^secret_key=.*`, + }, + }, + { + name: "exclude-multiple-from-base-set", + base: map[string]string{ + "in-default": `^secret_key=.*`, + "also-in-default": `^also-in-default=.*`, + "furthermore-in-default": `^furthermore-in-default=.*`, + }, + exclude: []string{"also-in-default", "furthermore-in-default"}, + expected: map[string]string{ + "in-default": `(?m)^secret_key=.*`, + }, + }, + { + name: "exclude-all", + base: map[string]string{ + "in-default": `^secret_key=.*`, + "also-in-default": `^also-in-default=.*`, + }, + exclude: []string{"*"}, + expected: map[string]string{}, + }, + { + name: "exclude-some", + base: map[string]string{ + "real": `^real=.*`, + "in-default": `^secret_key=.*`, + "also-in-default": `^also-in-default=.*`, + }, + exclude: []string{"*-default"}, + expected: map[string]string{ + "real": `(?m)^real=.*`, + }, + }, + { + name: "additional-pattern-unison", + base: map[string]string{ + "in-default": `^secret_key=.*`, + }, + additional: map[string]string{ + "additional": `^additional=.*`, + }, + expected: map[string]string{ + "in-default": `(?m)^secret_key=.*`, + "additional": `(?m)^additional=.*`, + }, + }, + { + name: "override", + base: map[string]string{ + "in-default": `^secret_key=.*`, + }, + additional: map[string]string{ + "in-default": `^additional=.*`, + }, + expected: map[string]string{ + "in-default": `(?m)^additional=.*`, + }, + }, + { + name: "exclude-and-override", + base: map[string]string{ + "in-default": `^secret_key=.*`, + }, + exclude: []string{"in-default"}, + additional: map[string]string{ + "in-default": `^additional=.*`, + }, + expected: map[string]string{ + "in-default": `(?m)^additional=.*`, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actualObj, err := GenerateSearchPatterns(test.base, test.additional, test.exclude) + if err != nil { + t.Fatalf("unable to combine: %+v", err) + } + + actual := make(map[string]string) + for n, v := range actualObj { + actual[n] = v.String() + } + + assert.Equal(t, test.expected, actual, "mismatched combination") + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/metadata_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/file/metadata_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..e9cf28b90ca96a35e2b7af734fe1a4b34c975302 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/metadata_cataloger.go @@ -0,0 +1,59 @@ +package file + +import ( + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/syft/source" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/go-progress" +) + +type MetadataCataloger struct { +} + +func NewMetadataCataloger() *MetadataCataloger { + return &MetadataCataloger{} +} + +func (i *MetadataCataloger) Catalog(resolver source.FileResolver) (map[source.Coordinates]source.FileMetadata, error) { + results := make(map[source.Coordinates]source.FileMetadata) + var locations []source.Location + for location := range resolver.AllLocations() { + locations = append(locations, location) + } + stage, prog := metadataCatalogingProgress(int64(len(locations))) + for _, location := range locations { + stage.Current = location.RealPath + metadata, err := resolver.FileMetadataByLocation(location) + if err != nil { + return nil, err + } + + results[location.Coordinates] = metadata + prog.N++ + } + log.Debugf("file metadata cataloger processed %d files", prog.N) + prog.SetCompleted() + return results, nil +} + +func metadataCatalogingProgress(locations int64) (*progress.Stage, *progress.Manual) { + stage := &progress.Stage{} + prog := &progress.Manual{ + Total: locations, + } + + bus.Publish(partybus.Event{ + Type: event.FileMetadataCatalogerStarted, + Value: struct { + progress.Stager + progress.Progressable + }{ + Stager: progress.Stager(stage), + Progressable: prog, + }, + }) + + return stage, prog +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/metadata_cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/metadata_cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..9ca27a6d014f45b67d4bfb6fa723ba77c430d273 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/metadata_cataloger_test.go @@ -0,0 +1,144 @@ +package file + +import ( + "flag" + "os" + "testing" + + "github.com/anchore/stereoscope/pkg/file" + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" +) + +var updateImageGoldenFiles = flag.Bool("update-image", false, "update the golden fixture images used for testing") + +func TestFileMetadataCataloger(t *testing.T) { + testImage := "image-file-type-mix" + + if *updateImageGoldenFiles { + imagetest.UpdateGoldenFixtureImage(t, testImage) + } + + img := imagetest.GetGoldenFixtureImage(t, testImage) + + c := NewMetadataCataloger() + + src, err := source.NewFromImage(img, "---") + if err != nil { + t.Fatalf("could not create source: %+v", err) + } + + resolver, err := src.FileResolver(source.SquashedScope) + if err != nil { + t.Fatalf("could not create resolver: %+v", err) + } + + actual, err := c.Catalog(resolver) + if err != nil { + t.Fatalf("could not catalog: %+v", err) + } + + tests := []struct { + path string + exists bool + expected source.FileMetadata + err bool + }{ + { + path: "/file-1.txt", + exists: true, + expected: source.FileMetadata{ + Mode: 0644, + Type: "RegularFile", + UserID: 1, + GroupID: 2, + Size: 7, + MIMEType: "text/plain", + }, + }, + { + path: "/hardlink-1", + exists: true, + expected: source.FileMetadata{ + Mode: 0644, + Type: "HardLink", + LinkDestination: "file-1.txt", + UserID: 1, + GroupID: 2, + MIMEType: "", + }, + }, + { + path: "/symlink-1", + exists: true, + expected: source.FileMetadata{ + Mode: 0777 | os.ModeSymlink, + Type: "SymbolicLink", + LinkDestination: "file-1.txt", + UserID: 0, + GroupID: 0, + MIMEType: "", + }, + }, + { + path: "/char-device-1", + exists: true, + expected: source.FileMetadata{ + Mode: 0644 | os.ModeDevice | os.ModeCharDevice, + Type: "CharacterDevice", + UserID: 0, + GroupID: 0, + MIMEType: "", + }, + }, + { + path: "/block-device-1", + exists: true, + expected: source.FileMetadata{ + Mode: 0644 | os.ModeDevice, + Type: "BlockDevice", + UserID: 0, + GroupID: 0, + MIMEType: "", + }, + }, + { + path: "/fifo-1", + exists: true, + expected: source.FileMetadata{ + Mode: 0644 | os.ModeNamedPipe, + Type: "FIFONode", + UserID: 0, + GroupID: 0, + MIMEType: "", + }, + }, + { + path: "/bin", + exists: true, + expected: source.FileMetadata{ + Mode: 0755 | os.ModeDir, + Type: "Directory", + UserID: 0, + GroupID: 0, + MIMEType: "", + }, + }, + } + + for _, test := range tests { + t.Run(test.path, func(t *testing.T) { + _, ref, err := img.SquashedTree().File(file.Path(test.path)) + if err != nil { + t.Fatalf("unable to get file: %+v", err) + } + + l := source.NewLocationFromImage(test.path, *ref, img) + + assert.Equal(t, test.expected, actual[l.Coordinates], "mismatched metadata") + + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/newline_counter.go b/ci/tools/openeuler-purl/syft-dev/syft/file/newline_counter.go new file mode 100644 index 0000000000000000000000000000000000000000..fec905523cd52050785746156d442680e4aedd70 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/newline_counter.go @@ -0,0 +1,39 @@ +package file + +import "io" + +type newlineCounter struct { + io.RuneReader + numBytes int64 + newLines []int64 +} + +func (c *newlineCounter) ReadRune() (r rune, size int, err error) { + r, size, err = c.RuneReader.ReadRune() + c.numBytes += int64(size) + if r == '\n' { + c.newLines = append(c.newLines, c.numBytes) + } + return +} + +func (c *newlineCounter) newlinesBefore(pos int64) int { + var result int + for _, nlPos := range c.newLines { + if nlPos <= pos { + result++ + } + } + return result +} + +func (c *newlineCounter) newlinePositionBefore(pos int64) int64 { + var last int64 + for _, nlPos := range c.newLines { + if nlPos > pos { + break + } + last = nlPos + } + return last +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/newline_counter_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/newline_counter_test.go new file mode 100644 index 0000000000000000000000000000000000000000..24282bceb84bf5704adc453651ec4436672910bd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/newline_counter_test.go @@ -0,0 +1,35 @@ +package file + +import ( + "bufio" + "io" + "strings" + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestLineCounter_ReadRune(t *testing.T) { + counter := &newlineCounter{RuneReader: bufio.NewReader(strings.NewReader("hi\nwhat's the weather like today?\ndunno...\n"))} + var err error + for err == nil { + _, _, err = counter.ReadRune() + } + if err != io.EOF { + t.Fatalf("should have gotten an eof, got %+v", err) + } + assert.Equal(t, 3, len(counter.newLines), "bad line count") + assert.Equal(t, []int64{3, 34, 43}, counter.newLines, "bad line positions") +} + +func TestLineCounter_newlinesBefore(t *testing.T) { + counter := &newlineCounter{RuneReader: bufio.NewReader(strings.NewReader("hi\nwhat's the weather like today?\ndunno...\n"))} + var err error + for err == nil { + _, _, err = counter.ReadRune() + } + if err != io.EOF { + t.Fatalf("should have gotten an eof, got %+v", err) + } + assert.Equal(t, 1, counter.newlinesBefore(10), "bad line count") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/search_result.go b/ci/tools/openeuler-purl/syft-dev/syft/file/search_result.go new file mode 100644 index 0000000000000000000000000000000000000000..dc12d14df20c5b2870338422a2055614d749d7df --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/search_result.go @@ -0,0 +1,18 @@ +package file + +import ( + "fmt" +) + +type SearchResult struct { + Classification string `json:"classification"` + LineNumber int64 `json:"lineNumber"` + LineOffset int64 `json:"lineOffset"` + SeekPosition int64 `json:"seekPosition"` + Length int64 `json:"length"` + Value string `json:"value,omitempty"` +} + +func (s SearchResult) String() string { + return fmt.Sprintf("SearchResult(classification=%q seek=%q length=%q)", s.Classification, s.SeekPosition, s.Length) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..b8f31980ea9955233d076b890b3395fa6837fa3e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_cataloger.go @@ -0,0 +1,158 @@ +package file + +import ( + "bytes" + "fmt" + "io" + "io/ioutil" + "regexp" + "sort" + + "github.com/anchore/syft/internal" + + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/syft/source" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/go-progress" +) + +var DefaultSecretsPatterns = map[string]string{ + "aws-access-key": `(?i)aws_access_key_id["'=:\s]*?(?P(A3T[A-Z0-9]|AKIA|AGPA|AIDA|AROA|AIPA|ANPA|ANVA|ASIA)[A-Z0-9]{16})`, + "aws-secret-key": `(?i)aws_secret_access_key["'=:\s]*?(?P[0-9a-zA-Z/+]{40})`, + "pem-private-key": `-----BEGIN (\S+ )?PRIVATE KEY(\sBLOCK)?-----((?P(\n.*?)+)-----END (\S+ )?PRIVATE KEY(\sBLOCK)?-----)?`, + "docker-config-auth": `"auths"((.*\n)*.*?"auth"\s*:\s*"(?P[^"]+)")?`, + "generic-api-key": `(?i)api(-|_)?key["'=:\s]*?(?P[A-Z0-9]{20,60})["']?(\s|$)`, +} + +type SecretsCataloger struct { + patterns map[string]*regexp.Regexp + revealValues bool + skipFilesAboveSize int64 +} + +func NewSecretsCataloger(patterns map[string]*regexp.Regexp, revealValues bool, maxFileSize int64) (*SecretsCataloger, error) { + return &SecretsCataloger{ + patterns: patterns, + revealValues: revealValues, + skipFilesAboveSize: maxFileSize, + }, nil +} + +func (i *SecretsCataloger) Catalog(resolver source.FileResolver) (map[source.Coordinates][]SearchResult, error) { + results := make(map[source.Coordinates][]SearchResult) + locations := allRegularFiles(resolver) + stage, prog, secretsDiscovered := secretsCatalogingProgress(int64(len(locations))) + for _, location := range locations { + stage.Current = location.RealPath + result, err := i.catalogLocation(resolver, location) + if internal.IsErrPathPermission(err) { + log.Debugf("secrets cataloger skipping - %+v", err) + continue + } + + if err != nil { + return nil, err + } + if len(result) > 0 { + secretsDiscovered.N += int64(len(result)) + results[location.Coordinates] = result + } + prog.N++ + } + log.Debugf("secrets cataloger discovered %d secrets", secretsDiscovered.N) + prog.SetCompleted() + return results, nil +} + +func (i *SecretsCataloger) catalogLocation(resolver source.FileResolver, location source.Location) ([]SearchResult, error) { + metadata, err := resolver.FileMetadataByLocation(location) + if err != nil { + return nil, err + } + + if metadata.Size == 0 { + return nil, nil + } + + if i.skipFilesAboveSize > 0 && metadata.Size > i.skipFilesAboveSize { + return nil, nil + } + + // TODO: in the future we can swap out search strategies here + secrets, err := catalogLocationByLine(resolver, location, i.patterns) + if err != nil { + return nil, internal.ErrPath{Context: "secrets-cataloger", Path: location.RealPath, Err: err} + } + + if i.revealValues { + for idx, secret := range secrets { + value, err := extractValue(resolver, location, secret.SeekPosition, secret.Length) + if err != nil { + return nil, err + } + secrets[idx].Value = value + } + } + + // sort by the start location of each secret as it appears in the location + sort.SliceStable(secrets, func(i, j int) bool { + return secrets[i].SeekPosition < secrets[j].SeekPosition + }) + + return secrets, nil +} + +func extractValue(resolver source.FileResolver, location source.Location, start, length int64) (string, error) { + readCloser, err := resolver.FileContentsByLocation(location) + if err != nil { + return "", fmt.Errorf("unable to fetch reader for location=%q : %w", location, err) + } + defer internal.CloseAndLogError(readCloser, location.VirtualPath) + + n, err := io.CopyN(ioutil.Discard, readCloser, start) + if err != nil { + return "", fmt.Errorf("unable to read contents for location=%q : %w", location, err) + } + if n != start { + return "", fmt.Errorf("unexpected seek location for location=%q : %d != %d", location, n, start) + } + + var buf bytes.Buffer + n, err = io.CopyN(&buf, readCloser, length) + if err != nil { + return "", fmt.Errorf("unable to read secret value for location=%q : %w", location, err) + } + if n != length { + return "", fmt.Errorf("unexpected secret length for location=%q : %d != %d", location, n, length) + } + + return buf.String(), nil +} + +type SecretsMonitor struct { + progress.Stager + SecretsDiscovered progress.Monitorable + progress.Progressable +} + +func secretsCatalogingProgress(locations int64) (*progress.Stage, *progress.Manual, *progress.Manual) { + stage := &progress.Stage{} + secretsDiscovered := &progress.Manual{} + prog := &progress.Manual{ + Total: locations, + } + + bus.Publish(partybus.Event{ + Type: event.SecretsCatalogerStarted, + Source: secretsDiscovered, + Value: SecretsMonitor{ + Stager: progress.Stager(stage), + SecretsDiscovered: secretsDiscovered, + Progressable: prog, + }, + }) + + return stage, prog, secretsDiscovered +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..696f3865c8756b05256dd80bae8a1ceaa5361646 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_cataloger_test.go @@ -0,0 +1,444 @@ +package file + +import ( + "regexp" + "testing" + + "github.com/anchore/syft/internal/file" + + "github.com/anchore/syft/syft/source" + + "github.com/stretchr/testify/assert" +) + +func TestSecretsCataloger(t *testing.T) { + tests := []struct { + name string + fixture string + reveal bool + maxSize int64 + patterns map[string]string + expected []SearchResult + constructorErr bool + catalogErr bool + }{ + { + name: "go-case-find-and-reveal", + fixture: "test-fixtures/secrets/simple.txt", + reveal: true, + patterns: map[string]string{ + "simple-secret-key": `^secret_key=.*`, + }, + expected: []SearchResult{ + { + Classification: "simple-secret-key", + LineNumber: 2, + LineOffset: 0, + SeekPosition: 34, + Length: 21, + Value: "secret_key=clear_text", + }, + }, + }, + { + name: "dont-reveal-secret-value", + fixture: "test-fixtures/secrets/simple.txt", + reveal: false, + patterns: map[string]string{ + "simple-secret-key": `^secret_key=.*`, + }, + expected: []SearchResult{ + { + Classification: "simple-secret-key", + LineNumber: 2, + LineOffset: 0, + SeekPosition: 34, + Length: 21, + Value: "", + }, + }, + }, + { + name: "reveal-named-capture-group", + fixture: "test-fixtures/secrets/simple.txt", + reveal: true, + patterns: map[string]string{ + "simple-secret-key": `^secret_key=(?P.*)`, + }, + expected: []SearchResult{ + { + Classification: "simple-secret-key", + LineNumber: 2, + LineOffset: 11, + SeekPosition: 45, + Length: 10, + Value: "clear_text", + }, + }, + }, + { + name: "multiple-secret-instances", + fixture: "test-fixtures/secrets/multiple.txt", + reveal: true, + patterns: map[string]string{ + "simple-secret-key": `secret_key=.*`, + }, + expected: []SearchResult{ + { + Classification: "simple-secret-key", + LineNumber: 1, + LineOffset: 0, + SeekPosition: 0, + Length: 22, + Value: "secret_key=clear_text1", + }, + { + Classification: "simple-secret-key", + LineNumber: 3, + LineOffset: 0, + SeekPosition: 57, + Length: 22, + Value: "secret_key=clear_text2", + }, + { + Classification: "simple-secret-key", + LineNumber: 4, + // note: this test captures a line offset case + LineOffset: 1, + SeekPosition: 81, + Length: 22, + Value: "secret_key=clear_text3", + }, + { + Classification: "simple-secret-key", + LineNumber: 6, + LineOffset: 0, + SeekPosition: 139, + Length: 22, + Value: "secret_key=clear_text4", + }, + }, + }, + { + name: "multiple-secret-instances-with-capture-group", + fixture: "test-fixtures/secrets/multiple.txt", + reveal: true, + patterns: map[string]string{ + "simple-secret-key": `secret_key=(?P.*)`, + }, + expected: []SearchResult{ + { + Classification: "simple-secret-key", + LineNumber: 1, + // note: value capture group location + LineOffset: 11, + SeekPosition: 11, + Length: 11, + Value: "clear_text1", + }, + { + Classification: "simple-secret-key", + LineNumber: 3, + LineOffset: 11, + SeekPosition: 68, + Length: 11, + Value: "clear_text2", + }, + { + Classification: "simple-secret-key", + LineNumber: 4, + // note: value capture group location + offset + LineOffset: 12, + SeekPosition: 92, + Length: 11, + Value: "clear_text3", + }, + { + Classification: "simple-secret-key", + LineNumber: 6, + LineOffset: 11, + SeekPosition: 150, + Length: 11, + Value: "clear_text4", + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + regexObjs := make(map[string]*regexp.Regexp) + for name, pattern := range test.patterns { + // always assume given patterns should be multiline + obj, err := regexp.Compile(`` + pattern) + if err != nil { + t.Fatalf("unable to parse regex: %+v", err) + } + regexObjs[name] = obj + } + + c, err := NewSecretsCataloger(regexObjs, test.reveal, test.maxSize) + if err != nil && !test.constructorErr { + t.Fatalf("could not create cataloger (but should have been able to): %+v", err) + } else if err == nil && test.constructorErr { + t.Fatalf("expected constructor error but did not get one") + } else if test.constructorErr && err != nil { + return + } + + resolver := source.NewMockResolverForPaths(test.fixture) + + actualResults, err := c.Catalog(resolver) + if err != nil && !test.catalogErr { + t.Fatalf("could not catalog (but should have been able to): %+v", err) + } else if err == nil && test.catalogErr { + t.Fatalf("expected catalog error but did not get one") + } else if test.catalogErr && err != nil { + return + } + + loc := source.NewLocation(test.fixture) + if _, exists := actualResults[loc.Coordinates]; !exists { + t.Fatalf("could not find location=%q in results", loc) + } + + assert.Equal(t, test.expected, actualResults[loc.Coordinates], "mismatched secrets") + }) + } +} + +func TestSecretsCataloger_DefaultSecrets(t *testing.T) { + regexObjs, err := GenerateSearchPatterns(DefaultSecretsPatterns, nil, nil) + if err != nil { + t.Fatalf("unable to get patterns: %+v", err) + } + + tests := []struct { + fixture string + expected []SearchResult + }{ + { + fixture: "test-fixtures/secrets/default/aws.env", + expected: []SearchResult{ + { + Classification: "aws-access-key", + LineNumber: 2, + LineOffset: 25, + SeekPosition: 64, + Length: 20, + Value: "AKIAIOSFODNN7EXAMPLE", + }, + { + Classification: "aws-secret-key", + LineNumber: 3, + LineOffset: 29, + SeekPosition: 114, + Length: 40, + Value: "wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY", + }, + }, + }, + { + fixture: "test-fixtures/secrets/default/aws.ini", + expected: []SearchResult{ + { + Classification: "aws-access-key", + LineNumber: 3, + LineOffset: 18, + SeekPosition: 67, + Length: 20, + Value: "AKIAIOSFODNN7EXAMPLE", + }, + { + Classification: "aws-secret-key", + LineNumber: 4, + LineOffset: 22, + SeekPosition: 110, + Length: 40, + Value: "wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY", + }, + }, + }, + { + fixture: "test-fixtures/secrets/default/private-key.pem", + expected: []SearchResult{ + { + Classification: "pem-private-key", + LineNumber: 2, + LineOffset: 27, + SeekPosition: 66, + Length: 351, + Value: ` +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDBj08sp5++4anG +cmQxJjAkBgNVBAoTHVByb2dyZXNzIFNvZnR3YXJlIENvcnBvcmF0aW9uMSAwHgYD +VQQDDBcqLmF3cy10ZXN0LnByb2dyZXNzLmNvbTCCASIwDQYJKoZIhvcNAQEBBQAD +bml6YXRpb252YWxzaGEyZzIuY3JsMIGgBggrBgEFBQcBAQSBkzCBkDBNBggrBgEF +BQcwAoZBaHR0cDovL3NlY3VyZS5nbG9iYWxzaWduLmNvbS9jYWNlcnQvZ3Nvcmdh +z3P668YfhUbKdRF6S42Cg6zn +`, + }, + }, + }, + { + fixture: "test-fixtures/secrets/default/private-key-openssl.pem", + expected: []SearchResult{ + { + Classification: "pem-private-key", + LineNumber: 2, + LineOffset: 35, + SeekPosition: 74, + Length: 351, + Value: ` +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDBj08sp5++4anG +cmQxJjAkBgNVBAoTHVByb2dyZXNzIFNvZnR3YXJlIENvcnBvcmF0aW9uMSAwHgYD +VQQDDBcqLmF3cy10ZXN0LnByb2dyZXNzLmNvbTCCASIwDQYJKoZIhvcNAQEBBQAD +bml6YXRpb252YWxzaGEyZzIuY3JsMIGgBggrBgEFBQcBAQSBkzCBkDBNBggrBgEF +BQcwAoZBaHR0cDovL3NlY3VyZS5nbG9iYWxzaWduLmNvbS9jYWNlcnQvZ3Nvcmdh +z3P668YfhUbKdRF6S42Cg6zn +`, + }, + }, + }, + { + // note: this test proves that the PEM regex matches the smallest possible match + // since the test catches two adjacent secrets + fixture: "test-fixtures/secrets/default/private-keys.pem", + expected: []SearchResult{ + { + Classification: "pem-private-key", + LineNumber: 1, + LineOffset: 35, + SeekPosition: 35, + Length: 351, + Value: ` +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDBj08sp5++4anG +cmQxJjAkBgNVBAoTHVByb2dyZXNzIFNvZnR3YXJlIENvcnBvcmF0aW9uMSAwHgYD +VQQDDBcqLmF3cy10ZXN0LnByb2dyZXNzLmNvbTCCASIwDQYJKoZIhvcNAQEBBQAD +bml6YXRpb252YWxzaGEyZzIuY3JsMIGgBggrBgEFBQcBAQSBkzCBkDBNBggrBgEF +BQcwAoZBaHR0cDovL3NlY3VyZS5nbG9iYWxzaWduLmNvbS9jYWNlcnQvZ3Nvcmdh +z3P668YfhUbKdRF6S42Cg6zn +`, + }, + { + Classification: "pem-private-key", + LineNumber: 9, + LineOffset: 35, + SeekPosition: 455, + Length: 351, + Value: ` +MIIEvgTHISISNOTAREALKEYoIBAQDBj08DBj08DBj08DBj08DBj08DBsp5++4an3 +cmQxJjAkBgNVBAoTHVByb2dyZXNzIFNvZnR3YXJlIENvcnBvcmF0aW9uMSAwHgY5 +VQQDDBcqLmF3cy10ZXN0SISNOTAREALKEYoIBAQDBj08DfffKoZIhvcNAQEBBQA7 +bml6SISNOTAREALKEYoIBAQDBj08DdssBggrBgEFBQcBAQSBkzCBkDBNBggrBgE8 +BQcwAoZBaHR0cDovL3NlY3VyZS5nbG9iYWxzaWduLmNvbS9jYWNlcnQvZ3Nvcmd1 +j4f668YfhUbKdRF6S6734856 +`, + }, + }, + }, + { + fixture: "test-fixtures/secrets/default/private-key-false-positive.pem", + expected: nil, + }, + { + // this test represents: + // 1. a docker config + // 2. a named capture group with the correct line number and line offset case + // 3. the named capture group is in a different line than the match start, and both the match start and the capture group have different line offsets + fixture: "test-fixtures/secrets/default/docker-config.json", + expected: []SearchResult{ + { + Classification: "docker-config-auth", + LineNumber: 5, + LineOffset: 15, + SeekPosition: 100, + Length: 10, + Value: "tOpsyKreTz", + }, + }, + }, + { + fixture: "test-fixtures/secrets/default/not-docker-config.json", + expected: nil, + }, + { + fixture: "test-fixtures/secrets/default/api-key.txt", + expected: []SearchResult{ + { + Classification: "generic-api-key", + LineNumber: 2, + LineOffset: 7, + SeekPosition: 33, + Length: 20, + Value: "12345A7a901b34567890", + }, + { + Classification: "generic-api-key", + LineNumber: 3, + LineOffset: 9, + SeekPosition: 63, + Length: 30, + Value: "12345A7a901b345678901234567890", + }, + { + Classification: "generic-api-key", + LineNumber: 4, + LineOffset: 10, + SeekPosition: 104, + Length: 40, + Value: "12345A7a901b3456789012345678901234567890", + }, + { + Classification: "generic-api-key", + LineNumber: 5, + LineOffset: 10, + SeekPosition: 156, + Length: 50, + Value: "12345A7a901b34567890123456789012345678901234567890", + }, + { + Classification: "generic-api-key", + LineNumber: 6, + LineOffset: 16, + SeekPosition: 224, + Length: 60, + Value: "12345A7a901b345678901234567890123456789012345678901234567890", + }, + { + Classification: "generic-api-key", + LineNumber: 14, + LineOffset: 8, + SeekPosition: 502, + Length: 20, + Value: "11111111111111111111", + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + + c, err := NewSecretsCataloger(regexObjs, true, 10*file.MB) + if err != nil { + t.Fatalf("could not create cataloger: %+v", err) + } + + resolver := source.NewMockResolverForPaths(test.fixture) + + actualResults, err := c.Catalog(resolver) + if err != nil { + t.Fatalf("could not catalog: %+v", err) + } + + loc := source.NewLocation(test.fixture) + if _, exists := actualResults[loc.Coordinates]; !exists && test.expected != nil { + t.Fatalf("could not find location=%q in results", loc) + } else if !exists && test.expected == nil { + return + } + + assert.Equal(t, test.expected, actualResults[loc.Coordinates], "mismatched secrets") + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_search_by_line_strategy.go b/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_search_by_line_strategy.go new file mode 100644 index 0000000000000000000000000000000000000000..0fd87ff63c77e8e24dd96dc93ae958ce510d72b1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/secrets_search_by_line_strategy.go @@ -0,0 +1,137 @@ +package file + +import ( + "bufio" + "errors" + "fmt" + "io" + "io/ioutil" + "regexp" + + "github.com/anchore/syft/internal" + + "github.com/anchore/syft/syft/source" +) + +func catalogLocationByLine(resolver source.FileResolver, location source.Location, patterns map[string]*regexp.Regexp) ([]SearchResult, error) { + readCloser, err := resolver.FileContentsByLocation(location) + if err != nil { + return nil, fmt.Errorf("unable to fetch reader for location=%q : %w", location, err) + } + defer internal.CloseAndLogError(readCloser, location.VirtualPath) + + var scanner = bufio.NewReader(readCloser) + var position int64 + var allSecrets []SearchResult + var lineNo int64 + var readErr error + for !errors.Is(readErr, io.EOF) { + lineNo++ + var line []byte + // TODO: we're at risk of large memory usage for very long lines + line, readErr = scanner.ReadBytes('\n') + if readErr != nil && readErr != io.EOF { + return nil, readErr + } + + lineSecrets, err := searchForSecretsWithinLine(resolver, location, patterns, line, lineNo, position) + if err != nil { + return nil, err + } + position += int64(len(line)) + allSecrets = append(allSecrets, lineSecrets...) + } + + return allSecrets, nil +} + +func searchForSecretsWithinLine(resolver source.FileResolver, location source.Location, patterns map[string]*regexp.Regexp, line []byte, lineNo int64, position int64) ([]SearchResult, error) { + var secrets []SearchResult + for name, pattern := range patterns { + matches := pattern.FindAllIndex(line, -1) + for i, match := range matches { + if i%2 == 1 { + // FindAllIndex returns pairs of numbers for each match, we are only interested in the starting (first) + // position in each pair. + continue + } + + lineOffset := int64(match[0]) + seekLocation := position + lineOffset + reader, err := readerAtPosition(resolver, location, seekLocation) + if err != nil { + return nil, err + } + + secret := extractSecretFromPosition(reader, name, pattern, lineNo, lineOffset, seekLocation) + if secret != nil { + secrets = append(secrets, *secret) + } + internal.CloseAndLogError(reader, location.VirtualPath) + } + } + + return secrets, nil +} + +func readerAtPosition(resolver source.FileResolver, location source.Location, seekPosition int64) (io.ReadCloser, error) { + readCloser, err := resolver.FileContentsByLocation(location) + if err != nil { + return nil, fmt.Errorf("unable to fetch reader for location=%q : %w", location, err) + } + if seekPosition > 0 { + n, err := io.CopyN(ioutil.Discard, readCloser, seekPosition) + if err != nil { + return nil, fmt.Errorf("unable to read contents for location=%q while searching for secrets: %w", location, err) + } + if n != seekPosition { + return nil, fmt.Errorf("unexpected seek location for location=%q while searching for secrets: %d != %d", location, n, seekPosition) + } + } + return readCloser, nil +} + +func extractSecretFromPosition(readCloser io.ReadCloser, name string, pattern *regexp.Regexp, lineNo, lineOffset, seekPosition int64) *SearchResult { + reader := &newlineCounter{RuneReader: bufio.NewReader(readCloser)} + positions := pattern.FindReaderSubmatchIndex(reader) + if len(positions) == 0 { + // no matches found + return nil + } + + index := pattern.SubexpIndex("value") + var indexOffset int + if index != -1 { + // there is a capture group, use the capture group selection as the secret value. To do this we want to + // use the position at the discovered offset. Note: all positions come in pairs, so you will need to adjust + // the offset accordingly (multiply by 2). + indexOffset = index * 2 + } + // get the start and stop of the secret value. Note: this covers both when there is a capture group + // and when there is not a capture group (full value match) + start, stop := int64(positions[indexOffset]), int64(positions[indexOffset+1]) + + if start < 0 || stop < 0 { + // no match location found. This can happen when there is a value capture group specified by the user + // and there was a match on the overall regex, but not for the capture group (which is possible if the capture + // group is optional). + return nil + } + + // lineNoOfSecret are the number of lines which occur before the start of the secret value + var lineNoOfSecret = lineNo + int64(reader.newlinesBefore(start)) + // lineOffsetOfSecret are the number of bytes that occur after the last newline but before the secret value. + var lineOffsetOfSecret = start - reader.newlinePositionBefore(start) + if lineNoOfSecret == lineNo { + // the secret value starts in the same line as the overall match, so we must consider that line offset + lineOffsetOfSecret += lineOffset + } + + return &SearchResult{ + Classification: name, + SeekPosition: start + seekPosition, + Length: stop - start, + LineNumber: lineNoOfSecret, + LineOffset: lineOffsetOfSecret, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/a-path.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/a-path.txt new file mode 100644 index 0000000000000000000000000000000000000000..67e9540341af9f83d155bd4a48bfbc7bdede539e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/a-path.txt @@ -0,0 +1 @@ +test-fixtures/a-path.txt file contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/another-path.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/another-path.txt new file mode 100644 index 0000000000000000000000000000000000000000..0d654f8fe86300e10b405eb23cc256f8046204df --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/another-path.txt @@ -0,0 +1 @@ +test-fixtures/another-path.txt file contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/.gitignore b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..7424f9e484746e9223cd7be43d86619a4c686542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/.gitignore @@ -0,0 +1 @@ +!libpython2.7.so \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/busybox b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/busybox new file mode 100644 index 0000000000000000000000000000000000000000..ac2bb305c6359c75b0c18bb8be4839ecd8eec5a7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/busybox @@ -0,0 +1 @@ +another bad binary \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/go b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/go new file mode 100644 index 0000000000000000000000000000000000000000..adbbb757b1d10ef463b175b6a593c5f22fee7ae7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/go @@ -0,0 +1 @@ +a bad go binary \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/libpython2.7.so b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/libpython2.7.so new file mode 100644 index 0000000000000000000000000000000000000000..f9e8d96f452a967611050f32769d1e06daeeebb2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/libpython2.7.so @@ -0,0 +1,3 @@ +# note: this should NOT match + +DO NOT DETECT \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/python2.6 b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/python2.6 new file mode 100644 index 0000000000000000000000000000000000000000..94639f34e0806d40cae33d8b068c8c3e0561110f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/negative/python2.6 @@ -0,0 +1,3 @@ +# note: this should NOT match + +just some noise \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/.gitignore b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..5b1ba3eb408becb7102641dc1a3ec2db4d163c66 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/.gitignore @@ -0,0 +1 @@ +!libpython3.7.so \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/VERSION b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/VERSION new file mode 100644 index 0000000000000000000000000000000000000000..5bedbed9f9570a82248170b5d624cbff670c19f9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/VERSION @@ -0,0 +1 @@ +go1.15-beta2 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/[ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/[ new file mode 100644 index 0000000000000000000000000000000000000000..7829d71b9419736fab184b53621fccdd7ee7bdc4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/[ @@ -0,0 +1,3 @@ +# note: this SHOULD match as busybox 3.33.3 + +noise!BusyBox v3.33.3!noise \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/busybox b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/busybox new file mode 120000 index 0000000000000000000000000000000000000000..c3e3150b864ddadea0eb0f4a1e1ace774944094c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/busybox @@ -0,0 +1 @@ +./[ \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/go b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/go new file mode 100644 index 0000000000000000000000000000000000000000..56c6f3c7a814d6eadbaf07c6e08037c355a600e9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/go @@ -0,0 +1 @@ +go1.14 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/libpython3.7.so b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/libpython3.7.so new file mode 100644 index 0000000000000000000000000000000000000000..aea0d1091124524e0bd9988063c62cd5b3737ce7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/libpython3.7.so @@ -0,0 +1,2 @@ +# note: this SHOULD match as python 3.7 +noise3.7.4a-vZ9!morenoise \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/patchlevel.h b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/patchlevel.h new file mode 100644 index 0000000000000000000000000000000000000000..c4245addd812dd01d088c1991d8927c88404e39c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/patchlevel.h @@ -0,0 +1,7 @@ +# note: this SHOULD match as python 3.9 + +some source code... + +#define PY_VERSION 3.9-aZ5 + +more source! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/python3.6 b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/python3.6 new file mode 100644 index 0000000000000000000000000000000000000000..fecd79a46d9440a07d17655ac7aa79554a42749f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/classifiers/positive/python3.6 @@ -0,0 +1,3 @@ +# note: this SHOULD match as python 3.6 + +noise3.6.3a-vZ9!morenoise \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-busybox/Dockerfile b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-busybox/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..94b54d2f4fe89515eb499392b63c610937788c92 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-busybox/Dockerfile @@ -0,0 +1 @@ +FROM busybox:1.35 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-file-type-mix/Dockerfile b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-file-type-mix/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..c2d61ef4da97878757d9ee4d2874671d99e60473 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-file-type-mix/Dockerfile @@ -0,0 +1,13 @@ +FROM busybox:latest + +ADD file-1.txt . +RUN chmod 644 file-1.txt +RUN chown 1:2 file-1.txt +RUN ln -s file-1.txt symlink-1 +# note: hard links may behave inconsistently, this should be a golden image +RUN ln file-1.txt hardlink-1 +RUN mknod char-device-1 c 89 1 +RUN mknod block-device-1 b 0 1 +RUN mknod fifo-1 p +RUN mkdir /dir +RUN rm -rf home etc/group etc/localtime etc/mtab etc/network etc/passwd etc/shadow var usr bin/* \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-file-type-mix/file-1.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-file-type-mix/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..d86db8155c35d08c4bcbdc95ed008e60fa8c489c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/image-file-type-mix/file-1.txt @@ -0,0 +1 @@ +file 1! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/last/empty/empty b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/last/empty/empty new file mode 100644 index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/last/path.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/last/path.txt new file mode 100644 index 0000000000000000000000000000000000000000..3d4a165ab882b9e058445e56736c64633e13a443 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/last/path.txt @@ -0,0 +1 @@ +test-fixtures/last/path.txt file contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/api-key.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/api-key.txt new file mode 100644 index 0000000000000000000000000000000000000000..63cb62cac9cfdbb6d3011fb7df2660bac7e7922f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/api-key.txt @@ -0,0 +1,14 @@ +# these should be matches +apikey=12345A7a901b34567890 +api_key =12345A7a901b345678901234567890 +API-KEY= '12345A7a901b3456789012345678901234567890' +API-key: "12345A7a901b34567890123456789012345678901234567890" +some_ApI-kEy = "12345A7a901b345678901234567890123456789012345678901234567890" + +# these should be non matches +api_key = "toolong12345A7a901b345678901234567890123456789012345678901234567890" +api_key = "tooshort" +not_api_k3y = "badkeyname12345A7a901b34567890" + +# value at EOF should match +api_key=11111111111111111111 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/aws.env b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/aws.env new file mode 100644 index 0000000000000000000000000000000000000000..7e5888a3801b9f445f4b5315bd911b9160cc2684 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/aws.env @@ -0,0 +1,3 @@ +# note: these are NOT real credentials +export AWS_ACCESS_KEY_ID=AKIAIOSFODNN7EXAMPLE +export AWS_SECRET_ACCESS_KEY=wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/aws.ini b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/aws.ini new file mode 100644 index 0000000000000000000000000000000000000000..0413424f6e0f0205f1b0cf8870f7e84e9cacbc50 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/aws.ini @@ -0,0 +1,4 @@ +# note: these are NOT real credentials +[default] +aws_access_key_id=AKIAIOSFODNN7EXAMPLE +aws_secret_access_key=wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/docker-config.json b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/docker-config.json new file mode 100644 index 0000000000000000000000000000000000000000..2a239cdaa935b3c5c6290ef4b983305fbe36f18f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/docker-config.json @@ -0,0 +1,10 @@ +{ + "experimental" : "disabled", + "auths" : { + "https://index.docker.io/v1/" : { + "auth": "tOpsyKreTz" + } + }, + "stackOrchestrator" : "swarm", + "credsStore" : "desktop" +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/not-docker-config.json b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/not-docker-config.json new file mode 100644 index 0000000000000000000000000000000000000000..c6baa32f103ca71a24020dc5acd297a93c6e1260 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/not-docker-config.json @@ -0,0 +1,4 @@ +{ + "endpoint" : "http://somewhere", + "auth" : "basic" +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key-false-positive.pem b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key-false-positive.pem new file mode 100644 index 0000000000000000000000000000000000000000..2cc142e3cb5e2a108103112fa501d81feaa55334 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key-false-positive.pem @@ -0,0 +1 @@ +-----BEGIN OPENSSL PRIVATE KEY----- \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key-openssl.pem b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key-openssl.pem new file mode 100644 index 0000000000000000000000000000000000000000..48e4d2361cb31acfc24607e48893c7bf410699de --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key-openssl.pem @@ -0,0 +1,9 @@ +# note: this is NOT a real private key +-----BEGIN OPENSSL PRIVATE KEY----- +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDBj08sp5++4anG +cmQxJjAkBgNVBAoTHVByb2dyZXNzIFNvZnR3YXJlIENvcnBvcmF0aW9uMSAwHgYD +VQQDDBcqLmF3cy10ZXN0LnByb2dyZXNzLmNvbTCCASIwDQYJKoZIhvcNAQEBBQAD +bml6YXRpb252YWxzaGEyZzIuY3JsMIGgBggrBgEFBQcBAQSBkzCBkDBNBggrBgEF +BQcwAoZBaHR0cDovL3NlY3VyZS5nbG9iYWxzaWduLmNvbS9jYWNlcnQvZ3Nvcmdh +z3P668YfhUbKdRF6S42Cg6zn +-----END OPENSSL PRIVATE KEY----- \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key.pem b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key.pem new file mode 100644 index 0000000000000000000000000000000000000000..e13aa1955ff2086bdc5e43cca93775c1f9a46f0c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-key.pem @@ -0,0 +1,10 @@ +# note: this is NOT a real private key +-----BEGIN PRIVATE KEY----- +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDBj08sp5++4anG +cmQxJjAkBgNVBAoTHVByb2dyZXNzIFNvZnR3YXJlIENvcnBvcmF0aW9uMSAwHgYD +VQQDDBcqLmF3cy10ZXN0LnByb2dyZXNzLmNvbTCCASIwDQYJKoZIhvcNAQEBBQAD +bml6YXRpb252YWxzaGEyZzIuY3JsMIGgBggrBgEFBQcBAQSBkzCBkDBNBggrBgEF +BQcwAoZBaHR0cDovL3NlY3VyZS5nbG9iYWxzaWduLmNvbS9jYWNlcnQvZ3Nvcmdh +z3P668YfhUbKdRF6S42Cg6zn +-----END PRIVATE KEY----- +other embedded text \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-keys.pem b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-keys.pem new file mode 100644 index 0000000000000000000000000000000000000000..27c0453652b3c6e581375683ee81acdfb260bf76 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/default/private-keys.pem @@ -0,0 +1,16 @@ +-----BEGIN OPENSSL PRIVATE KEY----- +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDBj08sp5++4anG +cmQxJjAkBgNVBAoTHVByb2dyZXNzIFNvZnR3YXJlIENvcnBvcmF0aW9uMSAwHgYD +VQQDDBcqLmF3cy10ZXN0LnByb2dyZXNzLmNvbTCCASIwDQYJKoZIhvcNAQEBBQAD +bml6YXRpb252YWxzaGEyZzIuY3JsMIGgBggrBgEFBQcBAQSBkzCBkDBNBggrBgEF +BQcwAoZBaHR0cDovL3NlY3VyZS5nbG9iYWxzaWduLmNvbS9jYWNlcnQvZ3Nvcmdh +z3P668YfhUbKdRF6S42Cg6zn +-----END OPENSSL PRIVATE KEY----- +-----BEGIN OPENSSL PRIVATE KEY----- +MIIEvgTHISISNOTAREALKEYoIBAQDBj08DBj08DBj08DBj08DBj08DBsp5++4an3 +cmQxJjAkBgNVBAoTHVByb2dyZXNzIFNvZnR3YXJlIENvcnBvcmF0aW9uMSAwHgY5 +VQQDDBcqLmF3cy10ZXN0SISNOTAREALKEYoIBAQDBj08DfffKoZIhvcNAQEBBQA7 +bml6SISNOTAREALKEYoIBAQDBj08DdssBggrBgEFBQcBAQSBkzCBkDBNBggrBgE8 +BQcwAoZBaHR0cDovL3NlY3VyZS5nbG9iYWxzaWduLmNvbS9jYWNlcnQvZ3Nvcmd1 +j4f668YfhUbKdRF6S6734856 +-----END OPENSSL PRIVATE KEY----- \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/multiple.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/multiple.txt new file mode 100644 index 0000000000000000000000000000000000000000..3c50205d16b269aec1afcc57dee4155ccaaf5904 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/multiple.txt @@ -0,0 +1,6 @@ +secret_key=clear_text1 +other text that should be ignored +secret_key=clear_text2 + secret_key=clear_text3 +also things that should be ignored +secret_key=clear_text4 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/simple.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/simple.txt new file mode 100644 index 0000000000000000000000000000000000000000..67fc2b755793acae06ceacc904bf5e9d108f67be --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/secrets/simple.txt @@ -0,0 +1,4 @@ +other text that should be ignored +secret_key=clear_text +---secret_key=clear_text +also things that should be ignored \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/snapshot/stereoscope-fixture-image-file-type-mix.golden b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/snapshot/stereoscope-fixture-image-file-type-mix.golden new file mode 100644 index 0000000000000000000000000000000000000000..e85036214d92338a13d636bbae3906d69d5d2c09 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/snapshot/stereoscope-fixture-image-file-type-mix.golden differ diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/nested/link-root b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/nested/link-root new file mode 120000 index 0000000000000000000000000000000000000000..24659224aae89aa00d59a19886dc31bd1d138627 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/nested/link-root @@ -0,0 +1 @@ +../real-root \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/file1.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/file1.txt new file mode 100644 index 0000000000000000000000000000000000000000..5452844a2006748e4ccd60e6e8d66645eca691ed --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/file1.txt @@ -0,0 +1 @@ +contents! diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/nested/file2.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/nested/file2.txt new file mode 100644 index 0000000000000000000000000000000000000000..5f7e2f21348693e894f060e1990fe8b0903b2e84 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/nested/file2.txt @@ -0,0 +1 @@ +more contents! diff --git a/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/nested/linked-file1.txt b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/nested/linked-file1.txt new file mode 120000 index 0000000000000000000000000000000000000000..4e7feb2d8cbafe940498ec9f6a4b46318167eb24 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/file/test-fixtures/symlinked-root/real-root/nested/linked-file1.txt @@ -0,0 +1 @@ +../file1.txt \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/formats.go b/ci/tools/openeuler-purl/syft-dev/syft/formats.go new file mode 100644 index 0000000000000000000000000000000000000000..f3433a48e019535859a5bb2121a20ee56728178f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/formats.go @@ -0,0 +1,110 @@ +package syft + +import ( + "bytes" + "strings" + + "github.com/anchore/syft/internal/formats/cyclonedxjson" + "github.com/anchore/syft/internal/formats/cyclonedxxml" + "github.com/anchore/syft/internal/formats/github" + "github.com/anchore/syft/internal/formats/spdx22json" + "github.com/anchore/syft/internal/formats/spdx22tagvalue" + "github.com/anchore/syft/internal/formats/syftjson" + "github.com/anchore/syft/internal/formats/table" + "github.com/anchore/syft/internal/formats/template" + "github.com/anchore/syft/internal/formats/text" + "github.com/anchore/syft/syft/sbom" +) + +// these have been exported for the benefit of API users +const ( + JSONFormatID = syftjson.ID + TextFormatID = text.ID + TableFormatID = table.ID + CycloneDxXMLFormatID = cyclonedxxml.ID + CycloneDxJSONFormatID = cyclonedxjson.ID + GitHubID = github.ID + SPDXTagValueFormatID = spdx22tagvalue.ID + SPDXJSONFormatID = spdx22json.ID + TemplateFormatID = template.ID +) + +var formats []sbom.Format + +func init() { + formats = []sbom.Format{ + syftjson.Format(), + cyclonedxxml.Format(), + cyclonedxjson.Format(), + github.Format(), + spdx22tagvalue.Format(), + spdx22json.Format(), + table.Format(), + text.Format(), + template.Format(), + } +} + +func FormatIDs() (ids []sbom.FormatID) { + for _, f := range formats { + ids = append(ids, f.ID()) + } + return ids +} + +func FormatByID(id sbom.FormatID) sbom.Format { + for _, f := range formats { + if f.ID() == id { + return f + } + } + return nil +} + +func FormatByName(name string) sbom.Format { + cleanName := cleanFormatName(name) + for _, f := range formats { + if cleanFormatName(string(f.ID())) == cleanName { + return f + } + } + + // handle any aliases for any supported format + switch cleanName { + case "json", "syftjson": + return FormatByID(syftjson.ID) + case "cyclonedx", "cyclone", "cyclonedxxml": + return FormatByID(cyclonedxxml.ID) + case "cyclonedxjson": + return FormatByID(cyclonedxjson.ID) + case "github", "githubjson": + return FormatByID(github.ID) + case "spdx", "spdxtv", "spdxtagvalue": + return FormatByID(spdx22tagvalue.ID) + case "spdxjson": + return FormatByID(spdx22json.ID) + case "table": + return FormatByID(table.ID) + case "text": + return FormatByID(text.ID) + case "template": + FormatByID(template.ID) + } + + return nil +} + +func cleanFormatName(name string) string { + r := strings.NewReplacer("-", "", "_", "") + return strings.ToLower(r.Replace(name)) +} + +func IdentifyFormat(by []byte) sbom.Format { + for _, f := range formats { + if err := f.Validate(bytes.NewReader(by)); err != nil { + continue + } + return f + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/formats_test.go b/ci/tools/openeuler-purl/syft-dev/syft/formats_test.go new file mode 100644 index 0000000000000000000000000000000000000000..9596abd6ba5c890953cb7c85b8e28304aa3cb515 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/formats_test.go @@ -0,0 +1,202 @@ +package syft + +import ( + "bytes" + "io" + "os" + "testing" + + "github.com/anchore/syft/internal/formats/cyclonedxjson" + "github.com/anchore/syft/internal/formats/cyclonedxxml" + "github.com/anchore/syft/internal/formats/github" + "github.com/anchore/syft/internal/formats/spdx22json" + "github.com/anchore/syft/internal/formats/spdx22tagvalue" + "github.com/anchore/syft/internal/formats/syftjson" + "github.com/anchore/syft/internal/formats/table" + "github.com/anchore/syft/internal/formats/template" + "github.com/anchore/syft/internal/formats/text" + "github.com/anchore/syft/syft/sbom" + "github.com/stretchr/testify/require" + + "github.com/stretchr/testify/assert" +) + +func TestIdentify(t *testing.T) { + tests := []struct { + fixture string + expected sbom.FormatID + }{ + { + fixture: "test-fixtures/alpine-syft.json", + expected: syftjson.ID, + }, + } + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + f, err := os.Open(test.fixture) + assert.NoError(t, err) + by, err := io.ReadAll(f) + assert.NoError(t, err) + frmt := IdentifyFormat(by) + assert.NotNil(t, frmt) + assert.Equal(t, test.expected, frmt.ID()) + }) + } +} + +func TestFormats_EmptyInput(t *testing.T) { + for _, format := range formats { + t.Run(format.ID().String(), func(t *testing.T) { + t.Run("format.Decode", func(t *testing.T) { + input := bytes.NewReader(nil) + + assert.NotPanics(t, func() { + decodedSBOM, err := format.Decode(input) + assert.Error(t, err) + assert.Nil(t, decodedSBOM) + }) + }) + + t.Run("format.Validate", func(t *testing.T) { + input := bytes.NewReader(nil) + + assert.NotPanics(t, func() { + err := format.Validate(input) + assert.Error(t, err) + }) + }) + }) + } +} + +func TestFormatByName(t *testing.T) { + + tests := []struct { + name string + want sbom.FormatID + }{ + // SPDX Tag-Value + { + name: "spdx", + want: spdx22tagvalue.ID, + }, + { + name: "spdx-tag-value", + want: spdx22tagvalue.ID, + }, + { + name: "spdx-tv", + want: spdx22tagvalue.ID, + }, + { + name: "spdxtv", // clean variant + want: spdx22tagvalue.ID, + }, + { + name: "spdx-2-tag-value", // clean variant + want: spdx22tagvalue.ID, + }, + { + name: "spdx-2-tagvalue", // clean variant + want: spdx22tagvalue.ID, + }, + { + name: "spdx2-tagvalue", // clean variant + want: spdx22tagvalue.ID, + }, + + // SPDX JSON + { + name: "spdx-json", + want: spdx22json.ID, + }, + { + name: "spdx-2-json", + want: spdx22json.ID, + }, + + // Cyclonedx JSON + { + name: "cyclonedx-json", + want: cyclonedxjson.ID, + }, + { + name: "cyclonedx-1-json", + want: cyclonedxjson.ID, + }, + + // Cyclonedx XML + { + name: "cyclonedx", + want: cyclonedxxml.ID, + }, + { + name: "cyclonedx-xml", + want: cyclonedxxml.ID, + }, + { + name: "cyclonedx-1-xml", + want: cyclonedxxml.ID, + }, + + // Syft Table + { + name: "table", + want: table.ID, + }, + + { + name: "syft-table", + want: table.ID, + }, + + // Syft Text + { + name: "text", + want: text.ID, + }, + + { + name: "syft-text", + want: text.ID, + }, + + // Syft JSON + { + name: "json", + want: syftjson.ID, + }, + + { + name: "syft-json", + want: syftjson.ID, + }, + + // GitHub JSON + { + name: "github", + want: github.ID, + }, + + { + name: "github-json", + want: github.ID, + }, + + { + name: "template", + want: template.ID, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + f := FormatByName(tt.name) + if tt.want == "" { + require.Nil(t, f) + return + } + require.NotNil(t, f) + assert.Equal(t, tt.want, f.ID()) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/lib.go b/ci/tools/openeuler-purl/syft-dev/syft/lib.go new file mode 100644 index 0000000000000000000000000000000000000000..d0a1fdf4d6d3db66ae181b95b21de75e75c04beb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/lib.go @@ -0,0 +1,88 @@ +/* +Package syft is a "one-stop-shop" for helper utilities for all major functionality provided by child packages of the syft library. + +Here is what the main execution path for syft does: + + 1. Parse a user image string to get a stereoscope image.Source object + 2. Invoke all catalogers to catalog the image, adding discovered packages to a single catalog object + 3. Invoke one or more encoders to output contents of the catalog + +A Source object encapsulates the image object to be cataloged and the user options (catalog all layers vs. squashed layer), +providing a way to inspect paths and file content within the image. The Source object, not the image object, is used +throughout the main execution path. This abstraction allows for decoupling of what is cataloged (a docker image, an OCI +image, a filesystem, etc) and how it is cataloged (the individual catalogers). + +Similar to the cataloging process, Linux distribution identification is also performed based on what is discovered within the image. +*/ +package syft + +import ( + "fmt" + + "github.com/anchore/syft/syft/artifact" + + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/logger" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger" + "github.com/anchore/syft/syft/source" + "github.com/wagoodman/go-partybus" +) + +// CatalogPackages takes an inventory of packages from the given image from a particular perspective +// (e.g. squashed source, all-layers source). Returns the discovered set of packages, the identified Linux +// distribution, and the source object used to wrap the data source. +func CatalogPackages(src *source.Source, cfg cataloger.Config) (*pkg.Catalog, []artifact.Relationship, *linux.Release, error) { + resolver, err := src.FileResolver(cfg.Search.Scope) + if err != nil { + return nil, nil, nil, fmt.Errorf("unable to determine resolver while cataloging packages: %w", err) + } + + // find the distro + release := linux.IdentifyRelease(resolver) + if release != nil { + log.Infof("identified distro: %s", release.String()) + } else { + log.Info("could not identify distro") + } + + // if the catalogers have been configured, use them regardless of input type + var catalogers []cataloger.Cataloger + if len(cfg.Catalogers) > 0 { + catalogers = cataloger.AllCatalogers(cfg) + } else { + // otherwise conditionally use the correct set of loggers based on the input type (container image or directory) + switch src.Metadata.Scheme { + case source.ImageScheme: + log.Info("cataloging image") + catalogers = cataloger.ImageCatalogers(cfg) + case source.FileScheme: + log.Info("cataloging file") + catalogers = cataloger.AllCatalogers(cfg) + case source.DirectoryScheme: + log.Info("cataloging directory") + catalogers = cataloger.DirectoryCatalogers(cfg) + default: + return nil, nil, nil, fmt.Errorf("unable to determine cataloger set from scheme=%+v", src.Metadata.Scheme) + } + } + + catalog, relationships, err := cataloger.Catalog(resolver, release, catalogers...) + if err != nil { + return nil, nil, nil, err + } + + return catalog, relationships, release, nil +} + +// SetLogger sets the logger object used for all syft logging calls. +func SetLogger(logger logger.Logger) { + log.Log = logger +} + +// SetBus sets the event bus for all syft library bus publish events onto (in-library subscriptions are not allowed). +func SetBus(b *partybus.Bus) { + bus.SetPublisher(b) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/identify_release.go b/ci/tools/openeuler-purl/syft-dev/syft/linux/identify_release.go new file mode 100644 index 0000000000000000000000000000000000000000..2b0fbfa48f00f5a98a8ded7c7f1ed42142b610d1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/identify_release.go @@ -0,0 +1,188 @@ +package linux + +import ( + "fmt" + "io" + "regexp" + "strings" + + "github.com/acobaugh/osrelease" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/source" + "github.com/google/go-cmp/cmp" +) + +// returns a distro or nil +type parseFunc func(string) (*Release, error) + +type parseEntry struct { + path string + fn parseFunc +} + +var identityFiles = []parseEntry{ + { + // most distros provide a link at this location + path: "/etc/os-release", + fn: parseOsRelease, + }, + { + // standard location for rhel & debian distros + path: "/usr/lib/os-release", + fn: parseOsRelease, + }, + { + // check for centos:6 + path: "/etc/system-release-cpe", + fn: parseSystemReleaseCPE, + }, + { + // last ditch effort for determining older centos version distro information + path: "/etc/redhat-release", + fn: parseRedhatRelease, + }, + // ///////////////////////////////////////////////////////////////////////////////////////////////////// + // IMPORTANT! checking busybox must be last since other distros contain the busybox binary + { + // check for busybox + path: "/bin/busybox", + fn: parseBusyBox, + }, + // ///////////////////////////////////////////////////////////////////////////////////////////////////// +} + +// IdentifyRelease parses distro-specific files to discover and raise linux distribution release details. +func IdentifyRelease(resolver source.FileResolver) *Release { + for _, entry := range identityFiles { + locations, err := resolver.FilesByPath(entry.path) + if err != nil { + log.Warnf("unable to get path locations from %s: %+v", entry.path, err) + continue + } + + for _, location := range locations { + contentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + log.Debugf("unable to get contents from %s: %s", entry.path, err) + continue + } + + content, err := io.ReadAll(contentReader) + internal.CloseAndLogError(contentReader, location.VirtualPath) + if err != nil { + log.Warnf("unable to read %q: %+v", location.RealPath, err) + break + } + + release, err := entry.fn(string(content)) + if err != nil { + log.Warnf("unable to parse %q", location.RealPath) + } + + if release != nil { + return release + } + } + } + + return nil +} + +func parseOsRelease(contents string) (*Release, error) { + values, err := osrelease.ReadString(contents) + if err != nil { + return nil, fmt.Errorf("unable to read os-release file: %w", err) + } + + var idLike []string + for _, s := range strings.Split(values["ID_LIKE"], " ") { + s = strings.TrimSpace(s) + if s == "" { + continue + } + idLike = append(idLike, s) + } + + r := Release{ + PrettyName: values["PRETTY_NAME"], + Name: values["NAME"], + ID: values["ID"], + IDLike: idLike, + Version: values["VERSION"], + VersionID: values["VERSION_ID"], + VersionCodename: values["VERSION_CODENAME"], + BuildID: values["BUILD_ID"], + ImageID: values["IMAGE_ID"], + ImageVersion: values["IMAGE_VERSION"], + Variant: values["VARIANT"], + VariantID: values["VARIANT_ID"], + HomeURL: values["HOME_URL"], + SupportURL: values["SUPPORT_URL"], + BugReportURL: values["BUG_REPORT_URL"], + PrivacyPolicyURL: values["PRIVACY_POLICY_URL"], + CPEName: values["CPE_NAME"], + } + + // don't allow for empty contents to result in a Release object being created + if cmp.Equal(r, Release{}) { + return nil, nil + } + + return &r, nil +} + +var busyboxVersionMatcher = regexp.MustCompile(`BusyBox v[\d.]+`) + +func parseBusyBox(contents string) (*Release, error) { + matches := busyboxVersionMatcher.FindAllString(contents, -1) + for _, match := range matches { + parts := strings.Split(match, " ") + version := strings.ReplaceAll(parts[1], "v", "") + + return simpleRelease(match, "busybox", version, ""), nil + } + return nil, nil +} + +// example CPE: cpe:/o:centos:linux:6:GA +var systemReleaseCpeMatcher = regexp.MustCompile(`cpe:\/o:(.*?):.*?:(.*?):.*?$`) + +// parseSystemReleaseCPE parses the older centos (6) file to determine distro metadata +func parseSystemReleaseCPE(contents string) (*Release, error) { + matches := systemReleaseCpeMatcher.FindAllStringSubmatch(contents, -1) + for _, match := range matches { + if len(match) < 3 { + continue + } + return simpleRelease(match[1], strings.ToLower(match[1]), match[2], match[0]), nil + } + return nil, nil +} + +// example: "CentOS release 6.10 (Final)" +var redhatReleaseMatcher = regexp.MustCompile(`(.*?)\srelease\s(\d\.\d+)`) + +// parseRedhatRelease is a fallback parsing method for determining distro information in older redhat versions +func parseRedhatRelease(contents string) (*Release, error) { + matches := redhatReleaseMatcher.FindAllStringSubmatch(contents, -1) + for _, match := range matches { + if len(match) < 3 { + continue + } + return simpleRelease(match[1], strings.ToLower(match[1]), match[2], ""), nil + } + return nil, nil +} + +func simpleRelease(prettyName, name, version, cpe string) *Release { + return &Release{ + PrettyName: prettyName, + Name: name, + ID: name, + IDLike: []string{name}, + Version: version, + VersionID: version, + CPEName: cpe, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/identify_release_test.go b/ci/tools/openeuler-purl/syft-dev/syft/linux/identify_release_test.go new file mode 100644 index 0000000000000000000000000000000000000000..687af079dc8fe87081071ab82577a6f8078b671b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/identify_release_test.go @@ -0,0 +1,536 @@ +package linux + +import ( + "io/ioutil" + "os" + "testing" + + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func TestIdentifyRelease(t *testing.T) { + tests := []struct { + fixture string + release *Release + }{ + { + fixture: "test-fixtures/os/alpine", + release: &Release{ + PrettyName: "Alpine Linux v3.11", + Name: "Alpine Linux", + ID: "alpine", + IDLike: nil, + VersionID: "3.11.6", + HomeURL: "https://alpinelinux.org/", + BugReportURL: "https://bugs.alpinelinux.org/", + }, + }, + { + fixture: "test-fixtures/os/amazon", + release: &Release{ + PrettyName: "Amazon Linux 2", + Name: "Amazon Linux", + ID: "amzn", + IDLike: []string{ + "centos", + "rhel", + "fedora", + }, + Version: "2", + VersionID: "2", + HomeURL: "https://amazonlinux.com/", + CPEName: "cpe:2.3:o:amazon:amazon_linux:2", + }, + }, + { + fixture: "test-fixtures/os/busybox", + release: &Release{ + PrettyName: "BusyBox v1.31.1", + Name: "busybox", + ID: "busybox", + IDLike: []string{"busybox"}, + Version: "1.31.1", + VersionID: "1.31.1", + }, + }, + { + fixture: "test-fixtures/os/centos", + release: &Release{ + PrettyName: "CentOS Linux 8 (Core)", + Name: "CentOS Linux", + ID: "centos", + IDLike: []string{"rhel", + "fedora", + }, + Version: "8 (Core)", + VersionID: "8", + HomeURL: "https://www.centos.org/", + BugReportURL: "https://bugs.centos.org/", + CPEName: "cpe:/o:centos:centos:8", + }, + }, + { + fixture: "test-fixtures/os/debian", + release: &Release{ + PrettyName: "Debian GNU/Linux 8 (jessie)", + Name: "Debian GNU/Linux", + ID: "debian", + IDLike: nil, + Version: "8 (jessie)", + VersionID: "8", + HomeURL: "http://www.debian.org/", + SupportURL: "http://www.debian.org/support", + BugReportURL: "https://bugs.debian.org/", + }, + }, + { + fixture: "test-fixtures/os/fedora", + release: &Release{ + PrettyName: "Fedora 31 (Container Image)", + Name: "Fedora", + ID: "fedora", + IDLike: nil, + Version: "31 (Container Image)", + VersionID: "31", + Variant: "Container Image", + VariantID: "container", + HomeURL: "https://fedoraproject.org/", + SupportURL: "https://fedoraproject.org/wiki/Communicating_and_getting_help", + BugReportURL: "https://bugzilla.redhat.com/", + PrivacyPolicyURL: "https://fedoraproject.org/wiki/Legal:PrivacyPolicy", + CPEName: "cpe:/o:fedoraproject:fedora:31", + }, + }, + { + fixture: "test-fixtures/os/redhat", + release: &Release{ + PrettyName: "Red Hat Enterprise Linux Server 7.3 (Maipo)", + Name: "Red Hat Enterprise Linux Server", + ID: "rhel", + IDLike: []string{"fedora"}, + Version: "7.3 (Maipo)", + VersionID: "7.3", + HomeURL: "https://www.redhat.com/", + BugReportURL: "https://bugzilla.redhat.com/", + CPEName: "cpe:/o:redhat:enterprise_linux:7.3:GA:server", + }, + }, + { + fixture: "test-fixtures/os/ubuntu", + release: &Release{ + PrettyName: "Ubuntu 20.04 LTS", + Name: "Ubuntu", + ID: "ubuntu", + IDLike: []string{"debian"}, + Version: "20.04 LTS (Focal Fossa)", + VersionCodename: "focal", + VersionID: "20.04", + HomeURL: "https://www.ubuntu.com/", + SupportURL: "https://help.ubuntu.com/", + BugReportURL: "https://bugs.launchpad.net/ubuntu/", + PrivacyPolicyURL: "https://www.ubuntu.com/legal/terms-and-policies/privacy-policy", + }, + }, + { + fixture: "test-fixtures/os/oraclelinux", + release: &Release{ + PrettyName: "Oracle Linux Server 8.3", + Name: "Oracle Linux Server", + ID: "ol", + IDLike: []string{"fedora"}, + Version: "8.3", + VersionID: "8.3", + Variant: "Server", + VariantID: "server", + HomeURL: "https://linux.oracle.com/", + BugReportURL: "https://bugzilla.oracle.com/", + CPEName: "cpe:/o:oracle:linux:8:3:server", + }, + }, + { + fixture: "test-fixtures/os/empty", + }, + { + fixture: "test-fixtures/os/custom", + release: &Release{ + PrettyName: "CentOS Linux 8 (Core)", + Name: "Scientific Linux", + ID: "scientific", + IDLike: []string{ + "rhel", + "fedora", + }, + Version: "16 (Core)", + VersionID: "8", + HomeURL: "https://www.centos.org/", + BugReportURL: "https://bugs.centos.org/", + CPEName: "cpe:/o:centos:centos:8", + }, + }, + { + fixture: "test-fixtures/os/opensuse-leap", + release: &Release{ + PrettyName: "openSUSE Leap 15.2", + Name: "openSUSE Leap", + ID: "opensuse-leap", + IDLike: []string{ + "suse", + "opensuse", + }, + Version: "15.2", + VersionID: "15.2", + HomeURL: "https://www.opensuse.org/", + BugReportURL: "https://bugs.opensuse.org", + CPEName: "cpe:/o:opensuse:leap:15.2", + }, + }, + { + fixture: "test-fixtures/os/sles", + release: &Release{ + PrettyName: "SUSE Linux Enterprise Server 15 SP2", + Name: "SLES", + ID: "sles", + IDLike: []string{"suse"}, + Version: "15-SP2", + VersionID: "15.2", + CPEName: "cpe:/o:suse:sles:15:sp2", + }, + }, + { + fixture: "test-fixtures/os/photon", + release: &Release{ + PrettyName: "VMware Photon OS/Linux", + Name: "VMware Photon OS", + ID: "photon", + IDLike: nil, + Version: "2.0", + VersionID: "2.0", + HomeURL: "https://vmware.github.io/photon/", + BugReportURL: "https://github.com/vmware/photon/issues", + }, + }, + { + fixture: "test-fixtures/os/arch", + release: &Release{ + PrettyName: "Arch Linux", + Name: "Arch Linux", + ID: "arch", + IDLike: nil, + BuildID: "rolling", + HomeURL: "https://www.archlinux.org/", + SupportURL: "https://bbs.archlinux.org/", + BugReportURL: "https://bugs.archlinux.org/", + }, + }, + { + fixture: "test-fixtures/partial-fields/missing-id", + release: &Release{ + Name: "Debian GNU/Linux", + IDLike: []string{"debian"}, + VersionID: "8", + }, + }, + { + fixture: "test-fixtures/partial-fields/unknown-id", + release: &Release{ + Name: "Debian GNU/Linux", + ID: "my-awesome-distro", + IDLike: []string{"debian"}, + VersionID: "8", + }, + }, + { + fixture: "test-fixtures/partial-fields/missing-version", + release: &Release{ + Name: "Debian GNU/Linux", + IDLike: []string{"debian"}, + }, + }, + { + fixture: "test-fixtures/os/centos6", + release: &Release{ + PrettyName: "centos", + Name: "centos", + ID: "centos", + IDLike: []string{"centos"}, + Version: "6", + VersionID: "6", + CPEName: "cpe:/o:centos:linux:6:GA", + }, + }, + { + fixture: "test-fixtures/os/centos5", + release: &Release{ + PrettyName: "CentOS", + Name: "centos", + ID: "centos", + IDLike: []string{"centos"}, + Version: "5.7", + VersionID: "5.7", + }, + }, + { + fixture: "test-fixtures/os/mariner", + release: &Release{ + PrettyName: "CBL-Mariner/Linux", + Name: "Common Base Linux Mariner", + ID: "mariner", + IDLike: nil, + Version: "1.0.20210901", + VersionID: "1.0", + HomeURL: "https://aka.ms/cbl-mariner", + SupportURL: "https://aka.ms/cbl-mariner", + BugReportURL: "https://aka.ms/cbl-mariner", + }, + }, + { + fixture: "test-fixtures/os/rockylinux", + release: &Release{ + PrettyName: "Rocky Linux 8.4 (Green Obsidian)", + Name: "Rocky Linux", + ID: "rocky", + IDLike: []string{ + "rhel", + "fedora", + }, + Version: "8.4 (Green Obsidian)", + VersionID: "8.4", + HomeURL: "https://rockylinux.org/", + BugReportURL: "https://bugs.rockylinux.org/", + CPEName: "cpe:/o:rocky:rocky:8.4:GA", + }, + }, + { + fixture: "test-fixtures/os/almalinux", + release: &Release{ + PrettyName: "AlmaLinux 8.4 (Electric Cheetah)", + Name: "AlmaLinux", + ID: "almalinux", + IDLike: []string{ + "rhel", + "centos", + "fedora", + }, + Version: "8.4 (Electric Cheetah)", + VersionID: "8.4", + HomeURL: "https://almalinux.org/", + BugReportURL: "https://bugs.almalinux.org/", + CPEName: "cpe:/o:almalinux:almalinux:8.4:GA", + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + s, err := source.NewFromDirectory(test.fixture) + require.NoError(t, err) + + resolver, err := s.FileResolver(source.SquashedScope) + require.NoError(t, err) + + assert.Equal(t, test.release, IdentifyRelease(resolver)) + }) + } +} + +func TestParseOsRelease(t *testing.T) { + + tests := []struct { + fixture string + release *Release + }{ + { + fixture: "test-fixtures/ubuntu-20.04", + + release: &Release{ + PrettyName: "Ubuntu 20.04 LTS", + Name: "Ubuntu", + ID: "ubuntu", + IDLike: []string{"debian"}, + Version: "20.04 LTS (Focal Fossa)", + VersionID: "20.04", + VersionCodename: "focal", + HomeURL: "https://www.ubuntu.com/", + SupportURL: "https://help.ubuntu.com/", + BugReportURL: "https://bugs.launchpad.net/ubuntu/", + PrivacyPolicyURL: "https://www.ubuntu.com/legal/terms-and-policies/privacy-policy", + }, + }, + + { + fixture: "test-fixtures/debian-8", + + release: &Release{ + PrettyName: "Debian GNU/Linux 8 (jessie)", + Name: "Debian GNU/Linux", + ID: "debian", + IDLike: nil, + Version: "8 (jessie)", + VersionID: "8", + HomeURL: "http://www.debian.org/", + SupportURL: "http://www.debian.org/support", + BugReportURL: "https://bugs.debian.org/", + }, + }, + + { + fixture: "test-fixtures/centos-8", + + release: &Release{ + PrettyName: "CentOS Linux 8 (Core)", + Name: "CentOS Linux", + ID: "centos", + IDLike: []string{ + "rhel", + "fedora", + }, + Version: "8 (Core)", + VersionID: "8", + HomeURL: "https://www.centos.org/", + BugReportURL: "https://bugs.centos.org/", + CPEName: "cpe:/o:centos:centos:8", + }, + }, + + { + fixture: "test-fixtures/rhel-8", + + release: &Release{ + PrettyName: "Red Hat Enterprise Linux 8.1 (Ootpa)", + Name: "Red Hat Enterprise Linux", + ID: "rhel", + IDLike: []string{"fedora"}, + Version: "8.1 (Ootpa)", + VersionID: "8.1", + HomeURL: "https://www.redhat.com/", + BugReportURL: "https://bugzilla.redhat.com/", + CPEName: "cpe:/o:redhat:enterprise_linux:8.1:GA", + }, + }, + + { + fixture: "test-fixtures/unprintable", + + release: &Release{ + PrettyName: "Debian GNU/Linux 8 (jessie)", + Name: "Debian GNU/Linux", + ID: "debian", + IDLike: nil, + Version: "8 (jessie)", + VersionID: "8", + HomeURL: "http://www.debian.org/", + SupportURL: "http://www.debian.org/support", + BugReportURL: "https://bugs.debian.org/", + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, + func(t *testing.T) { + release, + err := parseOsRelease(retrieveFixtureContentsAsString(test.fixture, + t)) + require.NoError(t, + err) + assert.Equal(t, + test.release, + release) + }) + } + +} + +func TestParseSystemReleaseCPE(t *testing.T) { + tests := []struct { + fixture string + release *Release + }{ + { + fixture: "test-fixtures/os/centos6/etc/system-release-cpe", + release: &Release{ + PrettyName: "centos", + Name: "centos", + ID: "centos", + IDLike: []string{"centos"}, + Version: "6", + VersionID: "6", + CPEName: "cpe:/o:centos:linux:6:GA", + }, + }, + { + fixture: "test-fixtures/bad-system-release-cpe", + release: nil, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + contents := retrieveFixtureContentsAsString(test.fixture, t) + release, err := parseSystemReleaseCPE(contents) + require.NoError(t, err) + if test.release == nil { + assert.Nil(t, release) + return + } + + assert.Equal(t, test.release, release) + }) + } +} + +func TestParseRedhatRelease(t *testing.T) { + tests := []struct { + fixture string + name string + release *Release + }{ + { + fixture: "test-fixtures/os/centos5/etc/redhat-release", + name: "Centos 5", + release: &Release{ + PrettyName: "CentOS", + Name: "centos", + ID: "centos", + IDLike: []string{"centos"}, + Version: "5.7", + VersionID: "5.7", + }, + }, + { + fixture: "test-fixtures/bad-redhat-release", + name: "Centos 5 Bad Redhat Release", + release: nil, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + release, err := parseRedhatRelease(retrieveFixtureContentsAsString(test.fixture, t)) + require.NoError(t, err) + if test.release == nil { + assert.Nil(t, release) + return + } + + assert.Equal(t, test.release, release) + }) + } +} + +func retrieveFixtureContentsAsString(fixturePath string, t *testing.T) string { + fixture, err := os.Open(fixturePath) + if err != nil { + t.Fatalf("could not open test fixture=%s: %+v", fixturePath, err) + } + defer fixture.Close() + + b, err := ioutil.ReadAll(fixture) + if err != nil { + t.Fatalf("unable to read fixture file: %+v", err) + } + + return string(b) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/release.go b/ci/tools/openeuler-purl/syft-dev/syft/linux/release.go new file mode 100644 index 0000000000000000000000000000000000000000..ab68fbc5e6fb517d14de0b0f9b5708a36801278d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/release.go @@ -0,0 +1,42 @@ +package linux + +// Release represents Linux Distribution release information as specified from https://www.freedesktop.org/software/systemd/man/os-release.html +type Release struct { + PrettyName string `cyclonedx:"prettyName"` // A pretty operating system name in a format suitable for presentation to the user. + Name string // identifies the operating system, without a version component, and suitable for presentation to the user. + ID string `cyclonedx:"id"` // identifies the operating system, excluding any version information and suitable for processing by scripts or usage in generated filenames. + IDLike []string `cyclonedx:"idLike"` // list of operating system identifiers in the same syntax as the ID= setting. It should list identifiers of operating systems that are closely related to the local operating system in regards to packaging and programming interfaces. + Version string // identifies the operating system version, excluding any OS name information, possibly including a release code name, and suitable for presentation to the user. + VersionID string `cyclonedx:"versionID"` // identifies the operating system version, excluding any OS name information or release code name, and suitable for processing by scripts or usage in generated filenames. + VersionCodename string `cyclonedx:"versionCodename"` + BuildID string `cyclonedx:"buildID"` // A string uniquely identifying the system image originally used as the installation base. + ImageID string `cyclonedx:"imageID"` + ImageVersion string `cyclonedx:"imageVersion"` + Variant string `cyclonedx:"variant"` // identifies a specific variant or edition of the operating system suitable for presentation to the user. + VariantID string `cyclonedx:"variantID"` // identifies a specific variant or edition of the operating system. This may be interpreted by other packages in order to determine a divergent default configuration. + HomeURL string + SupportURL string + BugReportURL string + PrivacyPolicyURL string + CPEName string // A CPE name for the operating system, in URI binding syntax +} + +func (r *Release) String() string { + if r == nil { + return "unknown" + } + if r.PrettyName != "" { + return r.PrettyName + } + if r.Name != "" { + return r.Name + } + if r.Version != "" { + return r.ID + " " + r.Version + } + if r.VersionID != "" { + return r.ID + " " + r.VersionID + } + + return r.ID + " " + r.BuildID +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/bad-redhat-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/bad-redhat-release new file mode 100644 index 0000000000000000000000000000000000000000..3b3e09a8043a1672a032ba797631b6139d846541 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/bad-redhat-release @@ -0,0 +1 @@ +CentOS release 5 (Final) \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/bad-system-release-cpe b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/bad-system-release-cpe new file mode 100644 index 0000000000000000000000000000000000000000..33f91e1e4c961ec2e68385f5e223fdc369fe7021 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/bad-system-release-cpe @@ -0,0 +1 @@ +cpe:/o:centos:6:GA \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/centos-8 b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/centos-8 new file mode 100644 index 0000000000000000000000000000000000000000..7f10b7745b93922e6754522ecd5bb9399fe0a67a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/centos-8 @@ -0,0 +1,17 @@ +NAME="CentOS Linux" +VERSION="8 (Core)" +ID="centos" +ID_LIKE="rhel fedora" +VERSION_ID="8" +PLATFORM_ID="platform:el8" +PRETTY_NAME="CentOS Linux 8 (Core)" +ANSI_COLOR="0;31" +CPE_NAME="cpe:/o:centos:centos:8" +HOME_URL="https://www.centos.org/" +BUG_REPORT_URL="https://bugs.centos.org/" + +CENTOS_MANTISBT_PROJECT="CentOS-8" +CENTOS_MANTISBT_PROJECT_VERSION="8" +REDHAT_SUPPORT_PRODUCT="centos" +REDHAT_SUPPORT_PRODUCT_VERSION="8" + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/debian-8 b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/debian-8 new file mode 100644 index 0000000000000000000000000000000000000000..120c51b0898ebe6ebbaaabd0580859c7a9c39701 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/debian-8 @@ -0,0 +1,8 @@ +PRETTY_NAME="Debian GNU/Linux 8 (jessie)" +NAME="Debian GNU/Linux" +VERSION_ID="8" +VERSION="8 (jessie)" +ID=debian +HOME_URL="http://www.debian.org/" +SUPPORT_URL="http://www.debian.org/support" +BUG_REPORT_URL="https://bugs.debian.org/" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/almalinux/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/almalinux/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..61deb8e91346b3cc47ae37f91a51149101b8f0fd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/almalinux/etc/os-release @@ -0,0 +1,15 @@ +NAME="AlmaLinux" +VERSION="8.4 (Electric Cheetah)" +ID="almalinux" +ID_LIKE="rhel centos fedora" +VERSION_ID="8.4" +PLATFORM_ID="platform:el8" +PRETTY_NAME="AlmaLinux 8.4 (Electric Cheetah)" +ANSI_COLOR="0;34" +CPE_NAME="cpe:/o:almalinux:almalinux:8.4:GA" +HOME_URL="https://almalinux.org/" +DOCUMENTATION_URL="https://wiki.almalinux.org/" +BUG_REPORT_URL="https://bugs.almalinux.org/" + +ALMALINUX_MANTISBT_PROJECT="AlmaLinux-8" +ALMALINUX_MANTISBT_PROJECT_VERSION="8.4" \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/alpine/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/alpine/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..39f4591b79ed95581a410ecde32a1ae1eeacb782 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/alpine/etc/os-release @@ -0,0 +1,6 @@ +NAME="Alpine Linux" +ID=alpine +VERSION_ID=3.11.6 +PRETTY_NAME="Alpine Linux v3.11" +HOME_URL="https://alpinelinux.org/" +BUG_REPORT_URL="https://bugs.alpinelinux.org/" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/amazon/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/amazon/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..07a45072fba642f95b7271facd18dd8371788df0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/amazon/etc/os-release @@ -0,0 +1,9 @@ +NAME="Amazon Linux" +VERSION="2" +ID="amzn" +ID_LIKE="centos rhel fedora" +VERSION_ID="2" +PRETTY_NAME="Amazon Linux 2" +ANSI_COLOR="0;33" +CPE_NAME="cpe:2.3:o:amazon:amazon_linux:2" +HOME_URL="https://amazonlinux.com/" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/arch/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/arch/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..e420b15e449464d872c217bfaf06577797f13cee --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/arch/etc/os-release @@ -0,0 +1,10 @@ +NAME="Arch Linux" +PRETTY_NAME="Arch Linux" +ID=arch +BUILD_ID=rolling +ANSI_COLOR="38;2;23;147;209" +HOME_URL="https://www.archlinux.org/" +DOCUMENTATION_URL="https://wiki.archlinux.org/" +SUPPORT_URL="https://bbs.archlinux.org/" +BUG_REPORT_URL="https://bugs.archlinux.org/" +LOGO=archlinux diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/centos5/etc/redhat-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/centos5/etc/redhat-release new file mode 100644 index 0000000000000000000000000000000000000000..5f60003a844837650cc9fc15c2baa5c49fa6cfed --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/centos5/etc/redhat-release @@ -0,0 +1 @@ +CentOS release 5.7 (Final) \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/centos6/etc/system-release-cpe b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/centos6/etc/system-release-cpe new file mode 100644 index 0000000000000000000000000000000000000000..f7671336181cbdd63a75ddd15834d647d0423ac1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/centos6/etc/system-release-cpe @@ -0,0 +1 @@ +cpe:/o:centos:linux:6:GA \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/custom/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/custom/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..97edcdbf24fad2a69f1155c40c01d5292227d340 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/custom/etc/os-release @@ -0,0 +1,17 @@ +NAME="Scientific Linux" +VERSION="16 (Core)" +ID="scientific" +ID_LIKE="rhel fedora" +VERSION_ID="8" +PLATFORM_ID="platform:el8" +PRETTY_NAME="CentOS Linux 8 (Core)" +ANSI_COLOR="0;31" +CPE_NAME="cpe:/o:centos:centos:8" +HOME_URL="https://www.centos.org/" +BUG_REPORT_URL="https://bugs.centos.org/" + +CENTOS_MANTISBT_PROJECT="CentOS-8" +CENTOS_MANTISBT_PROJECT_VERSION="8" +REDHAT_SUPPORT_PRODUCT="centos" +REDHAT_SUPPORT_PRODUCT_VERSION="8" + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/empty/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/empty/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/mariner/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/mariner/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..6af1d8798f3c66d96c633a883c8ea6b325511899 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/mariner/etc/os-release @@ -0,0 +1,9 @@ +NAME="Common Base Linux Mariner" +VERSION="1.0.20210901" +ID=mariner +VERSION_ID=1.0 +PRETTY_NAME="CBL-Mariner/Linux" +ANSI_COLOR="1;34" +HOME_URL="https://aka.ms/cbl-mariner" +BUG_REPORT_URL="https://aka.ms/cbl-mariner" +SUPPORT_URL="https://aka.ms/cbl-mariner" \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/opensuse-leap/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/opensuse-leap/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..1494bc552b377e8c9c237c2e2588690d68a3be2b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/opensuse-leap/etc/os-release @@ -0,0 +1,10 @@ +NAME="openSUSE Leap" +VERSION="15.2" +ID="opensuse-leap" +ID_LIKE="suse opensuse" +VERSION_ID="15.2" +PRETTY_NAME="openSUSE Leap 15.2" +ANSI_COLOR="0;32" +CPE_NAME="cpe:/o:opensuse:leap:15.2" +BUG_REPORT_URL="https://bugs.opensuse.org" +HOME_URL="https://www.opensuse.org/" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/oraclelinux/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/oraclelinux/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..85a8c1a16d1f30e07141d3ab6c27a80a2e4c77b7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/oraclelinux/etc/os-release @@ -0,0 +1,18 @@ +NAME="Oracle Linux Server" +VERSION="8.3" +ID="ol" +ID_LIKE="fedora" +VARIANT="Server" +VARIANT_ID="server" +VERSION_ID="8.3" +PLATFORM_ID="platform:el8" +PRETTY_NAME="Oracle Linux Server 8.3" +ANSI_COLOR="0;31" +CPE_NAME="cpe:/o:oracle:linux:8:3:server" +HOME_URL="https://linux.oracle.com/" +BUG_REPORT_URL="https://bugzilla.oracle.com/" + +ORACLE_BUGZILLA_PRODUCT="Oracle Linux 8" +ORACLE_BUGZILLA_PRODUCT_VERSION=8.3 +ORACLE_SUPPORT_PRODUCT="Oracle Linux" +ORACLE_SUPPORT_PRODUCT_VERSION=8.3 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/photon/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/photon/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..cea880c421671df8ebbc07cb11bfaedecd7db26a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/photon/etc/os-release @@ -0,0 +1,8 @@ +NAME="VMware Photon OS" +VERSION="2.0" +ID=photon +VERSION_ID=2.0 +PRETTY_NAME="VMware Photon OS/Linux" +ANSI_COLOR="1;34" +HOME_URL="https://vmware.github.io/photon/" +BUG_REPORT_URL="https://github.com/vmware/photon/issues" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/rockylinux/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/rockylinux/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..2b0f971696d11580fc418080e401d95129f4df6f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/rockylinux/etc/os-release @@ -0,0 +1,13 @@ +NAME="Rocky Linux" +VERSION="8.4 (Green Obsidian)" +ID="rocky" +ID_LIKE="rhel fedora" +VERSION_ID="8.4" +PLATFORM_ID="platform:el8" +PRETTY_NAME="Rocky Linux 8.4 (Green Obsidian)" +ANSI_COLOR="0;32" +CPE_NAME="cpe:/o:rocky:rocky:8.4:GA" +HOME_URL="https://rockylinux.org/" +BUG_REPORT_URL="https://bugs.rockylinux.org/" +ROCKY_SUPPORT_PRODUCT="Rocky Linux" +ROCKY_SUPPORT_PRODUCT_VERSION="8" \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/sles/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/sles/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..9068e540cef995184f08677d02a2e1abbea96dd0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/sles/etc/os-release @@ -0,0 +1,9 @@ +NAME="SLES" +VERSION="15-SP2" +VERSION_ID="15.2" +PRETTY_NAME="SUSE Linux Enterprise Server 15 SP2" +ID="sles" +ID_LIKE="suse" +ANSI_COLOR="0;32" +CPE_NAME="cpe:/o:suse:sles:15:sp2" +DOCUMENTATION_URL="https://documentation.suse.com/" \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/ubuntu/etc/os-release b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/ubuntu/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..e07dd980dbf0e957cc2fc48a0c423505623ec643 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/os/ubuntu/etc/os-release @@ -0,0 +1,12 @@ +NAME="Ubuntu" +VERSION="20.04 LTS (Focal Fossa)" +ID=ubuntu +ID_LIKE=debian +PRETTY_NAME="Ubuntu 20.04 LTS" +VERSION_ID="20.04" +HOME_URL="https://www.ubuntu.com/" +SUPPORT_URL="https://help.ubuntu.com/" +BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/" +PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy" +VERSION_CODENAME=focal +UBUNTU_CODENAME=focal diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/rhel-8 b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/rhel-8 new file mode 100644 index 0000000000000000000000000000000000000000..216c1d22660d215e9c367c0daee4eacb8e00fe65 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/rhel-8 @@ -0,0 +1,16 @@ +NAME="Red Hat Enterprise Linux" +VERSION="8.1 (Ootpa)" +ID="rhel" +ID_LIKE="fedora" +VERSION_ID="8.1" +PLATFORM_ID="platform:el8" +PRETTY_NAME="Red Hat Enterprise Linux 8.1 (Ootpa)" +ANSI_COLOR="0;31" +CPE_NAME="cpe:/o:redhat:enterprise_linux:8.1:GA" +HOME_URL="https://www.redhat.com/" +BUG_REPORT_URL="https://bugzilla.redhat.com/" + +REDHAT_BUGZILLA_PRODUCT="Red Hat Enterprise Linux 8" +REDHAT_BUGZILLA_PRODUCT_VERSION=8.1 +REDHAT_SUPPORT_PRODUCT="Red Hat Enterprise Linux" +REDHAT_SUPPORT_PRODUCT_VERSION="8.1" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/ubuntu-20.04 b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/ubuntu-20.04 new file mode 100644 index 0000000000000000000000000000000000000000..e07dd980dbf0e957cc2fc48a0c423505623ec643 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/ubuntu-20.04 @@ -0,0 +1,12 @@ +NAME="Ubuntu" +VERSION="20.04 LTS (Focal Fossa)" +ID=ubuntu +ID_LIKE=debian +PRETTY_NAME="Ubuntu 20.04 LTS" +VERSION_ID="20.04" +HOME_URL="https://www.ubuntu.com/" +SUPPORT_URL="https://help.ubuntu.com/" +BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/" +PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy" +VERSION_CODENAME=focal +UBUNTU_CODENAME=focal diff --git a/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/unprintable b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/unprintable new file mode 100644 index 0000000000000000000000000000000000000000..fa9c6b547a78fd8a54d5d9f020648bf577c9cdbd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/linux/test-fixtures/unprintable @@ -0,0 +1,8 @@ +PRETTY_NAME="Debian GNU/Linux 8 (jessie)" +NAME="Debian GNU/Linux" +VERSION_ID="8" +VERSION="8 (jessie)" +ID=debian +HOME_URL="http://www.debian.org/" +SUPPORT_URL="http://www.debian.org/support" +BUG_REPORT_URL="https://bugs.debian.org/" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/logger/logger.go b/ci/tools/openeuler-purl/syft-dev/syft/logger/logger.go new file mode 100644 index 0000000000000000000000000000000000000000..3ace363f5caeb7255e30a8f6dd27aadb5a91ae27 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/logger/logger.go @@ -0,0 +1,16 @@ +/* +Package logger defines the logging interface which is used throughout the syft library. +*/ +package logger + +// Logger represents the behavior for logging within the syft library. +type Logger interface { + Errorf(format string, args ...interface{}) + Error(args ...interface{}) + Warnf(format string, args ...interface{}) + Warn(args ...interface{}) + Infof(format string, args ...interface{}) + Info(args ...interface{}) + Debugf(format string, args ...interface{}) + Debug(args ...interface{}) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/alpm_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/alpm_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..0867915c651a463f42abc10ad1578fc6b3d847ca --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/alpm_metadata.go @@ -0,0 +1,80 @@ +package pkg + +import ( + "sort" + "time" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/linux" + "github.com/scylladb/go-set/strset" +) + +const AlpmDBGlob = "**/var/lib/pacman/local/**/desc" + +type AlpmMetadata struct { + BasePackage string `mapstructure:"base" json:"basepackage"` + Package string `mapstructure:"name" json:"package"` + Version string `mapstructure:"version" json:"version"` + Description string `mapstructure:"desc" json:"description"` + Architecture string `mapstructure:"arch" json:"architecture"` + Size int `mapstructure:"size" json:"size" cyclonedx:"size"` + Packager string `mapstructure:"packager" json:"packager"` + License string `mapstructure:"license" json:"license"` + URL string `mapstructure:"url" json:"url"` + Validation string `mapstructure:"validation" json:"validation"` + Reason int `mapstructure:"reason" json:"reason"` + Files []AlpmFileRecord `mapstructure:"files" json:"files"` + Backup []AlpmFileRecord `mapstructure:"backup" json:"backup"` +} + +type AlpmFileRecord struct { + Path string `mapstruture:"path" json:"path,omitempty"` + Type string `mapstructure:"type" json:"type,omitempty"` + UID string `mapstructure:"uid" json:"uid,omitempty"` + GID string `mapstructure:"gid" json:"gid,omitempty"` + Time time.Time `mapstructure:"time" json:"time,omitempty"` + Size string `mapstructure:"size" json:"size,omitempty"` + Link string `mapstructure:"link" json:"link,omitempty"` + Digests []file.Digest `mapstructure:"digests" json:"digest,omitempty"` +} + +// PackageURL returns the PURL for the specific Arch Linux package (see https://github.com/package-url/purl-spec) +func (m AlpmMetadata) PackageURL(distro *linux.Release) string { + qualifiers := map[string]string{ + PURLQualifierArch: m.Architecture, + } + + if m.BasePackage != "" { + qualifiers[PURLQualifierUpstream] = m.BasePackage + } + + distroID := "" + if distro != nil { + distroID = distro.ID + } + + return packageurl.NewPackageURL( + "alpm", + distroID, + m.Package, + m.Version, + purlQualifiers( + qualifiers, + distro, + ), + "", + ).ToString() +} + +func (m AlpmMetadata) OwnedFiles() (result []string) { + s := strset.New() + for _, f := range m.Files { + if f.Path != "" { + s.Add(f.Path) + } + } + result = s.List() + sort.Strings(result) + return result +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/alpm_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/alpm_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..8adae54b16425d523fd6e1ca2c8433bc06e4280d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/alpm_metadata_test.go @@ -0,0 +1,112 @@ +package pkg + +import ( + "testing" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" + "github.com/sergi/go-diff/diffmatchpatch" +) + +func TestAlpmMetadata_pURL(t *testing.T) { + tests := []struct { + name string + metadata AlpmMetadata + distro linux.Release + expected string + }{ + { + name: "gocase", + metadata: AlpmMetadata{ + Package: "p", + Version: "v", + Architecture: "a", + }, + distro: linux.Release{ + ID: "arch", + BuildID: "rolling", + }, + expected: "pkg:alpm/arch/p@v?arch=a&distro=arch-rolling", + }, + { + name: "missing architecture", + metadata: AlpmMetadata{ + Package: "p", + Version: "v", + }, + distro: linux.Release{ + ID: "arch", + }, + expected: "pkg:alpm/arch/p@v?distro=arch", + }, + { + metadata: AlpmMetadata{ + Package: "python", + Version: "3.10.0", + Architecture: "any", + }, + distro: linux.Release{ + ID: "arch", + BuildID: "rolling", + }, + expected: "pkg:alpm/arch/python@3.10.0?arch=any&distro=arch-rolling", + }, + { + metadata: AlpmMetadata{ + Package: "g plus plus", + Version: "v84", + Architecture: "x86_64", + }, + distro: linux.Release{ + ID: "arch", + BuildID: "rolling", + }, + expected: "pkg:alpm/arch/g%20plus%20plus@v84?arch=x86_64&distro=arch-rolling", + }, + { + name: "add source information as qualifier", + metadata: AlpmMetadata{ + Package: "p", + Version: "v", + Architecture: "a", + BasePackage: "origin", + }, + distro: linux.Release{ + ID: "arch", + BuildID: "rolling", + }, + expected: "pkg:alpm/arch/p@v?arch=a&upstream=origin&distro=arch-rolling", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := test.metadata.PackageURL(&test.distro) + if actual != test.expected { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.expected, actual, true) + t.Errorf("diff: %s", dmp.DiffPrettyText(diffs)) + } + // verify packageurl can parse + purl, err := packageurl.FromString(actual) + if err != nil { + t.Errorf("cannot re-parse purl: %s", actual) + } + if purl.Name != test.metadata.Package { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.metadata.Package, purl.Name, true) + t.Errorf("invalid purl name: %s", dmp.DiffPrettyText(diffs)) + } + if purl.Version != test.metadata.Version { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.metadata.Version, purl.Version, true) + t.Errorf("invalid purl version: %s", dmp.DiffPrettyText(diffs)) + } + if purl.Qualifiers.Map()["arch"] != test.metadata.Architecture { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.metadata.Architecture, purl.Qualifiers.Map()["arch"], true) + t.Errorf("invalid purl architecture: %s", dmp.DiffPrettyText(diffs)) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/apk_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/apk_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..843b5a77f78153a2cf22edbc6b5535129965ebe9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/apk_metadata.go @@ -0,0 +1,85 @@ +package pkg + +import ( + "sort" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/linux" + "github.com/scylladb/go-set/strset" +) + +const ApkDBGlob = "**/lib/apk/db/installed" + +var ( + _ FileOwner = (*ApkMetadata)(nil) + _ urlIdentifier = (*ApkMetadata)(nil) +) + +// ApkMetadata represents all captured data for a Alpine DB package entry. +// See the following sources for more information: +// - https://wiki.alpinelinux.org/wiki/Apk_spec +// - https://git.alpinelinux.org/apk-tools/tree/src/package.c +// - https://git.alpinelinux.org/apk-tools/tree/src/database.c +type ApkMetadata struct { + Package string `mapstructure:"P" json:"package"` + OriginPackage string `mapstructure:"o" json:"originPackage" cyclonedx:"originPackage"` + Maintainer string `mapstructure:"m" json:"maintainer"` + Version string `mapstructure:"V" json:"version"` + License string `mapstructure:"L" json:"license"` + Architecture string `mapstructure:"A" json:"architecture"` + URL string `mapstructure:"U" json:"url"` + Description string `mapstructure:"T" json:"description"` + Size int `mapstructure:"S" json:"size" cyclonedx:"size"` + InstalledSize int `mapstructure:"I" json:"installedSize" cyclonedx:"installedSize"` + PullDependencies string `mapstructure:"D" json:"pullDependencies" cyclonedx:"pullDependencies"` + PullChecksum string `mapstructure:"C" json:"pullChecksum" cyclonedx:"pullChecksum"` + GitCommitOfAport string `mapstructure:"c" json:"gitCommitOfApkPort" cyclonedx:"gitCommitOfApkPort"` + Files []ApkFileRecord `json:"files"` +} + +// ApkFileRecord represents a single file listing and metadata from a APK DB entry (which may have many of these file records). +type ApkFileRecord struct { + Path string `json:"path"` + OwnerUID string `json:"ownerUid,omitempty"` + OwnerGID string `json:"ownerGid,omitempty"` + Permissions string `json:"permissions,omitempty"` + Digest *file.Digest `json:"digest,omitempty"` +} + +// PackageURL returns the PURL for the specific Alpine package (see https://github.com/package-url/purl-spec) +func (m ApkMetadata) PackageURL(distro *linux.Release) string { + qualifiers := map[string]string{ + PURLQualifierArch: m.Architecture, + } + + if m.OriginPackage != "" { + qualifiers[PURLQualifierUpstream] = m.OriginPackage + } + + return packageurl.NewPackageURL( + // note: this is currently a candidate and not technically within spec + // see https://github.com/package-url/purl-spec#other-candidate-types-to-define + "alpine", + "", + m.Package, + m.Version, + purlQualifiers( + qualifiers, + distro, + ), + "", + ).ToString() +} + +func (m ApkMetadata) OwnedFiles() (result []string) { + s := strset.New() + for _, f := range m.Files { + if f.Path != "" { + s.Add(f.Path) + } + } + result = s.List() + sort.Strings(result) + return result +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/apk_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/apk_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..1e981201f28b3c824f9fa9580a839083ad30a532 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/apk_metadata_test.go @@ -0,0 +1,157 @@ +package pkg + +import ( + "strings" + "testing" + + "github.com/anchore/syft/syft/linux" + + "github.com/anchore/packageurl-go" + "github.com/go-test/deep" + "github.com/sergi/go-diff/diffmatchpatch" +) + +func TestApkMetadata_pURL(t *testing.T) { + tests := []struct { + name string + metadata ApkMetadata + distro linux.Release + expected string + }{ + { + name: "gocase", + metadata: ApkMetadata{ + Package: "p", + Version: "v", + Architecture: "a", + }, + distro: linux.Release{ + ID: "alpine", + VersionID: "3.4.6", + }, + expected: "pkg:alpine/p@v?arch=a&distro=alpine-3.4.6", + }, + { + name: "missing architecture", + metadata: ApkMetadata{ + Package: "p", + Version: "v", + }, + distro: linux.Release{ + ID: "alpine", + VersionID: "3.4.6", + }, + expected: "pkg:alpine/p@v?distro=alpine-3.4.6", + }, + // verify #351 + { + metadata: ApkMetadata{ + Package: "g++", + Version: "v84", + Architecture: "am86", + }, + distro: linux.Release{ + ID: "alpine", + VersionID: "3.4.6", + }, + expected: "pkg:alpine/g++@v84?arch=am86&distro=alpine-3.4.6", + }, + { + metadata: ApkMetadata{ + Package: "g plus plus", + Version: "v84", + Architecture: "am86", + }, + distro: linux.Release{ + ID: "alpine", + VersionID: "3.15.0", + }, + expected: "pkg:alpine/g%20plus%20plus@v84?arch=am86&distro=alpine-3.15.0", + }, + { + name: "add source information as qualifier", + metadata: ApkMetadata{ + Package: "p", + Version: "v", + Architecture: "a", + OriginPackage: "origin", + }, + distro: linux.Release{ + ID: "alpine", + VersionID: "3.4.6", + }, + expected: "pkg:alpine/p@v?arch=a&upstream=origin&distro=alpine-3.4.6", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := test.metadata.PackageURL(&test.distro) + if actual != test.expected { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.expected, actual, true) + t.Errorf("diff: %s", dmp.DiffPrettyText(diffs)) + } + // verify packageurl can parse + purl, err := packageurl.FromString(actual) + if err != nil { + t.Errorf("cannot re-parse purl: %s", actual) + } + if purl.Name != test.metadata.Package { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.metadata.Package, purl.Name, true) + t.Errorf("invalid purl name: %s", dmp.DiffPrettyText(diffs)) + } + if purl.Version != test.metadata.Version { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.metadata.Version, purl.Version, true) + t.Errorf("invalid purl version: %s", dmp.DiffPrettyText(diffs)) + } + if purl.Qualifiers.Map()["arch"] != test.metadata.Architecture { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.metadata.Architecture, purl.Qualifiers.Map()["arch"], true) + t.Errorf("invalid purl architecture: %s", dmp.DiffPrettyText(diffs)) + } + }) + } +} + +func TestApkMetadata_FileOwner(t *testing.T) { + tests := []struct { + metadata ApkMetadata + expected []string + }{ + { + metadata: ApkMetadata{ + Files: []ApkFileRecord{ + {Path: "/somewhere"}, + {Path: "/else"}, + }, + }, + expected: []string{ + "/else", + "/somewhere", + }, + }, + { + metadata: ApkMetadata{ + Files: []ApkFileRecord{ + {Path: "/somewhere"}, + {Path: ""}, + }, + }, + expected: []string{ + "/somewhere", + }, + }, + } + + for _, test := range tests { + t.Run(strings.Join(test.expected, ","), func(t *testing.T) { + actual := test.metadata.OwnedFiles() + for _, d := range deep.Equal(test.expected, actual) { + t.Errorf("diff: %+v", d) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cargo_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cargo_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..f5c4a6694edd714a3bfbf83b1ed4ff88e3986c3a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cargo_metadata.go @@ -0,0 +1,19 @@ +package pkg + +type CargoMetadata struct { + Packages []CargoPackageMetadata `toml:"package"` +} + +// Pkgs returns all of the packages referenced within the Cargo.lock metadata. +func (m CargoMetadata) Pkgs() []*Package { + pkgs := make([]*Package, 0) + + for _, p := range m.Packages { + if p.Dependencies == nil { + p.Dependencies = make([]string, 0) + } + pkgs = append(pkgs, p.Pkg()) + } + + return pkgs +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cargo_package_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cargo_package_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..936062d445204f700f6764ac8d09fc8b9e83460a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cargo_package_metadata.go @@ -0,0 +1,40 @@ +package pkg + +import ( + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +var _ urlIdentifier = (*CargoPackageMetadata)(nil) + +type CargoPackageMetadata struct { + Name string `toml:"name" json:"name"` + Version string `toml:"version" json:"version"` + Source string `toml:"source" json:"source"` + Checksum string `toml:"checksum" json:"checksum"` + Dependencies []string `toml:"dependencies" json:"dependencies"` +} + +// Pkg returns the standard `pkg.Package` representation of the package referenced within the Cargo.lock metadata. +func (p CargoPackageMetadata) Pkg() *Package { + return &Package{ + Name: p.Name, + Version: p.Version, + Language: Rust, + Type: RustPkg, + MetadataType: RustCargoPackageMetadataType, + Metadata: p, + } +} + +// PackageURL returns the PURL for the specific rust package (see https://github.com/package-url/purl-spec) +func (p CargoPackageMetadata) PackageURL(_ *linux.Release) string { + return packageurl.NewPackageURL( + "cargo", + "", + p.Name, + p.Version, + nil, + "", + ).ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/catalog.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/catalog.go new file mode 100644 index 0000000000000000000000000000000000000000..7dfff5126d0a8ed92ef4a029077fbf1a26a8cd12 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/catalog.go @@ -0,0 +1,220 @@ +package pkg + +import ( + "sort" + "sync" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/jinzhu/copier" +) + +type orderedIDSet struct { + slice []artifact.ID +} + +func (s *orderedIDSet) add(ids ...artifact.ID) { +loopNewIDs: + for _, newID := range ids { + for _, existingID := range s.slice { + if existingID == newID { + continue loopNewIDs + } + } + s.slice = append(s.slice, newID) + } +} + +// Catalog represents a collection of Packages. +type Catalog struct { + byID map[artifact.ID]Package + idsByName map[string]orderedIDSet + idsByType map[Type]orderedIDSet + idsByPath map[string]orderedIDSet // note: this is real path or virtual path + lock sync.RWMutex +} + +// NewCatalog returns a new empty Catalog +func NewCatalog(pkgs ...Package) *Catalog { + catalog := Catalog{ + byID: make(map[artifact.ID]Package), + idsByName: make(map[string]orderedIDSet), + idsByType: make(map[Type]orderedIDSet), + idsByPath: make(map[string]orderedIDSet), + } + + for _, p := range pkgs { + catalog.Add(p) + } + + return &catalog +} + +// PackageCount returns the total number of packages that have been added. +func (c *Catalog) PackageCount() int { + return len(c.byID) +} + +// Package returns the package with the given ID. +func (c *Catalog) Package(id artifact.ID) *Package { + v, exists := c.byID[id] + if !exists { + return nil + } + var p Package + if err := copier.Copy(&p, &v); err != nil { + log.Warnf("unable to copy package id=%q name=%q: %+v", id, v.Name, err) + return nil + } + p.id = v.id + return &p +} + +// PackagesByPath returns all packages that were discovered from the given path. +func (c *Catalog) PackagesByPath(path string) []Package { + return c.Packages(c.idsByPath[path].slice) +} + +// PackagesByName returns all packages that were discovered with a matching name. +func (c *Catalog) PackagesByName(name string) []Package { + return c.Packages(c.idsByName[name].slice) +} + +// Packages returns all packages for the given ID. +func (c *Catalog) Packages(ids []artifact.ID) (result []Package) { + for _, i := range ids { + p, exists := c.byID[i] + if exists { + result = append(result, p) + } + } + return result +} + +// Add a package to the Catalog. +func (c *Catalog) Add(p Package) { + c.lock.Lock() + defer c.lock.Unlock() + + id := p.ID() + if id == "" { + log.Warnf("found package with empty ID while adding to the catalog: %+v", p) + p.SetID() + id = p.ID() + } + + if existing, exists := c.byID[id]; exists { + // there is already a package with this fingerprint merge the existing record with the new one + if err := existing.merge(p); err != nil { + log.Warnf("failed to merge packages: %+v", err) + } else { + c.addPathsToIndex(p) + } + return + } + + c.addToIndex(p) +} + +func (c *Catalog) addToIndex(p Package) { + c.byID[p.id] = p + c.addNameToIndex(p) + c.addTypeToIndex(p) + c.addPathsToIndex(p) +} + +func (c *Catalog) addNameToIndex(p Package) { + nameIndex := c.idsByName[p.Name] + nameIndex.add(p.id) + c.idsByName[p.Name] = nameIndex +} + +func (c *Catalog) addTypeToIndex(p Package) { + typeIndex := c.idsByType[p.Type] + typeIndex.add(p.id) + c.idsByType[p.Type] = typeIndex +} + +func (c *Catalog) addPathsToIndex(p Package) { + observedPaths := internal.NewStringSet() + for _, l := range p.Locations.ToSlice() { + if l.RealPath != "" && !observedPaths.Contains(l.RealPath) { + c.addPathToIndex(p.id, l.RealPath) + observedPaths.Add(l.RealPath) + } + if l.VirtualPath != "" && l.RealPath != l.VirtualPath && !observedPaths.Contains(l.VirtualPath) { + c.addPathToIndex(p.id, l.VirtualPath) + observedPaths.Add(l.VirtualPath) + } + } +} + +func (c *Catalog) addPathToIndex(id artifact.ID, path string) { + pathIndex := c.idsByPath[path] + pathIndex.add(id) + c.idsByPath[path] = pathIndex +} + +// Enumerate all packages for the given type(s), enumerating all packages if no type is specified. +func (c *Catalog) Enumerate(types ...Type) <-chan Package { + channel := make(chan Package) + go func() { + defer close(channel) + if c == nil { + // we should allow enumerating from a catalog that was never created (which will result in no packages enumerated) + return + } + for ty, ids := range c.idsByType { + if len(types) != 0 { + found := false + typeCheck: + for _, t := range types { + if t == ty { + found = true + break typeCheck + } + } + if !found { + continue + } + } + for _, id := range ids.slice { + p := c.Package(id) + if p != nil { + channel <- *p + } + } + } + }() + return channel +} + +// Sorted enumerates all packages for the given types sorted by package name. Enumerates all packages if no type +// is specified. +func (c *Catalog) Sorted(types ...Type) (pkgs []Package) { + for p := range c.Enumerate(types...) { + pkgs = append(pkgs, p) + } + + sort.SliceStable(pkgs, func(i, j int) bool { + if pkgs[i].Name == pkgs[j].Name { + if pkgs[i].Version == pkgs[j].Version { + iLocations := pkgs[i].Locations.ToSlice() + jLocations := pkgs[j].Locations.ToSlice() + if pkgs[i].Type == pkgs[j].Type && len(iLocations) > 0 && len(jLocations) > 0 { + if iLocations[0].String() == jLocations[0].String() { + // compare IDs as a final fallback + return pkgs[i].ID() < pkgs[j].ID() + } + return iLocations[0].String() < jLocations[0].String() + } + return pkgs[i].Type < pkgs[j].Type + } + return pkgs[i].Version < pkgs[j].Version + } + return pkgs[i].Name < pkgs[j].Name + }) + + return pkgs +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/catalog_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/catalog_test.go new file mode 100644 index 0000000000000000000000000000000000000000..43f52b87bd13b25cc72bdd43255d203c3e4197a1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/catalog_test.go @@ -0,0 +1,274 @@ +package pkg + +import ( + "testing" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/source" + "github.com/scylladb/go-set/strset" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +type expectedIndexes struct { + byType map[Type]*strset.Set + byPath map[string]*strset.Set +} + +func TestCatalogAddPopulatesIndex(t *testing.T) { + + var pkgs = []Package{ + { + Locations: source.NewLocationSet( + source.NewVirtualLocation("/a/path", "/another/path"), + source.NewVirtualLocation("/b/path", "/bee/path"), + ), + Type: RpmPkg, + }, + { + Locations: source.NewLocationSet( + source.NewVirtualLocation("/c/path", "/another/path"), + source.NewVirtualLocation("/d/path", "/another/path"), + ), + Type: NpmPkg, + }, + } + + for i := range pkgs { + p := &pkgs[i] + p.SetID() + } + + fixtureID := func(i int) string { + return string(pkgs[i].ID()) + } + + tests := []struct { + name string + expectedIndexes expectedIndexes + }{ + { + name: "vanilla-add", + expectedIndexes: expectedIndexes{ + byType: map[Type]*strset.Set{ + RpmPkg: strset.New(fixtureID(0)), + NpmPkg: strset.New(fixtureID(1)), + }, + byPath: map[string]*strset.Set{ + "/another/path": strset.New(fixtureID(0), fixtureID(1)), + "/a/path": strset.New(fixtureID(0)), + "/b/path": strset.New(fixtureID(0)), + "/bee/path": strset.New(fixtureID(0)), + "/c/path": strset.New(fixtureID(1)), + "/d/path": strset.New(fixtureID(1)), + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + c := NewCatalog(pkgs...) + + assertIndexes(t, c, test.expectedIndexes) + + }) + } +} + +func assertIndexes(t *testing.T, c *Catalog, expectedIndexes expectedIndexes) { + // assert path index + assert.Len(t, c.idsByPath, len(expectedIndexes.byPath), "unexpected path index length") + for path, expectedIds := range expectedIndexes.byPath { + actualIds := strset.New() + for _, p := range c.PackagesByPath(path) { + actualIds.Add(string(p.ID())) + } + + if !expectedIds.IsEqual(actualIds) { + t.Errorf("mismatched IDs for path=%q : %+v", path, strset.SymmetricDifference(actualIds, expectedIds)) + } + } + + // assert type index + assert.Len(t, c.idsByType, len(expectedIndexes.byType), "unexpected type index length") + for ty, expectedIds := range expectedIndexes.byType { + actualIds := strset.New() + for p := range c.Enumerate(ty) { + actualIds.Add(string(p.ID())) + } + + if !expectedIds.IsEqual(actualIds) { + t.Errorf("mismatched IDs for type=%q : %+v", ty, strset.SymmetricDifference(actualIds, expectedIds)) + } + } +} + +func TestCatalog_PathIndexDeduplicatesRealVsVirtualPaths(t *testing.T) { + p1 := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/b/path", "/another/path"), + source.NewVirtualLocation("/b/path", "/b/path"), + ), + Type: RpmPkg, + Name: "Package-1", + } + + p2 := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/b/path", "/b/path"), + ), + Type: RpmPkg, + Name: "Package-2", + } + p2Dup := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/b/path", "/another/path"), + source.NewVirtualLocation("/b/path", "/c/path/b/dup"), + ), + Type: RpmPkg, + Name: "Package-2", + } + + tests := []struct { + name string + pkgs []Package + paths []string + }{ + { + name: "multiple locations with shared path", + pkgs: []Package{p1}, + paths: []string{ + "/b/path", + "/another/path", + }, + }, + { + name: "one location with shared path", + pkgs: []Package{p2}, + paths: []string{ + "/b/path", + }, + }, + { + name: "two instances with similar locations", + pkgs: []Package{p2, p2Dup}, + paths: []string{ + "/b/path", + "/another/path", + "/c/path/b/dup", // this updated the path index on merge + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + for _, path := range test.paths { + actualPackages := NewCatalog(test.pkgs...).PackagesByPath(path) + require.Len(t, actualPackages, 1) + } + }) + } + +} + +func TestCatalog_MergeRecords(t *testing.T) { + var tests = []struct { + name string + pkgs []Package + expectedLocations []source.Location + }{ + { + name: "multiple Locations with shared path", + pkgs: []Package{ + { + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/b/path", + FileSystemID: "a", + }, + VirtualPath: "/another/path", + }, + ), + Type: RpmPkg, + }, + { + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/b/path", + FileSystemID: "b", + }, + VirtualPath: "/another/path", + }, + ), + Type: RpmPkg, + }, + }, + expectedLocations: []source.Location{ + { + Coordinates: source.Coordinates{ + RealPath: "/b/path", + FileSystemID: "a", + }, + VirtualPath: "/another/path", + }, + { + Coordinates: source.Coordinates{ + RealPath: "/b/path", + FileSystemID: "b", + }, + VirtualPath: "/another/path", + }, + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + actual := NewCatalog(tt.pkgs...).PackagesByPath("/b/path") + require.Len(t, actual, 1) + assert.Equal(t, tt.expectedLocations, actual[0].Locations.ToSlice()) + }) + } +} + +func TestCatalog_EnumerateNilCatalog(t *testing.T) { + var c *Catalog + assert.Empty(t, c.Enumerate()) +} + +func Test_idOrderedSet_add(t *testing.T) { + tests := []struct { + name string + input []artifact.ID + expected []artifact.ID + }{ + { + name: "elements deduplicated when added", + input: []artifact.ID{ + "1", "2", "3", "4", "1", "2", "3", "4", "1", "2", "3", "4", + }, + expected: []artifact.ID{ + "1", "2", "3", "4", + }, + }, + { + name: "elements retain ordering when added", + input: []artifact.ID{ + "4", "3", "2", "1", + }, + expected: []artifact.ID{ + "4", "3", "2", "1", + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + var s orderedIDSet + s.add(tt.input...) + assert.Equal(t, tt.expected, s.slice) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..87a7b285e89d792c769803b90ee67ae79c970901 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/cataloger.go @@ -0,0 +1,48 @@ +package alpm + +import ( + "fmt" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +const catalogerName = "alpmdb-cataloger" + +type Cataloger struct{} + +// NewAlpmdbCataloger returns a new ALPM DB cataloger object. +func NewAlpmdbCataloger() *Cataloger { + return &Cataloger{} +} + +// Name returns a string that uniquely describes a cataloger +func (c *Cataloger) Name() string { + return catalogerName +} + +// Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing rpm db installation. +func (c *Cataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + fileMatches, err := resolver.FilesByGlob(pkg.AlpmDBGlob) + if err != nil { + return nil, nil, fmt.Errorf("failed to find rpmdb's by glob: %w", err) + } + + var pkgs []pkg.Package + for _, location := range fileMatches { + dbContentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + return nil, nil, err + } + + discoveredPkgs, err := parseAlpmDB(resolver, location.RealPath, dbContentReader) + internal.CloseAndLogError(dbContentReader, location.VirtualPath) + if err != nil { + return nil, nil, fmt.Errorf("unable to catalog package=%+v: %w", location.RealPath, err) + } + pkgs = append(pkgs, discoveredPkgs...) + } + return pkgs, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/parse_alpm_db.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/parse_alpm_db.go new file mode 100644 index 0000000000000000000000000000000000000000..5125cc1d5f6a4a09fe19579be5f5061e8bf341b5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/parse_alpm_db.go @@ -0,0 +1,245 @@ +package alpm + +import ( + "bufio" + "compress/gzip" + "fmt" + "io" + "path/filepath" + "strconv" + "strings" + "time" + + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/mitchellh/mapstructure" + "github.com/vbatts/go-mtree" +) + +var ( + ignoredFiles = map[string]bool{ + "/set": true, + ".BUILDINFO": true, + ".PKGINFO": true, + "": true, + } +) + +func newAlpmDBPackage(d *pkg.AlpmMetadata) *pkg.Package { + return &pkg.Package{ + Name: d.Package, + Version: d.Version, + FoundBy: catalogerName, + Type: "alpm", + Licenses: strings.Split(d.License, " "), + MetadataType: pkg.AlpmMetadataType, + Metadata: *d, + } +} + +func newScanner(reader io.Reader) *bufio.Scanner { + // This is taken from the apk parser + // https://github.com/anchore/syft/blob/v0.47.0/syft/pkg/cataloger/apkdb/parse_apk_db.go#L37 + const maxScannerCapacity = 1024 * 1024 + bufScan := make([]byte, maxScannerCapacity) + scanner := bufio.NewScanner(reader) + scanner.Buffer(bufScan, maxScannerCapacity) + onDoubleLF := func(data []byte, atEOF bool) (advance int, token []byte, err error) { + for i := 0; i < len(data); i++ { + if i > 0 && data[i-1] == '\n' && data[i] == '\n' { + return i + 1, data[:i-1], nil + } + } + if !atEOF { + return 0, nil, nil + } + // deliver the last token (which could be an empty string) + return 0, data, bufio.ErrFinalToken + } + + scanner.Split(onDoubleLF) + return scanner +} + +func getFileReader(path string, resolver source.FileResolver) (io.Reader, error) { + locs, err := resolver.FilesByPath(path) + if err != nil { + return nil, err + } + // TODO: Should we maybe check if we found the file + dbContentReader, err := resolver.FileContentsByLocation(locs[0]) + if err != nil { + return nil, err + } + return dbContentReader, nil +} + +//nolint:funlen +func parseDatabase(b *bufio.Scanner) (*pkg.AlpmMetadata, error) { + var entry pkg.AlpmMetadata + var err error + pkgFields := make(map[string]interface{}) + for b.Scan() { + fields := strings.SplitN(b.Text(), "\n", 2) + + // End of File + if len(fields) == 1 { + break + } + + // The alpm database surrounds the keys with %. + key := strings.ReplaceAll(fields[0], "%", "") + key = strings.ToLower(key) + value := strings.TrimSpace(fields[1]) + + switch key { + case "files": + var files []map[string]string + for _, f := range strings.Split(value, "\n") { + path := fmt.Sprintf("/%s", f) + if ok := ignoredFiles[path]; !ok { + files = append(files, map[string]string{"path": path}) + } + } + pkgFields[key] = files + case "backup": + var backup []map[string]interface{} + for _, f := range strings.Split(value, "\n") { + fields := strings.SplitN(f, "\t", 2) + path := fmt.Sprintf("/%s", fields[0]) + if ok := ignoredFiles[path]; !ok { + backup = append(backup, map[string]interface{}{ + "path": path, + "digests": []file.Digest{{ + Algorithm: "md5", + Value: fields[1], + }}}) + } + } + pkgFields[key] = backup + case "reason": + fallthrough + case "size": + pkgFields[key], err = strconv.ParseInt(value, 10, 64) + if err != nil { + return nil, fmt.Errorf("failed to parse %s to integer", value) + } + default: + pkgFields[key] = value + } + } + if err := mapstructure.Decode(pkgFields, &entry); err != nil { + return nil, fmt.Errorf("unable to parse ALPM metadata: %w", err) + } + if entry.Package == "" && len(entry.Files) == 0 && len(entry.Backup) == 0 { + return nil, nil + } + + if entry.Backup == nil { + entry.Backup = make([]pkg.AlpmFileRecord, 0) + } + return &entry, nil +} + +func parseMtree(r io.Reader) ([]pkg.AlpmFileRecord, error) { + var err error + var entries []pkg.AlpmFileRecord + + r, err = gzip.NewReader(r) + if err != nil { + return nil, err + } + specDh, err := mtree.ParseSpec(r) + if err != nil { + return nil, err + } + for _, f := range specDh.Entries { + var entry pkg.AlpmFileRecord + entry.Digests = make([]file.Digest, 0) + fileFields := make(map[string]interface{}) + if ok := ignoredFiles[f.Name]; ok { + continue + } + path := fmt.Sprintf("/%s", f.Name) + fileFields["path"] = path + for _, kv := range f.Keywords { + kw := string(kv.Keyword()) + switch kw { + case "time": + // All unix timestamps have a .0 suffixs. + v := strings.Split(kv.Value(), ".") + i, _ := strconv.ParseInt(v[0], 10, 64) + tm := time.Unix(i, 0) + fileFields[kw] = tm + case "sha256digest": + entry.Digests = append(entry.Digests, file.Digest{ + Algorithm: "sha256", + Value: kv.Value(), + }) + case "md5digest": + entry.Digests = append(entry.Digests, file.Digest{ + Algorithm: "md5digest", + Value: kv.Value(), + }) + default: + fileFields[kw] = kv.Value() + } + } + if err := mapstructure.Decode(fileFields, &entry); err != nil { + return nil, fmt.Errorf("unable to parse ALPM mtree data: %w", err) + } + entries = append(entries, entry) + } + return entries, nil +} + +func parseAlpmDBEntry(reader io.Reader) (*pkg.AlpmMetadata, error) { + scanner := newScanner(reader) + metadata, err := parseDatabase(scanner) + if err != nil { + return nil, err + } + if metadata == nil { + return nil, nil + } + return metadata, nil +} + +func parseAlpmDB(resolver source.FileResolver, desc string, reader io.Reader) ([]pkg.Package, error) { + metadata, err := parseAlpmDBEntry(reader) + if err != nil { + return nil, err + } + + base := filepath.Dir(desc) + mtree := filepath.Join(base, "mtree") + r, err := getFileReader(mtree, resolver) + if err != nil { + return nil, err + } + pkgFiles, err := parseMtree(r) + if err != nil { + return nil, err + } + // The replace the files found the the pacman database with the files from the mtree These contain more metadata and + // thus more useful. + metadata.Files = pkgFiles + + // We only really do this to get any backup database entries from the files database + files := filepath.Join(base, "files") + _, err = getFileReader(files, resolver) + if err != nil { + return nil, err + } + filesMetadata, err := parseAlpmDBEntry(reader) + if err != nil { + return nil, err + } else if filesMetadata != nil { + metadata.Backup = filesMetadata.Backup + } + + p := *newAlpmDBPackage(metadata) + p.SetID() + return []pkg.Package{p}, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/parse_alpm_db_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/parse_alpm_db_test.go new file mode 100644 index 0000000000000000000000000000000000000000..fd5e28a0cacb306a64e2a7f85fc5b2a5a3cafb73 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/parse_alpm_db_test.go @@ -0,0 +1,195 @@ +package alpm + +import ( + "bufio" + "os" + "testing" + "time" + + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestDatabaseParser(t *testing.T) { + tests := []struct { + name string + expected pkg.AlpmMetadata + }{ + { + name: "test alpm database parsing", + expected: pkg.AlpmMetadata{ + Backup: []pkg.AlpmFileRecord{ + { + Path: "/etc/pacman.conf", + Digests: []file.Digest{{ + Algorithm: "md5", + Value: "de541390e52468165b96511c4665bff4", + }}, + }, + { + Path: "/etc/makepkg.conf", + Digests: []file.Digest{{ + Algorithm: "md5", + Value: "79fce043df7dfc676ae5ecb903762d8b", + }}, + }, + }, + Files: []pkg.AlpmFileRecord{ + { + Path: "/etc/", + }, + { + Path: "/etc/makepkg.conf", + }, + { + Path: "/etc/pacman.conf", + }, + { + Path: "/usr/", + }, + { + Path: "/usr/bin/", + }, + { + Path: "/usr/bin/makepkg", + }, + { + Path: "/usr/bin/makepkg-template", + }, + { + Path: "/usr/bin/pacman", + }, + { + Path: "/usr/bin/pacman-conf", + }, + { + Path: "/var/", + }, + { + Path: "/var/cache/", + }, + { + Path: "/var/cache/pacman/", + }, + { + Path: "/var/cache/pacman/pkg/", + }, + { + Path: "/var/lib/", + }, + { + Path: "/var/lib/pacman/", + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + file, err := os.Open("test-fixtures/files") + if err != nil { + t.Fatal("Unable to read test-fixtures/file: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + reader := bufio.NewReader(file) + + entry, err := parseAlpmDBEntry(reader) + if err != nil { + t.Fatal("Unable to read file contents: ", err) + } + + if diff := deep.Equal(entry.Files, test.expected.Files); diff != nil { + for _, d := range diff { + t.Errorf("files diff: %+v", d) + } + } + if diff := deep.Equal(entry.Backup, test.expected.Backup); diff != nil { + for _, d := range diff { + t.Errorf("backup diff: %+v", d) + } + } + }) + } +} + +func parseTime(stime string) time.Time { + t, _ := time.Parse(time.RFC3339, stime) + return t +} + +func TestMtreeParse(t *testing.T) { + tests := []struct { + name string + expected []pkg.AlpmFileRecord + }{ + { + name: "test mtree parsing", + expected: []pkg.AlpmFileRecord{ + { + Path: "/etc", + Type: "dir", + Time: parseTime("2022-04-10T14:59:52+02:00"), + Digests: make([]file.Digest, 0), + }, + { + Path: "/etc/pacman.d", + Type: "dir", + Time: parseTime("2022-04-10T14:59:52+02:00"), + Digests: make([]file.Digest, 0), + }, + { + Path: "/etc/pacman.d/mirrorlist", + Size: "44683", + Time: parseTime("2022-04-10T14:59:52+02:00"), + Digests: []file.Digest{ + { + Algorithm: "md5digest", + Value: "81c39827e38c759d7e847f05db62c233", + }, + { + Algorithm: "sha256", + Value: "fc135ab26f2a227b9599b66a2f1ba325c445acb914d60e7ecf6e5997a87abe1e", + }, + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + file, err := os.Open("test-fixtures/mtree") + if err != nil { + t.Fatal("Unable to read test-fixtures/mtree: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + reader := bufio.NewReader(file) + + entry, err := parseMtree(reader) + if err != nil { + t.Fatal("Unable to read file contents: ", err) + } + + if diff := deep.Equal(entry, test.expected); diff != nil { + for _, d := range diff { + t.Errorf("files diff: %+v", d) + } + } + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/test-fixtures/files b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/test-fixtures/files new file mode 100644 index 0000000000000000000000000000000000000000..5e1b9326e4ec561833f209d245ec96c6d4cd547b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/test-fixtures/files @@ -0,0 +1,20 @@ +%FILES% +etc/ +etc/makepkg.conf +etc/pacman.conf +usr/ +usr/bin/ +usr/bin/makepkg +usr/bin/makepkg-template +usr/bin/pacman +usr/bin/pacman-conf +var/ +var/cache/ +var/cache/pacman/ +var/cache/pacman/pkg/ +var/lib/ +var/lib/pacman/ + +%BACKUP% +etc/pacman.conf de541390e52468165b96511c4665bff4 +etc/makepkg.conf 79fce043df7dfc676ae5ecb903762d8b diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/test-fixtures/mtree b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/test-fixtures/mtree new file mode 100644 index 0000000000000000000000000000000000000000..adf8cc4bb08834e2a1f924f04dc0f79ddf3e8e5c Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/alpm/test-fixtures/mtree differ diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..f82aef79889868e8c059546441beff41da559952 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/cataloger.go @@ -0,0 +1,18 @@ +/* +Package apkdb provides a concrete Cataloger implementation for Alpine DB files. +*/ +package apkdb + +import ( + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewApkdbCataloger returns a new Alpine DB cataloger object. +func NewApkdbCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + pkg.ApkDBGlob: parseApkDB, + } + + return common.NewGenericCataloger(nil, globParsers, "apkdb-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/parse_apk_db.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/parse_apk_db.go new file mode 100644 index 0000000000000000000000000000000000000000..34038f2ab65636e829f698340528cebf90dbc329 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/parse_apk_db.go @@ -0,0 +1,164 @@ +package apkdb + +import ( + "bufio" + "fmt" + "io" + "path" + "strconv" + "strings" + + "github.com/anchore/syft/syft/artifact" + + "github.com/anchore/syft/syft/file" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "github.com/mitchellh/mapstructure" +) + +// integrity check +var _ common.ParserFn = parseApkDB + +func newApkDBPackage(d *pkg.ApkMetadata) *pkg.Package { + return &pkg.Package{ + Name: d.Package, + Version: d.Version, + Licenses: strings.Split(d.License, " "), + Type: pkg.ApkPkg, + MetadataType: pkg.ApkMetadataType, + Metadata: *d, + } +} + +// parseApkDb parses individual packages from a given Alpine DB file. For more information on specific fields +// see https://wiki.alpinelinux.org/wiki/Apk_spec . +func parseApkDB(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + // larger capacity for the scanner. + const maxScannerCapacity = 1024 * 1024 + // a new larger buffer for the scanner + bufScan := make([]byte, maxScannerCapacity) + packages := make([]*pkg.Package, 0) + + scanner := bufio.NewScanner(reader) + scanner.Buffer(bufScan, maxScannerCapacity) + onDoubleLF := func(data []byte, atEOF bool) (advance int, token []byte, err error) { + for i := 0; i < len(data); i++ { + if i > 0 && data[i-1] == '\n' && data[i] == '\n' { + return i + 1, data[:i-1], nil + } + } + if !atEOF { + return 0, nil, nil + } + // deliver the last token (which could be an empty string) + return 0, data, bufio.ErrFinalToken + } + + scanner.Split(onDoubleLF) + for scanner.Scan() { + metadata, err := parseApkDBEntry(strings.NewReader(scanner.Text())) + if err != nil { + return nil, nil, err + } + if metadata != nil { + packages = append(packages, newApkDBPackage(metadata)) + } + } + + if err := scanner.Err(); err != nil { + return nil, nil, fmt.Errorf("failed to parse APK DB file: %w", err) + } + + return packages, nil, nil +} + +// parseApkDBEntry reads and parses a single pkg.ApkMetadata element from the stream, returning nil if their are no more entries. +// +//nolint:funlen +func parseApkDBEntry(reader io.Reader) (*pkg.ApkMetadata, error) { + var entry pkg.ApkMetadata + pkgFields := make(map[string]interface{}) + files := make([]pkg.ApkFileRecord, 0) + + var fileRecord *pkg.ApkFileRecord + lastFile := "/" + + scanner := bufio.NewScanner(reader) + for scanner.Scan() { + line := scanner.Text() + fields := strings.SplitN(line, ":", 2) + if len(fields) != 2 { + continue + } + + key := fields[0] + value := strings.TrimSpace(fields[1]) + + switch key { + case "F": + currentFile := "/" + value + + newFileRecord := pkg.ApkFileRecord{ + Path: currentFile, + } + files = append(files, newFileRecord) + fileRecord = &files[len(files)-1] + + // future aux references are relative to previous "F" records + lastFile = currentFile + continue + case "R": + newFileRecord := pkg.ApkFileRecord{ + Path: path.Join(lastFile, value), + } + files = append(files, newFileRecord) + fileRecord = &files[len(files)-1] + case "a", "M": + ownershipFields := strings.Split(value, ":") + if len(ownershipFields) < 3 { + log.Warnf("unexpected APK ownership field: %q", value) + continue + } + if fileRecord == nil { + log.Warnf("ownership field with no parent record: %q", value) + continue + } + fileRecord.OwnerUID = ownershipFields[0] + fileRecord.OwnerGID = ownershipFields[1] + fileRecord.Permissions = ownershipFields[2] + // note: there are more optional fields available that we are not capturing, e.g.: + // "0:0:755:Q1JaDEHQHBbizhEzoWK1YxuraNU/4=" + case "Z": + if fileRecord == nil { + log.Warnf("checksum field with no parent record: %q", value) + continue + } + fileRecord.Digest = &file.Digest{ + Algorithm: "sha1", + Value: value, + } + case "I", "S": + // coerce to integer + iVal, err := strconv.Atoi(value) + if err != nil { + return nil, fmt.Errorf("failed to parse APK int: '%+v'", value) + } + pkgFields[key] = iVal + default: + pkgFields[key] = value + } + } + + if err := mapstructure.Decode(pkgFields, &entry); err != nil { + return nil, fmt.Errorf("unable to parse APK metadata: %w", err) + } + if entry.Package == "" { + return nil, nil + } + + entry.Files = files + + return &entry, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/parse_apk_db_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/parse_apk_db_test.go new file mode 100644 index 0000000000000000000000000000000000000000..958c1f8709a30de46e500df7739f3e7927f2b8df --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/parse_apk_db_test.go @@ -0,0 +1,798 @@ +package apkdb + +import ( + "bufio" + "os" + "testing" + + "github.com/anchore/syft/syft/file" + + "github.com/go-test/deep" + + "github.com/anchore/syft/syft/pkg" +) + +func TestExtraFileAttributes(t *testing.T) { + tests := []struct { + name string + expected pkg.ApkMetadata + }{ + { + name: "test extra file attributes (checksum) are ignored", + expected: pkg.ApkMetadata{ + Files: []pkg.ApkFileRecord{ + { + Path: "/usr", + }, + { + Path: "/usr/lib", + }, + { + Path: "/usr/lib/jvm", + }, + { + Path: "/usr/lib/jvm/java-1.8-openjdk", + }, + { + Path: "/usr/lib/jvm/java-1.8-openjdk/bin", + }, + { + Path: "/usr/lib/jvm/java-1.8-openjdk/bin/policytool", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1M0C9qfC/+kdRiOodeihG2GMRtkE=", + }, + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + file, err := os.Open("test-fixtures/extra-file-attributes") + if err != nil { + t.Fatal("Unable to read test-fixtures/extra-file-attributes: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + reader := bufio.NewReader(file) + + entry, err := parseApkDBEntry(reader) + if err != nil { + t.Fatal("Unable to read file contents: ", err) + } + + if diff := deep.Equal(entry.Files, test.expected.Files); diff != nil { + for _, d := range diff { + t.Errorf("diff: %+v", d) + } + } + }) + } +} + +func TestSinglePackageDetails(t *testing.T) { + tests := []struct { + fixture string + expected pkg.ApkMetadata + }{ + { + fixture: "test-fixtures/single", + expected: pkg.ApkMetadata{ + Package: "musl-utils", + OriginPackage: "musl", + Version: "1.1.24-r2", + Description: "the musl c library (libc) implementation", + Maintainer: "Timo Teräs ", + License: "MIT BSD GPL2+", + Architecture: "x86_64", + URL: "https://musl.libc.org/", + Size: 37944, + InstalledSize: 151552, + PullDependencies: "scanelf so:libc.musl-x86_64.so.1", + PullChecksum: "Q1bTtF5526tETKfL+lnigzIDvm+2o=", + GitCommitOfAport: "4024cc3b29ad4c65544ad068b8f59172b5494306", + Files: []pkg.ApkFileRecord{ + { + Path: "/sbin", + }, + { + Path: "/sbin/ldconfig", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1Kja2+POZKxEkUOZqwSjC6kmaED4=", + }, + }, + { + Path: "/usr", + }, + { + Path: "/usr/bin", + }, + { + Path: "/usr/bin/iconv", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1CVmFbdY+Hv6/jAHl1gec2Kbx1EY=", + }, + }, + { + Path: "/usr/bin/ldd", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1yFAhGggmL7ERgbIA7KQxyTzf3ks=", + }, + }, + { + Path: "/usr/bin/getconf", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1dAdYK8M/INibRQF5B3Rw7cmNDDA=", + }, + }, + { + Path: "/usr/bin/getent", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1eR2Dz/WylabgbWMTkd2+hGmEya4=", + }, + }, + }, + }, + }, + { + fixture: "test-fixtures/base", + expected: pkg.ApkMetadata{ + Package: "alpine-baselayout", + OriginPackage: "alpine-baselayout", + Version: "3.2.0-r6", + Description: "Alpine base dir structure and init scripts", + Maintainer: "Natanael Copa ", + License: "GPL-2.0-only", + Architecture: "x86_64", + URL: "https://git.alpinelinux.org/cgit/aports/tree/main/alpine-baselayout", + Size: 19917, + InstalledSize: 409600, + PullDependencies: "/bin/sh so:libc.musl-x86_64.so.1", + PullChecksum: "Q1myMNfd7u5v5UTgNHeq1e31qTjZU=", + GitCommitOfAport: "e1c51734fa96fa4bac92e9f14a474324c67916fc", + Files: []pkg.ApkFileRecord{ + { + Path: "/dev", + }, + { + Path: "/dev/pts", + }, + { + Path: "/dev/shm", + }, + { + Path: "/etc", + }, + { + Path: "/etc/fstab", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q11Q7hNe8QpDS531guqCdrXBzoA/o=", + }, + }, + { + Path: "/etc/group", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1oJ16xWudgKOrXIEquEDzlF2Lsm4=", + }, + }, + { + Path: "/etc/hostname", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q16nVwYVXP/tChvUPdukVD2ifXOmc=", + }, + }, + { + Path: "/etc/hosts", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1BD6zJKZTRWyqGnPi4tSfd3krsMU=", + }, + }, + { + Path: "/etc/inittab", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1TsthbhW7QzWRe1E/NKwTOuD4pHc=", + }, + }, + { + Path: "/etc/modules", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1toogjUipHGcMgECgPJX64SwUT1M=", + }, + }, + { + Path: "/etc/motd", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1XmduVVNURHQ27TvYp1Lr5TMtFcA=", + }, + }, + { + Path: "/etc/mtab", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "777", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1kiljhXXH1LlQroHsEJIkPZg2eiw=", + }, + }, + { + Path: "/etc/passwd", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1TchuuLUfur0izvfZQZxgN/LJhB8=", + }, + }, + { + Path: "/etc/profile", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1KpFb8kl5LvwXWlY3e58FNsjrI34=", + }, + }, + { + Path: "/etc/protocols", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q13FqXUnvuOpMDrH/6rehxuYAEE34=", + }, + }, + { + Path: "/etc/services", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1C6HJNgQvLWqt5VY+n7MZJ1rsDuY=", + }, + }, + { + Path: "/etc/shadow", + OwnerUID: "0", + OwnerGID: "42", + Permissions: "640", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1ltrPIAW2zHeDiajsex2Bdmq3uqA=", + }, + }, + { + Path: "/etc/shells", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1ojm2YdpCJ6B/apGDaZ/Sdb2xJkA=", + }, + }, + { + Path: "/etc/sysctl.conf", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q14upz3tfnNxZkIEsUhWn7Xoiw96g=", + }, + }, + { + Path: "/etc/apk", + }, + { + Path: "/etc/conf.d", + }, + { + Path: "/etc/crontabs", + }, + { + Path: "/etc/crontabs/root", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "600", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1vfk1apUWI4yLJGhhNRd0kJixfvY=", + }, + }, + { + Path: "/etc/init.d", + }, + { + Path: "/etc/modprobe.d", + }, + { + Path: "/etc/modprobe.d/aliases.conf", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1WUbh6TBYNVK7e4Y+uUvLs/7viqk=", + }, + }, + { + Path: "/etc/modprobe.d/blacklist.conf", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1xxYGU6S6TLQvb7ervPrWWwAWqMg=", + }, + }, + { + Path: "/etc/modprobe.d/i386.conf", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1pnay/njn6ol9cCssL7KiZZ8etlc=", + }, + }, + { + Path: "/etc/modprobe.d/kms.conf", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1ynbLn3GYDpvajba/ldp1niayeog=", + }, + }, + { + Path: "/etc/modules-load.d", + }, + { + Path: "/etc/network", + }, + { + Path: "/etc/network/if-down.d", + }, + { + Path: "/etc/network/if-post-down.d", + }, + { + Path: "/etc/network/if-pre-up.d", + }, + { + Path: "/etc/network/if-up.d", + }, + { + Path: "/etc/opt", + }, + { + Path: "/etc/periodic", + }, + { + Path: "/etc/periodic/15min", + }, + { + Path: "/etc/periodic/daily", + }, + { + Path: "/etc/periodic/hourly", + }, + { + Path: "/etc/periodic/monthly", + }, + { + Path: "/etc/periodic/weekly", + }, + { + Path: "/etc/profile.d", + }, + { + Path: "/etc/profile.d/color_prompt", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q10wL23GuSCVfumMRgakabUI6EsSk=", + }, + }, + { + Path: "/etc/profile.d/locale", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1R4bIEpnKxxOSrlnZy9AoawqZ5DU=", + }, + }, + { + Path: "/etc/sysctl.d", + }, + { + Path: "/home", + }, + { + Path: "/lib", + }, + { + Path: "/lib/firmware", + }, + { + Path: "/lib/mdev", + }, + { + Path: "/lib/modules-load.d", + }, + { + Path: "/lib/sysctl.d", + }, + { + Path: "/lib/sysctl.d/00-alpine.conf", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1HpElzW1xEgmKfERtTy7oommnq6c=", + }, + }, + { + Path: "/media", + }, + { + Path: "/media/cdrom", + }, + { + Path: "/media/floppy", + }, + { + Path: "/media/usb", + }, + { + Path: "/mnt", + }, + { + Path: "/opt", + }, + { + Path: "/proc", + }, + { + Path: "/root", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "700", + }, + { + Path: "/run", + }, + { + Path: "/sbin", + }, + { + Path: "/sbin/mkmntdirs", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1YeuSmC7iDbEWrusPzA/zUQF6YSg=", + }, + }, + { + Path: "/srv", + }, + { + Path: "/sys", + }, + { + Path: "/tmp", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "1777", + }, + { + Path: "/usr", + }, + { + Path: "/usr/lib", + }, + { + Path: "/usr/lib/modules-load.d", + }, + { + Path: "/usr/local", + }, + { + Path: "/usr/local/bin", + }, + { + Path: "/usr/local/lib", + }, + { + Path: "/usr/local/share", + }, + { + Path: "/usr/sbin", + }, + { + Path: "/usr/share", + }, + { + Path: "/usr/share/man", + }, + { + Path: "/usr/share/misc", + }, + { + Path: "/var", + }, + { + Path: "/var/run", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "777", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q11/SNZz/8cK2dSKK+cJpVrZIuF4Q=", + }, + }, + { + Path: "/var/cache", + }, + { + Path: "/var/cache/misc", + }, + { + Path: "/var/empty", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "555", + }, + { + Path: "/var/lib", + }, + { + Path: "/var/lib/misc", + }, + { + Path: "/var/local", + }, + { + Path: "/var/lock", + }, + { + Path: "/var/lock/subsys", + }, + { + Path: "/var/log", + }, + { + Path: "/var/mail", + }, + { + Path: "/var/opt", + }, + { + Path: "/var/spool", + }, + { + Path: "/var/spool/mail", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "777", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1dzbdazYZA2nTzSIG3YyNw7d4Juc=", + }, + }, + { + Path: "/var/spool/cron", + }, + { + Path: "/var/spool/cron/crontabs", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "777", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1OFZt+ZMp7j0Gny0rqSKuWJyqYmA=", + }, + }, + { + Path: "/var/tmp", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "1777", + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + file, err := os.Open(test.fixture) + if err != nil { + t.Fatal("Unable to read fixture: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + reader := bufio.NewReader(file) + + entry, err := parseApkDBEntry(reader) + if err != nil { + t.Fatal("Unable to read file contents: ", err) + } + + if diff := deep.Equal(*entry, test.expected); diff != nil { + for _, d := range diff { + t.Errorf("diff: %+v", d) + } + } + }) + } +} + +func TestMultiplePackages(t *testing.T) { + tests := []struct { + fixture string + expected []*pkg.Package + }{ + { + fixture: "test-fixtures/multiple", + expected: []*pkg.Package{ + { + Name: "libc-utils", + Version: "0.7.2-r0", + Licenses: []string{"BSD"}, + Type: pkg.ApkPkg, + MetadataType: pkg.ApkMetadataType, + Metadata: pkg.ApkMetadata{ + Package: "libc-utils", + OriginPackage: "libc-dev", + Maintainer: "Natanael Copa ", + Version: "0.7.2-r0", + License: "BSD", + Architecture: "x86_64", + URL: "http://alpinelinux.org", + Description: "Meta package to pull in correct libc", + Size: 1175, + InstalledSize: 4096, + PullChecksum: "Q1p78yvTLG094tHE1+dToJGbmYzQE=", + GitCommitOfAport: "97b1c2842faa3bfa30f5811ffbf16d5ff9f1a479", + PullDependencies: "musl-utils", + Files: []pkg.ApkFileRecord{}, + }, + }, + { + Name: "musl-utils", + Version: "1.1.24-r2", + Licenses: []string{"MIT", "BSD", "GPL2+"}, + Type: pkg.ApkPkg, + MetadataType: pkg.ApkMetadataType, + Metadata: pkg.ApkMetadata{ + Package: "musl-utils", + OriginPackage: "musl", + Version: "1.1.24-r2", + Description: "the musl c library (libc) implementation", + Maintainer: "Timo Teräs ", + License: "MIT BSD GPL2+", + Architecture: "x86_64", + URL: "https://musl.libc.org/", + Size: 37944, + InstalledSize: 151552, + PullDependencies: "scanelf so:libc.musl-x86_64.so.1", + PullChecksum: "Q1bTtF5526tETKfL+lnigzIDvm+2o=", + GitCommitOfAport: "4024cc3b29ad4c65544ad068b8f59172b5494306", + Files: []pkg.ApkFileRecord{ + { + Path: "/sbin", + }, + { + Path: "/sbin/ldconfig", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1Kja2+POZKxEkUOZqwSjC6kmaED4=", + }, + }, + { + Path: "/usr", + }, + { + Path: "/usr/bin", + }, + { + Path: "/usr/bin/iconv", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1CVmFbdY+Hv6/jAHl1gec2Kbx1EY=", + }, + }, + { + Path: "/usr/bin/ldd", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1yFAhGggmL7ERgbIA7KQxyTzf3ks=", + }, + }, + { + Path: "/usr/bin/getconf", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1dAdYK8M/INibRQF5B3Rw7cmNDDA=", + }, + }, + { + Path: "/usr/bin/getent", + OwnerUID: "0", + OwnerGID: "0", + Permissions: "755", + Digest: &file.Digest{ + Algorithm: "sha1", + Value: "Q1eR2Dz/WylabgbWMTkd2+hGmEya4=", + }, + }, + }, + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + file, err := os.Open(test.fixture) + if err != nil { + t.Fatal("Unable to read: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + // TODO: no relationships are under test yet + pkgs, _, err := parseApkDB(file.Name(), file) + if err != nil { + t.Fatal("Unable to read file contents: ", err) + } + + if len(pkgs) != 2 { + t.Fatalf("unexpected number of entries: %d", len(pkgs)) + } + + for idx, entry := range pkgs { + if diff := deep.Equal(entry, test.expected[idx]); diff != nil { + for _, d := range diff { + t.Errorf("diff: %+v", d) + } + } + } + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/base b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/base new file mode 100644 index 0000000000000000000000000000000000000000..6fc37e44f2a6d0548cb53339864d00774c3ea16a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/base @@ -0,0 +1,149 @@ +C:Q1myMNfd7u5v5UTgNHeq1e31qTjZU= +P:alpine-baselayout +V:3.2.0-r6 +A:x86_64 +S:19917 +I:409600 +T:Alpine base dir structure and init scripts +U:https://git.alpinelinux.org/cgit/aports/tree/main/alpine-baselayout +L:GPL-2.0-only +o:alpine-baselayout +m:Natanael Copa +t:1590679557 +c:e1c51734fa96fa4bac92e9f14a474324c67916fc +D:/bin/sh so:libc.musl-x86_64.so.1 +p:cmd:mkmntdirs +F:dev +F:dev/pts +F:dev/shm +F:etc +R:fstab +Z:Q11Q7hNe8QpDS531guqCdrXBzoA/o= +R:group +Z:Q1oJ16xWudgKOrXIEquEDzlF2Lsm4= +R:hostname +Z:Q16nVwYVXP/tChvUPdukVD2ifXOmc= +R:hosts +Z:Q1BD6zJKZTRWyqGnPi4tSfd3krsMU= +R:inittab +Z:Q1TsthbhW7QzWRe1E/NKwTOuD4pHc= +R:modules +Z:Q1toogjUipHGcMgECgPJX64SwUT1M= +R:motd +Z:Q1XmduVVNURHQ27TvYp1Lr5TMtFcA= +R:mtab +a:0:0:777 +Z:Q1kiljhXXH1LlQroHsEJIkPZg2eiw= +R:passwd +Z:Q1TchuuLUfur0izvfZQZxgN/LJhB8= +R:profile +Z:Q1KpFb8kl5LvwXWlY3e58FNsjrI34= +R:protocols +Z:Q13FqXUnvuOpMDrH/6rehxuYAEE34= +R:services +Z:Q1C6HJNgQvLWqt5VY+n7MZJ1rsDuY= +R:shadow +a:0:42:640 +Z:Q1ltrPIAW2zHeDiajsex2Bdmq3uqA= +R:shells +Z:Q1ojm2YdpCJ6B/apGDaZ/Sdb2xJkA= +R:sysctl.conf +Z:Q14upz3tfnNxZkIEsUhWn7Xoiw96g= +F:etc/apk +F:etc/conf.d +F:etc/crontabs +R:root +a:0:0:600 +Z:Q1vfk1apUWI4yLJGhhNRd0kJixfvY= +F:etc/init.d +F:etc/modprobe.d +R:aliases.conf +Z:Q1WUbh6TBYNVK7e4Y+uUvLs/7viqk= +R:blacklist.conf +Z:Q1xxYGU6S6TLQvb7ervPrWWwAWqMg= +R:i386.conf +Z:Q1pnay/njn6ol9cCssL7KiZZ8etlc= +R:kms.conf +Z:Q1ynbLn3GYDpvajba/ldp1niayeog= +F:etc/modules-load.d +F:etc/network +F:etc/network/if-down.d +F:etc/network/if-post-down.d +F:etc/network/if-pre-up.d +F:etc/network/if-up.d +F:etc/opt +F:etc/periodic +F:etc/periodic/15min +F:etc/periodic/daily +F:etc/periodic/hourly +F:etc/periodic/monthly +F:etc/periodic/weekly +F:etc/profile.d +R:color_prompt +Z:Q10wL23GuSCVfumMRgakabUI6EsSk= +R:locale +Z:Q1R4bIEpnKxxOSrlnZy9AoawqZ5DU= +F:etc/sysctl.d +F:home +F:lib +F:lib/firmware +F:lib/mdev +F:lib/modules-load.d +F:lib/sysctl.d +R:00-alpine.conf +Z:Q1HpElzW1xEgmKfERtTy7oommnq6c= +F:media +F:media/cdrom +F:media/floppy +F:media/usb +F:mnt +F:opt +F:proc +F:root +M:0:0:700 +F:run +F:sbin +R:mkmntdirs +a:0:0:755 +Z:Q1YeuSmC7iDbEWrusPzA/zUQF6YSg= +F:srv +F:sys +F:tmp +M:0:0:1777 +F:usr +F:usr/lib +F:usr/lib/modules-load.d +F:usr/local +F:usr/local/bin +F:usr/local/lib +F:usr/local/share +F:usr/sbin +F:usr/share +F:usr/share/man +F:usr/share/misc +F:var +R:run +a:0:0:777 +Z:Q11/SNZz/8cK2dSKK+cJpVrZIuF4Q= +F:var/cache +F:var/cache/misc +F:var/empty +M:0:0:555 +F:var/lib +F:var/lib/misc +F:var/local +F:var/lock +F:var/lock/subsys +F:var/log +F:var/mail +F:var/opt +F:var/spool +R:mail +a:0:0:777 +Z:Q1dzbdazYZA2nTzSIG3YyNw7d4Juc= +F:var/spool/cron +R:crontabs +a:0:0:777 +Z:Q1OFZt+ZMp7j0Gny0rqSKuWJyqYmA= +F:var/tmp +M:0:0:1777 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/extra-file-attributes b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/extra-file-attributes new file mode 100644 index 0000000000000000000000000000000000000000..0c96d4e0e69a9ed210eadf87a512f4dd4d12e506 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/extra-file-attributes @@ -0,0 +1,22 @@ +P:openjdk8-jre +V:8.212.04-r0 +A:x86_64 +S:359029 +I:970752 +T:OpenJDK 8 Java Runtime +U:https://icedtea.classpath.org/ +L:custom +o:openjdk8 +m:Timo Teras +t:1556993127 +c:46badd1aabd3375ae4b41c7194bc448f74b2ea4a +D:java-cacerts nss so:libX11.so.6 so:libXcomposite.so.1 so:libXext.so.6 so:libXi.so.6 so:libXrender.so.1 so:libXtst.so.6 so:libasound.so.2 so:libc.musl-x86_64.so.1 so:libfreetype.so.6 so:libgcc_s.so.1 so:libgif.so.7 so:libjpeg.so.8 so:libpng16.so.16 so:libstdc++.so.6 so:openjdk8:libawt.so so:openjdk8:libjava.so so:openjdk8:libjli.so so:openjdk8:libjvm.so +p:so:openjdk8:libawt_xawt.so=0 so:openjdk8:libfontmanager.so=0 so:openjdk8:libjawt.so=0 so:openjdk8:libjsoundalsa.so=0 so:openjdk8:libsplashscreen.so=0 +F:usr +F:usr/lib +F:usr/lib/jvm +F:usr/lib/jvm/java-1.8-openjdk +F:usr/lib/jvm/java-1.8-openjdk/bin +R:policytool +a:0:0:755:Q1JaDEHQHBbizhEzoWK1YxuraNU/4= +Z:Q1M0C9qfC/+kdRiOodeihG2GMRtkE= diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/multiple b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/multiple new file mode 100644 index 0000000000000000000000000000000000000000..9ade5ff5abb1e94bce724c24417a65cdb77ca48a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/multiple @@ -0,0 +1,56 @@ +C:Q1p78yvTLG094tHE1+dToJGbmYzQE= +P:libc-utils +V:0.7.2-r0 +A:x86_64 +S:1175 +I:4096 +T:Meta package to pull in correct libc +U:http://alpinelinux.org +L:BSD +o:libc-dev +m:Natanael Copa +t:1575749004 +c:97b1c2842faa3bfa30f5811ffbf16d5ff9f1a479 +D:musl-utils + + + + + + + + +C:Q1bTtF5526tETKfL+lnigzIDvm+2o= +P:musl-utils +V:1.1.24-r2 +A:x86_64 +S:37944 +I:151552 +T:the musl c library (libc) implementation +U:https://musl.libc.org/ +L:MIT BSD GPL2+ +o:musl +m:Timo Teräs +t:1584790550 +c:4024cc3b29ad4c65544ad068b8f59172b5494306 +D:scanelf so:libc.musl-x86_64.so.1 +p:cmd:getconf cmd:getent cmd:iconv cmd:ldconfig cmd:ldd +r:libiconv +F:sbin +R:ldconfig +a:0:0:755 +Z:Q1Kja2+POZKxEkUOZqwSjC6kmaED4= +F:usr +F:usr/bin +R:iconv +a:0:0:755 +Z:Q1CVmFbdY+Hv6/jAHl1gec2Kbx1EY= +R:ldd +a:0:0:755 +Z:Q1yFAhGggmL7ERgbIA7KQxyTzf3ks= +R:getconf +a:0:0:755 +Z:Q1dAdYK8M/INibRQF5B3Rw7cmNDDA= +R:getent +a:0:0:755 +Z:Q1eR2Dz/WylabgbWMTkd2+hGmEya4= \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/single b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/single new file mode 100644 index 0000000000000000000000000000000000000000..5abf4f2237ea94f63fd790a036685e1fb35503c6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/apkdb/test-fixtures/single @@ -0,0 +1,34 @@ +C:Q1bTtF5526tETKfL+lnigzIDvm+2o= +P:musl-utils +V:1.1.24-r2 +A:x86_64 +S:37944 +I:151552 +T:the musl c library (libc) implementation +U:https://musl.libc.org/ +L:MIT BSD GPL2+ +o:musl +m:Timo Teräs +t:1584790550 +c:4024cc3b29ad4c65544ad068b8f59172b5494306 +D:scanelf so:libc.musl-x86_64.so.1 +p:cmd:getconf cmd:getent cmd:iconv cmd:ldconfig cmd:ldd +r:libiconv +F:sbin +R:ldconfig +a:0:0:755 +Z:Q1Kja2+POZKxEkUOZqwSjC6kmaED4= +F:usr +F:usr/bin +R:iconv +a:0:0:755 +Z:Q1CVmFbdY+Hv6/jAHl1gec2Kbx1EY= +R:ldd +a:0:0:755 +Z:Q1yFAhGggmL7ERgbIA7KQxyTzf3ks= +R:getconf +a:0:0:755 +Z:Q1dAdYK8M/INibRQF5B3Rw7cmNDDA= +R:getent +a:0:0:755 +Z:Q1eR2Dz/WylabgbWMTkd2+hGmEya4= \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/catalog.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/catalog.go new file mode 100644 index 0000000000000000000000000000000000000000..c9bd4f51a4f4b465c0c54e4d03b52753088a40fa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/catalog.go @@ -0,0 +1,145 @@ +package cataloger + +import ( + "fmt" + + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/event" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common/cpe" + "github.com/anchore/syft/syft/source" + "github.com/hashicorp/go-multierror" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/go-progress" +) + +// Monitor provides progress-related data for observing the progress of a Catalog() call (published on the event bus). +type Monitor struct { + FilesProcessed progress.Monitorable // the number of files selected and contents analyzed from all registered catalogers + PackagesDiscovered progress.Monitorable // the number of packages discovered from all registered catalogers +} + +// newMonitor creates a new Monitor object and publishes the object on the bus as a PackageCatalogerStarted event. +func newMonitor() (*progress.Manual, *progress.Manual) { + filesProcessed := progress.Manual{} + packagesDiscovered := progress.Manual{} + + bus.Publish(partybus.Event{ + Type: event.PackageCatalogerStarted, + Value: Monitor{ + FilesProcessed: progress.Monitorable(&filesProcessed), + PackagesDiscovered: progress.Monitorable(&packagesDiscovered), + }, + }) + return &filesProcessed, &packagesDiscovered +} + +// Catalog a given source (container image or filesystem) with the given catalogers, returning all discovered packages. +// In order to efficiently retrieve contents from a underlying container image the content fetch requests are +// done in bulk. Specifically, all files of interest are collected from each catalogers and accumulated into a single +// request. +func Catalog(resolver source.FileResolver, release *linux.Release, catalogers ...Cataloger) (*pkg.Catalog, []artifact.Relationship, error) { + catalog := pkg.NewCatalog() + var allRelationships []artifact.Relationship + + filesProcessed, packagesDiscovered := newMonitor() + + // perform analysis, accumulating errors for each failed analysis + var errs error + for _, c := range catalogers { + // find packages from the underlying raw data + log.Debugf("cataloging with %q", c.Name()) + packages, relationships, err := c.Catalog(resolver) + if err != nil { + errs = multierror.Append(errs, err) + continue + } + + catalogedPackages := len(packages) + + log.Debugf("discovered %d packages", catalogedPackages) + packagesDiscovered.N += int64(catalogedPackages) + + for _, p := range packages { + // generate CPEs (note: this is excluded from package ID, so is safe to mutate) + p.CPEs = cpe.Generate(p) + + // generate PURL (note: this is excluded from package ID, so is safe to mutate) + p.PURL = pkg.URL(p, release) + + // if we were not able to identify the language we have an opportunity + // to try and get this value from the PURL. Worst case we assert that + // we could not identify the language at either stage and set UnknownLanguage + if p.Language == "" { + p.Language = pkg.LanguageFromPURL(p.PURL) + } + + // create file-to-package relationships for files owned by the package + owningRelationships, err := packageFileOwnershipRelationships(p, resolver) + if err != nil { + log.Warnf("unable to create any package-file relationships for package name=%q: %w", p.Name, err) + } else { + allRelationships = append(allRelationships, owningRelationships...) + } + + // add to catalog + catalog.Add(p) + } + + allRelationships = append(allRelationships, relationships...) + } + + allRelationships = append(allRelationships, pkg.NewRelationships(catalog)...) + + if errs != nil { + return nil, nil, errs + } + + filesProcessed.SetCompleted() + packagesDiscovered.SetCompleted() + + return catalog, allRelationships, nil +} + +func packageFileOwnershipRelationships(p pkg.Package, resolver source.FilePathResolver) ([]artifact.Relationship, error) { + fileOwner, ok := p.Metadata.(pkg.FileOwner) + if !ok { + return nil, nil + } + + locations := map[artifact.ID]source.Location{} + + for _, path := range fileOwner.OwnedFiles() { + pathRefs, err := resolver.FilesByPath(path) + if err != nil { + return nil, fmt.Errorf("unable to find path for path=%q: %w", path, err) + } + + if len(pathRefs) == 0 { + // ideally we want to warn users about missing files from a package, however, it is very common for + // container image authors to delete files that are not needed in order to keep image sizes small. Adding + // a warning here would be needlessly noisy (even for popular base images). + continue + } + + for _, ref := range pathRefs { + if oldRef, ok := locations[ref.Coordinates.ID()]; ok { + log.Debugf("found path duplicate of %s", oldRef.RealPath) + } + locations[ref.Coordinates.ID()] = ref + } + } + + var relationships []artifact.Relationship + for _, location := range locations { + relationships = append(relationships, artifact.Relationship{ + From: p, + To: location.Coordinates, + Type: artifact.ContainsRelationship, + }) + } + return relationships, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..ec2be5ad3bbe573fa323bddae98188a6cba086c3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cataloger.go @@ -0,0 +1,164 @@ +/* +Package cataloger provides the ability to process files from a container image or file system and discover packages +(gems, wheels, jars, rpms, debs, etc). Specifically, this package contains both a catalog function to utilize all +catalogers defined in child packages as well as the interface definition to implement a cataloger. +*/ +package cataloger + +import ( + "strings" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/alpm" + "github.com/anchore/syft/syft/pkg/cataloger/apkdb" + "github.com/anchore/syft/syft/pkg/cataloger/cpp" + "github.com/anchore/syft/syft/pkg/cataloger/dart" + "github.com/anchore/syft/syft/pkg/cataloger/deb" + "github.com/anchore/syft/syft/pkg/cataloger/dotnet" + "github.com/anchore/syft/syft/pkg/cataloger/golang" + "github.com/anchore/syft/syft/pkg/cataloger/haskell" + "github.com/anchore/syft/syft/pkg/cataloger/java" + "github.com/anchore/syft/syft/pkg/cataloger/javascript" + "github.com/anchore/syft/syft/pkg/cataloger/php" + "github.com/anchore/syft/syft/pkg/cataloger/portage" + "github.com/anchore/syft/syft/pkg/cataloger/python" + "github.com/anchore/syft/syft/pkg/cataloger/rpm" + "github.com/anchore/syft/syft/pkg/cataloger/ruby" + "github.com/anchore/syft/syft/pkg/cataloger/rust" + "github.com/anchore/syft/syft/pkg/cataloger/swift" + "github.com/anchore/syft/syft/source" +) + +const AllCatalogersPattern = "all" + +// Cataloger describes behavior for an object to participate in parsing container image or file system +// contents for the purpose of discovering Packages. Each concrete implementation should focus on discovering Packages +// for a specific Package Type or ecosystem. +type Cataloger interface { + // Name returns a string that uniquely describes a cataloger + Name() string + // Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing the catalog source. + Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) +} + +// ImageCatalogers returns a slice of locally implemented catalogers that are fit for detecting installations of packages. +func ImageCatalogers(cfg Config) []Cataloger { + return filterCatalogers([]Cataloger{ + alpm.NewAlpmdbCataloger(), + ruby.NewGemSpecCataloger(), + python.NewPythonPackageCataloger(), + php.NewPHPComposerInstalledCataloger(), + javascript.NewJavascriptPackageCataloger(), + deb.NewDpkgdbCataloger(), + rpm.NewRpmdbCataloger(), + java.NewJavaCataloger(cfg.Java()), + apkdb.NewApkdbCataloger(), + golang.NewGoModuleBinaryCataloger(), + dotnet.NewDotnetDepsCataloger(), + portage.NewPortageCataloger(), + }, cfg.Catalogers) +} + +// DirectoryCatalogers returns a slice of locally implemented catalogers that are fit for detecting packages from index files (and select installations) +func DirectoryCatalogers(cfg Config) []Cataloger { + return filterCatalogers([]Cataloger{ + alpm.NewAlpmdbCataloger(), + ruby.NewGemFileLockCataloger(), + python.NewPythonIndexCataloger(), + python.NewPythonPackageCataloger(), + php.NewPHPComposerLockCataloger(), + javascript.NewJavascriptLockCataloger(), + deb.NewDpkgdbCataloger(), + rpm.NewRpmdbCataloger(), + rpm.NewFileCataloger(), + java.NewJavaCataloger(cfg.Java()), + java.NewJavaPomCataloger(), + apkdb.NewApkdbCataloger(), + golang.NewGoModuleBinaryCataloger(), + golang.NewGoModFileCataloger(), + rust.NewCargoLockCataloger(), + dart.NewPubspecLockCataloger(), + dotnet.NewDotnetDepsCataloger(), + swift.NewCocoapodsCataloger(), + cpp.NewConanfileCataloger(), + portage.NewPortageCataloger(), + haskell.NewHackageCataloger(), + }, cfg.Catalogers) +} + +// AllCatalogers returns all implemented catalogers +func AllCatalogers(cfg Config) []Cataloger { + return filterCatalogers([]Cataloger{ + alpm.NewAlpmdbCataloger(), + ruby.NewGemFileLockCataloger(), + ruby.NewGemSpecCataloger(), + python.NewPythonIndexCataloger(), + python.NewPythonPackageCataloger(), + javascript.NewJavascriptLockCataloger(), + javascript.NewJavascriptPackageCataloger(), + deb.NewDpkgdbCataloger(), + rpm.NewRpmdbCataloger(), + rpm.NewFileCataloger(), + java.NewJavaCataloger(cfg.Java()), + java.NewJavaPomCataloger(), + apkdb.NewApkdbCataloger(), + golang.NewGoModuleBinaryCataloger(), + golang.NewGoModFileCataloger(), + rust.NewCargoLockCataloger(), + rust.NewRustAuditBinaryCataloger(), + dart.NewPubspecLockCataloger(), + dotnet.NewDotnetDepsCataloger(), + php.NewPHPComposerInstalledCataloger(), + php.NewPHPComposerLockCataloger(), + swift.NewCocoapodsCataloger(), + cpp.NewConanfileCataloger(), + portage.NewPortageCataloger(), + haskell.NewHackageCataloger(), + }, cfg.Catalogers) +} + +func RequestedAllCatalogers(cfg Config) bool { + for _, enableCatalogerPattern := range cfg.Catalogers { + if enableCatalogerPattern == AllCatalogersPattern { + return true + } + } + return false +} + +func filterCatalogers(catalogers []Cataloger, enabledCatalogerPatterns []string) []Cataloger { + // if cataloger is not set, all applicable catalogers are enabled by default + if len(enabledCatalogerPatterns) == 0 { + return catalogers + } + for _, enableCatalogerPattern := range enabledCatalogerPatterns { + if enableCatalogerPattern == AllCatalogersPattern { + return catalogers + } + } + var keepCatalogers []Cataloger + for _, cataloger := range catalogers { + if contains(enabledCatalogerPatterns, cataloger.Name()) { + keepCatalogers = append(keepCatalogers, cataloger) + continue + } + log.Infof("skipping cataloger %q", cataloger.Name()) + } + return keepCatalogers +} + +func contains(enabledPartial []string, catalogerName string) bool { + catalogerName = strings.TrimSuffix(catalogerName, "-cataloger") + for _, partial := range enabledPartial { + partial = strings.TrimSuffix(partial, "-cataloger") + if partial == "" { + continue + } + if strings.Contains(catalogerName, partial) { + return true + } + } + return false +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e47944dab823ea5d9cf1a69d0899eb576f906351 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cataloger_test.go @@ -0,0 +1,201 @@ +package cataloger + +import ( + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" + "testing" +) + +var _ Cataloger = (*dummy)(nil) + +type dummy struct { + name string +} + +func (d dummy) Name() string { + return d.name +} + +func (d dummy) Catalog(_ source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + panic("not implemented") +} + +func Test_filterCatalogers(t *testing.T) { + tests := []struct { + name string + patterns []string + catalogers []string + want []string + }{ + { + name: "no filtering", + patterns: nil, + catalogers: []string{ + "ruby-gemspec-cataloger", + "python-package-cataloger", + "php-composer-installed-cataloger", + "javascript-package-cataloger", + "dpkgdb-cataloger", + "rpmdb-cataloger", + "java-cataloger", + "apkdb-cataloger", + "go-module-binary-cataloger", + }, + want: []string{ + "ruby-gemspec-cataloger", + "python-package-cataloger", + "php-composer-installed-cataloger", + "javascript-package-cataloger", + "dpkgdb-cataloger", + "rpmdb-cataloger", + "java-cataloger", + "apkdb-cataloger", + "go-module-binary-cataloger", + }, + }, + { + name: "exact name match", + patterns: []string{ + "rpmdb-cataloger", + "javascript-package-cataloger", + }, + catalogers: []string{ + "ruby-gemspec-cataloger", + "python-package-cataloger", + "php-composer-installed-cataloger", + "javascript-package-cataloger", + "dpkgdb-cataloger", + "rpmdb-cataloger", + "java-cataloger", + "apkdb-cataloger", + "go-module-binary-cataloger", + }, + want: []string{ + "javascript-package-cataloger", + "rpmdb-cataloger", + }, + }, + { + name: "partial name match", + patterns: []string{ + "ruby", + "installed", + }, + catalogers: []string{ + "ruby-gemspec-cataloger", + "ruby-gemfile-cataloger", + "python-package-cataloger", + "php-composer-installed-cataloger", + "javascript-package-cataloger", + "dpkgdb-cataloger", + "rpmdb-cataloger", + "java-cataloger", + "apkdb-cataloger", + "go-module-binary-cataloger", + }, + want: []string{ + "php-composer-installed-cataloger", + "ruby-gemspec-cataloger", + "ruby-gemfile-cataloger", + }, + }, + { + name: "ignore 'cataloger' keyword", + patterns: []string{ + "cataloger", + }, + catalogers: []string{ + "ruby-gemspec-cataloger", + "ruby-gemfile-cataloger", + "python-package-cataloger", + "php-composer-installed-cataloger", + "javascript-package-cataloger", + "dpkgdb-cataloger", + "rpmdb-cataloger", + "java-cataloger", + "apkdb-cataloger", + "go-module-binary-cataloger", + }, + want: []string{}, + }, + { + name: "only some patterns match", + patterns: []string{ + "cataloger", + "go-module", + }, + catalogers: []string{ + "ruby-gemspec-cataloger", + "ruby-gemfile-cataloger", + "python-package-cataloger", + "php-composer-installed-cataloger", + "javascript-package-cataloger", + "dpkgdb-cataloger", + "rpmdb-cataloger", + "java-cataloger", + "apkdb-cataloger", + "go-module-binary-cataloger", + }, + want: []string{ + "go-module-binary-cataloger", + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + var catalogers []Cataloger + for _, n := range tt.catalogers { + catalogers = append(catalogers, dummy{name: n}) + } + got := filterCatalogers(catalogers, tt.patterns) + var gotNames []string + for _, g := range got { + gotNames = append(gotNames, g.Name()) + } + assert.ElementsMatch(t, tt.want, gotNames) + }) + } +} + +func Test_contains(t *testing.T) { + type args struct { + } + tests := []struct { + name string + enabledCatalogers []string + catalogerName string + want bool + }{ + { + name: "keep exact match", + enabledCatalogers: []string{ + "php-composer-installed-cataloger", + }, + catalogerName: "php-composer-installed-cataloger", + want: true, + }, + { + name: "match substring", + enabledCatalogers: []string{ + "python", + }, + catalogerName: "python-package-cataloger", + want: true, + }, + { + name: "dont match on 'cataloger'", + enabledCatalogers: []string{ + "cataloger", + }, + catalogerName: "python-package-cataloger", + want: false, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + assert.Equal(t, tt.want, contains(tt.enabledCatalogers, tt.catalogerName)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/candidate_by_package_type.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/candidate_by_package_type.go new file mode 100644 index 0000000000000000000000000000000000000000..d177827d6be213c795dd2804059ce45e35362b8a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/candidate_by_package_type.go @@ -0,0 +1,194 @@ +package cpe + +import ( + "github.com/anchore/syft/syft/pkg" +) + +// candidateComposite is a convenience when creating the defaultCandidateAdditions set +type candidateComposite struct { + pkg.Type + candidateKey + candidateAddition +} + +// defaultCandidateAdditions is all of the known cases for product and vendor field values that should be used when +// select package information is discovered +var defaultCandidateAdditions = buildCandidateLookup( + []candidateComposite{ + // Java packages + { + pkg.JavaPkg, + candidateKey{PkgName: "springframework"}, + candidateAddition{AdditionalProducts: []string{"spring_framework", "springsource_spring_framework"}, AdditionalVendors: []string{"pivotal_software", "springsource", "vmware"}}, + }, + { + pkg.JavaPkg, + candidateKey{PkgName: "spring-core"}, + candidateAddition{AdditionalProducts: []string{"spring_framework", "springsource_spring_framework"}, AdditionalVendors: []string{"pivotal_software", "springsource", "vmware"}}, + }, + { + // example image: docker.io/nuxeo:latest + pkg.JavaPkg, + candidateKey{PkgName: "elasticsearch"}, // , Vendor: "elasticsearch"}, + candidateAddition{AdditionalVendors: []string{"elastic"}}, + }, + { + // example image: docker.io/kaazing-gateway:latest + pkg.JavaPkg, + candidateKey{PkgName: "log4j"}, // , Vendor: "apache-software-foundation"}, + candidateAddition{AdditionalVendors: []string{"apache"}}, + }, + + { + // example image: cassandra:latest + pkg.JavaPkg, + candidateKey{PkgName: "apache-cassandra"}, // , Vendor: "apache"}, + candidateAddition{AdditionalProducts: []string{"cassandra"}}, + }, + { + // example image: cloudbees/cloudbees-core-mm:2.319.3.4 + // this is a wrapped packaging of the handlebars.js node module + pkg.JavaPkg, + candidateKey{PkgName: "handlebars"}, + candidateAddition{AdditionalVendors: []string{"handlebarsjs"}}, + }, + // NPM packages + { + pkg.NpmPkg, + candidateKey{PkgName: "hapi"}, + candidateAddition{AdditionalProducts: []string{"hapi_server_framework"}}, + }, + { + pkg.NpmPkg, + candidateKey{PkgName: "handlebars.js"}, + candidateAddition{AdditionalProducts: []string{"handlebars"}}, + }, + { + pkg.NpmPkg, + candidateKey{PkgName: "is-my-json-valid"}, + candidateAddition{AdditionalProducts: []string{"is_my_json_valid"}}, + }, + { + pkg.NpmPkg, + candidateKey{PkgName: "mustache"}, + candidateAddition{AdditionalProducts: []string{"mustache.js"}}, + }, + + // Gem packages + { + pkg.GemPkg, + candidateKey{PkgName: "Arabic-Prawn"}, + candidateAddition{AdditionalProducts: []string{"arabic_prawn"}}, + }, + { + pkg.GemPkg, + candidateKey{PkgName: "bio-basespace-sdk"}, + candidateAddition{AdditionalProducts: []string{"basespace_ruby_sdk"}}, + }, + { + pkg.GemPkg, + candidateKey{PkgName: "cremefraiche"}, + candidateAddition{AdditionalProducts: []string{"creme_fraiche"}}, + }, + { + pkg.GemPkg, + candidateKey{PkgName: "html-sanitizer"}, + candidateAddition{AdditionalProducts: []string{"html_sanitizer"}}, + }, + { + pkg.GemPkg, + candidateKey{PkgName: "sentry-raven"}, + candidateAddition{AdditionalProducts: []string{"raven-ruby"}}, + }, + { + pkg.GemPkg, + candidateKey{PkgName: "RedCloth"}, + candidateAddition{AdditionalProducts: []string{"redcloth_library"}}, + }, + { + pkg.GemPkg, + candidateKey{PkgName: "VladTheEnterprising"}, + candidateAddition{AdditionalProducts: []string{"vladtheenterprising"}}, + }, + { + pkg.GemPkg, + candidateKey{PkgName: "yajl-ruby"}, + candidateAddition{AdditionalProducts: []string{"yajl-ruby_gem"}}, + }, + // Python packages + { + pkg.PythonPkg, + candidateKey{PkgName: "python-rrdtool"}, + candidateAddition{AdditionalProducts: []string{"rrdtool"}}, + }, + }) + +// buildCandidateLookup is a convenience function for creating the defaultCandidateAdditions set +func buildCandidateLookup(cc []candidateComposite) (ca map[pkg.Type]map[candidateKey]candidateAddition) { + ca = make(map[pkg.Type]map[candidateKey]candidateAddition) + for _, c := range cc { + if _, ok := ca[c.Type]; !ok { + ca[c.Type] = make(map[candidateKey]candidateAddition) + } + ca[c.Type][c.candidateKey] = c.candidateAddition + } + + return ca +} + +// candidateKey represents the set of inputs that should be matched on in order to signal more candidate additions to be used. +type candidateKey struct { + Vendor string + PkgName string +} + +// candidateAddition are the specific additions that should be considered during CPE generation (given a specific candidateKey) +type candidateAddition struct { + AdditionalProducts []string + AdditionalVendors []string +} + +// findAdditionalVendors searches all possible vendor additions that could be added during the CPE generation process (given package info + a vendor candidate) +func findAdditionalVendors(allAdditions map[pkg.Type]map[candidateKey]candidateAddition, ty pkg.Type, pkgName, vendor string) (vendors []string) { + additions, ok := allAdditions[ty] + if !ok { + return nil + } + + if addition, ok := additions[candidateKey{ + Vendor: vendor, + PkgName: pkgName, + }]; ok { + vendors = append(vendors, addition.AdditionalVendors...) + } + + if addition, ok := additions[candidateKey{ + PkgName: pkgName, + }]; ok { + vendors = append(vendors, addition.AdditionalVendors...) + } + + if addition, ok := additions[candidateKey{ + Vendor: vendor, + }]; ok { + vendors = append(vendors, addition.AdditionalVendors...) + } + + return vendors +} + +// findAdditionalProducts searches all possible product additions that could be added during the CPE generation process (given package info) +func findAdditionalProducts(allAdditions map[pkg.Type]map[candidateKey]candidateAddition, ty pkg.Type, pkgName string) (products []string) { + additions, ok := allAdditions[ty] + if !ok { + return nil + } + + if addition, ok := additions[candidateKey{ + PkgName: pkgName, + }]; ok { + products = append(products, addition.AdditionalProducts...) + } + + return products +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/candidate_by_package_type_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/candidate_by_package_type_test.go new file mode 100644 index 0000000000000000000000000000000000000000..497d298a6a0a267d4935d69d104995a4aa1ef48d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/candidate_by_package_type_test.go @@ -0,0 +1,155 @@ +package cpe + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_additionalProducts(t *testing.T) { + tests := []struct { + name string + allAdditions map[pkg.Type]map[candidateKey]candidateAddition + ty pkg.Type + pkgName string + expected []string + }{ + { + name: "product name addition", + allAdditions: map[pkg.Type]map[candidateKey]candidateAddition{ + pkg.JavaPkg: { + candidateKey{ + PkgName: "spring-core", + }: { + AdditionalProducts: []string{"spring_framework", "springsource_spring_framework"}, + }, + }, + }, + ty: pkg.JavaPkg, + pkgName: "spring-core", + expected: []string{"spring_framework", "springsource_spring_framework"}, + }, + { + name: "no addition found", + allAdditions: map[pkg.Type]map[candidateKey]candidateAddition{ + pkg.JavaPkg: { + candidateKey{ + PkgName: "spring-core", + }: { + AdditionalProducts: []string{"spring_framework", "springsource_spring_framework"}, + }, + }, + }, + ty: pkg.JavaPkg, + pkgName: "nothing", + expected: nil, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, findAdditionalProducts(test.allAdditions, test.ty, test.pkgName)) + }) + } +} + +func Test_additionalVendors(t *testing.T) { + tests := []struct { + name string + allAdditions map[pkg.Type]map[candidateKey]candidateAddition + ty pkg.Type + pkgName string + vendor string + expected []string + }{ + { + name: "vendor addition by input vendor", + allAdditions: map[pkg.Type]map[candidateKey]candidateAddition{ + pkg.JavaPkg: { + candidateKey{ + Vendor: "my-vendor", + }: { + AdditionalVendors: []string{"awesome-vendor-addition"}, + }, + // note: the below keys should not be matched + candidateKey{ + PkgName: "my-package-name", + Vendor: "my-vendor", + }: { + AdditionalVendors: []string{"bad-addition"}, + }, + candidateKey{ + PkgName: "my-package-name", + }: { + AdditionalVendors: []string{"bad-addition"}, + }, + }, + }, + ty: pkg.JavaPkg, + pkgName: "NOT-MY-PACKAGE", + vendor: "my-vendor", + expected: []string{"awesome-vendor-addition"}, + }, + { + name: "vendor addition by input package name", + allAdditions: map[pkg.Type]map[candidateKey]candidateAddition{ + pkg.JavaPkg: { + candidateKey{ + PkgName: "my-package-name", + }: { + AdditionalVendors: []string{"awesome-vendor-addition"}, + }, + // note: the below keys should not be matched + candidateKey{ + PkgName: "my-package-name", + Vendor: "my-vendor", + }: { + AdditionalVendors: []string{"bad-addition"}, + }, + candidateKey{ + Vendor: "my-vendor", + }: { + AdditionalVendors: []string{"bad-addition"}, + }, + }, + }, + ty: pkg.JavaPkg, + pkgName: "my-package-name", + vendor: "NOT-MY-VENDOR", + expected: []string{"awesome-vendor-addition"}, + }, + { + name: "vendor addition by input package name + vendor", + allAdditions: map[pkg.Type]map[candidateKey]candidateAddition{ + pkg.JavaPkg: { + candidateKey{ + PkgName: "my-package-name", + Vendor: "my-vendor", + }: { + AdditionalVendors: []string{"awesome-vendor-addition"}, + }, + // note: the below keys should not be matched + candidateKey{ + PkgName: "my-package-name", + }: { + AdditionalVendors: []string{"one-good-addition"}, + }, + candidateKey{ + Vendor: "my-vendor", + }: { + AdditionalVendors: []string{"another-good-addition"}, + }, + }, + }, + ty: pkg.JavaPkg, + pkgName: "my-package-name", + vendor: "my-vendor", + expected: []string{"awesome-vendor-addition", "one-good-addition", "another-good-addition"}, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, findAdditionalVendors(test.allAdditions, test.ty, test.pkgName, test.vendor)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate.go new file mode 100644 index 0000000000000000000000000000000000000000..c7abbb1e5b0c899c6c2d52ae0cd049d96a721356 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate.go @@ -0,0 +1,112 @@ +package cpe + +import ( + "strconv" + + "github.com/scylladb/go-set/strset" +) + +// fieldCandidate represents a single "guess" for a specific field in a future CPE (vendor, product, target SW, etc). +// When generating these candidates depending on the field the value was sourced from there may be only a subset of +// transforms that should be applied (downstream of extraction). Expressing candidates in this struct allows for this +// flexibility such that downstream transforms can be elected into or skipped over. +type fieldCandidate struct { + value string + disallowSubSelections bool + disallowDelimiterVariations bool +} + +type fieldCandidateSet map[fieldCandidate]struct{} + +func newFieldCandidateSetFromSets(sets ...fieldCandidateSet) fieldCandidateSet { + s := newFieldCandidateSet() + for _, set := range sets { + s.add(set.list()...) + } + return s +} + +func newFieldCandidateSet(values ...string) fieldCandidateSet { + s := make(fieldCandidateSet) + s.addValue(values...) + return s +} + +func (s fieldCandidateSet) addValue(values ...string) { + for _, value := range values { + // default candidate as an allow-all + candidate := fieldCandidate{ + value: cleanCandidateField(value), + } + s[candidate] = struct{}{} + } +} + +func (s fieldCandidateSet) add(candidates ...fieldCandidate) { + for _, candidate := range candidates { + candidate.value = cleanCandidateField(candidate.value) + s[candidate] = struct{}{} + } +} + +func (s fieldCandidateSet) removeByValue(values ...string) { + for _, value := range values { + s.removeWhere(valueEquals(value)) + } +} + +// removeWhere removes all entries from the fieldCandidateSet for which the condition function returns true. +func (s fieldCandidateSet) removeWhere(condition fieldCandidateCondition) { + for candidate := range s { + if condition(candidate) { + delete(s, candidate) + } + } +} + +func (s fieldCandidateSet) clear() { + for k := range s { + delete(s, k) + } +} + +func (s fieldCandidateSet) union(others ...fieldCandidateSet) { + for _, other := range others { + s.add(other.list()...) + } +} + +func (s fieldCandidateSet) list() (results []fieldCandidate) { + for c := range s { + results = append(results, c) + } + + return results +} + +func (s fieldCandidateSet) values() (results []string) { + for _, c := range s.list() { + results = append(results, c.value) + } + + return results +} + +func (s fieldCandidateSet) uniqueValues() []string { + return strset.New(s.values()...).List() +} + +func (s fieldCandidateSet) copy() fieldCandidateSet { + newSet := newFieldCandidateSet() + newSet.add(s.list()...) + + return newSet +} + +func cleanCandidateField(field string) string { + cleanedValue, err := strconv.Unquote(field) + if err != nil { + return field + } + return cleanedValue +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate_filter.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate_filter.go new file mode 100644 index 0000000000000000000000000000000000000000..203d0e7fcbbf0b9e4b62cb982a8f7acba3fe3f9b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate_filter.go @@ -0,0 +1,18 @@ +package cpe + +// A fieldCandidateCondition returns true if the condition is true for a given fieldCandidate. +type fieldCandidateCondition func(fieldCandidate) bool + +func subSelectionsDisallowed(c fieldCandidate) bool { + return c.disallowSubSelections +} + +func delimiterVariationsDisallowed(c fieldCandidate) bool { + return c.disallowDelimiterVariations +} + +func valueEquals(v string) fieldCandidateCondition { + return func(candidate fieldCandidate) bool { + return candidate.value == v + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate_test.go new file mode 100644 index 0000000000000000000000000000000000000000..f4f70d22da885be31eec58da560fc019e4a17576 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/field_candidate_test.go @@ -0,0 +1,350 @@ +package cpe + +import ( + "strings" + "testing" + + "github.com/stretchr/testify/assert" +) + +func Test_cpeCandidateValues_filter(t *testing.T) { + tests := []struct { + name string + input []fieldCandidate + exclusionConditions []fieldCandidateCondition + expect []string + }{ + { + name: "gocase", + input: []fieldCandidate{ + { + value: "allow anything", + }, + { + value: "no-sub-selections", + disallowSubSelections: true, + }, + { + value: "no-delimiter-variations", + disallowDelimiterVariations: true, + }, + { + value: "allow nothing", + disallowSubSelections: true, + disallowDelimiterVariations: true, + }, + }, + expect: []string{ + "allow anything", + "no-sub-selections", + "no-delimiter-variations", + "allow nothing", + }, + }, + { + name: "filter out sub-selections", + input: []fieldCandidate{ + { + value: "allow anything", + }, + { + value: "no-sub-selections", + disallowSubSelections: true, + }, + { + value: "no-delimiter-variations", + disallowDelimiterVariations: true, + }, + { + value: "allow nothing", + disallowSubSelections: true, + disallowDelimiterVariations: true, + }, + }, + exclusionConditions: []fieldCandidateCondition{ + subSelectionsDisallowed, + }, + expect: []string{ + "allow anything", + "no-delimiter-variations", + }, + }, + { + name: "filter out delimiter-variations", + input: []fieldCandidate{ + { + value: "allow anything", + }, + { + value: "no-sub-selections", + disallowSubSelections: true, + }, + { + value: "no-delimiter-variations", + disallowDelimiterVariations: true, + }, + { + value: "allow nothing", + disallowSubSelections: true, + disallowDelimiterVariations: true, + }, + }, + exclusionConditions: []fieldCandidateCondition{ + delimiterVariationsDisallowed, + }, + expect: []string{ + "allow anything", + "no-sub-selections", + }, + }, + { + name: "all exclusionConditions", + input: []fieldCandidate{ + { + value: "allow anything", + }, + { + value: "no-sub-selections", + disallowSubSelections: true, + }, + { + value: "no-delimiter-variations", + disallowDelimiterVariations: true, + }, + { + value: "allow nothing", + disallowSubSelections: true, + disallowDelimiterVariations: true, + }, + }, + exclusionConditions: []fieldCandidateCondition{ + delimiterVariationsDisallowed, + subSelectionsDisallowed, + }, + expect: []string{ + "allow anything", + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + set := newFieldCandidateSet() + set.add(test.input...) + + for _, condition := range test.exclusionConditions { + set.removeWhere(condition) + } + + assert.ElementsMatch(t, test.expect, set.values()) + }) + } +} + +func Test_cpeFieldCandidateSet_addValue(t *testing.T) { + s := newFieldCandidateSet() + // we should clean all values (unquote strings) + s.addValue(`"string!"`) + assert.ElementsMatch(t, []string{"string!"}, s.values()) +} + +func Test_cpeFieldCandidateSet_add(t *testing.T) { + s := newFieldCandidateSet() + // we should clean all values (unquote strings) + s.add(fieldCandidate{ + value: `"string!"`, + }) + assert.ElementsMatch(t, []string{"string!"}, s.values()) +} + +func Test_cpeFieldCandidateSet_clear(t *testing.T) { + s := newFieldCandidateSet("1", "2") + assert.NotEmpty(t, s.values()) + s.clear() + assert.Empty(t, s.values()) +} + +func Test_cpeFieldCandidateSet_union(t *testing.T) { + s1 := newFieldCandidateSet("1", "2") + assert.Len(t, s1.list(), 2) + s2 := newFieldCandidateSet("2", "3", "4") + assert.Len(t, s2.list(), 3) + s3 := newFieldCandidateSet() + s3.add( + fieldCandidate{ + value: "1", + disallowSubSelections: true, + disallowDelimiterVariations: false, + }, + fieldCandidate{ + value: "4", + disallowSubSelections: false, + disallowDelimiterVariations: true, + }, + fieldCandidate{ + value: "5", + disallowSubSelections: true, + disallowDelimiterVariations: true, + }, + ) + assert.Len(t, s3.list(), 3) + + s1.union(s2, s3) + + // 1 & 4 have duplicate entries since there are candidate conditions set + assert.ElementsMatch(t, s1.values(), []string{"1", "1", "2", "3", "4", "4", "5"}) + + assert.ElementsMatch(t, s1.list(), []fieldCandidate{ + { + value: "1", + }, + { + value: "1", + disallowSubSelections: true, + disallowDelimiterVariations: false, + }, + { + value: "2", + }, + { + value: "3", + }, + { + value: "4", + }, + { + value: "4", + disallowSubSelections: false, + disallowDelimiterVariations: true, + }, + { + value: "5", + disallowSubSelections: true, + disallowDelimiterVariations: true, + }, + }) +} + +func Test_cpeFieldCandidateSet_union_byValue(t *testing.T) { + s1 := newFieldCandidateSet("1", "2") + assert.Len(t, s1.list(), 2) + s2 := newFieldCandidateSet("2", "3", "4") + assert.Len(t, s2.list(), 3) + s3 := newFieldCandidateSet("1", "4", "5") + assert.Len(t, s3.list(), 3) + + s1.union(s2, s3) + + assert.ElementsMatch(t, s1.values(), []string{"1", "2", "3", "4", "5"}) + + assert.ElementsMatch(t, s1.list(), []fieldCandidate{ + { + value: "1", + }, + { + value: "2", + }, + { + value: "3", + }, + { + value: "4", + }, + { + value: "5", + }, + }) +} + +func Test_cpeFieldCandidateSet_uniqueValues(t *testing.T) { + set := newFieldCandidateSet() + set.add( + fieldCandidate{ + value: "1", + }, + fieldCandidate{ + value: "1", + disallowSubSelections: true, + }, + fieldCandidate{ + value: "2", + disallowDelimiterVariations: true, + }, + fieldCandidate{ + value: "2", + }, + fieldCandidate{ + value: "3", + disallowSubSelections: true, + disallowDelimiterVariations: true, + }, + ) + + assert.ElementsMatch(t, []string{"1", "2", "3"}, set.uniqueValues()) + +} + +func Test_cpeFieldCandidateSet_removeByValue(t *testing.T) { + s := newFieldCandidateSet() + + // should be removed + s.add(fieldCandidate{ + value: "1", + disallowSubSelections: true, + disallowDelimiterVariations: true, + }) + s.add(fieldCandidate{ + value: "1", + disallowSubSelections: true, + }) + s.add(fieldCandidate{ + value: "1", + disallowDelimiterVariations: true, + }) + s.add(fieldCandidate{ + value: "1", + }) + + // should not be removed + s.add(fieldCandidate{ + value: "2", + }) + + assert.Len(t, s.values(), 5) + + s.removeByValue("1") + + assert.Len(t, s.values(), 1) +} + +func Test_cpeFieldCandidateSet_removeByCondition(t *testing.T) { + s := newFieldCandidateSet() + + // should be removed + s.add(fieldCandidate{ + value: "1", + disallowSubSelections: true, + }) + s.add(fieldCandidate{ + value: "hello-world", + }) + + // should not be removed + s.add(fieldCandidate{ + value: "2", + }) + + assert.Len(t, s.values(), 3) + + s.removeWhere(func(candidate fieldCandidate) bool { + return candidate.disallowSubSelections == true + }) + + assert.Len(t, s.values(), 2) + + s.removeWhere(func(candidate fieldCandidate) bool { + return strings.Contains(candidate.value, "-") + }) + + assert.Len(t, s.values(), 1) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/filter.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/filter.go new file mode 100644 index 0000000000000000000000000000000000000000..cfb696c7d3db947b547dcd3e04a07088a8b24e12 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/filter.go @@ -0,0 +1,73 @@ +package cpe + +import ( + "strings" + + "github.com/anchore/syft/syft/pkg" + "github.com/facebookincubator/nvdtools/wfn" +) + +const jenkinsName = "jenkins" + +// filterFn instances should return true if the given CPE should be removed from a collection for the given package +type filterFn func(cpe pkg.CPE, p pkg.Package) bool + +var cpeFilters = []filterFn{ + disallowJiraClientServerMismatch, + disallowJenkinsServerCPEForPluginPackage, + disallowJenkinsCPEsNotAssociatedWithJenkins, + disallowNonParseableCPEs, +} + +func filter(cpes []pkg.CPE, p pkg.Package, filters ...filterFn) (result []pkg.CPE) { +cpeLoop: + for _, cpe := range cpes { + for _, fn := range filters { + if fn(cpe, p) { + continue cpeLoop + } + } + // all filter functions passed on filtering this CPE + result = append(result, cpe) + } + return result +} + +func disallowNonParseableCPEs(cpe pkg.CPE, _ pkg.Package) bool { + v := pkg.CPEString(cpe) + _, err := pkg.NewCPE(v) + + cannotParse := err != nil + + return cannotParse +} + +// jenkins plugins should not match against jenkins +func disallowJenkinsServerCPEForPluginPackage(cpe pkg.CPE, p pkg.Package) bool { + if p.Type == pkg.JenkinsPluginPkg && cpe.Product == jenkinsName { + return true + } + return false +} + +// filter to account that packages that are not for jenkins but have a CPE generated that will match against jenkins +func disallowJenkinsCPEsNotAssociatedWithJenkins(cpe pkg.CPE, p pkg.Package) bool { + // jenkins server should only match against a product with the name jenkins + if cpe.Product == jenkinsName && !strings.Contains(strings.ToLower(p.Name), jenkinsName) { + if cpe.Vendor == wfn.Any || cpe.Vendor == jenkinsName || cpe.Vendor == "cloudbees" { + return true + } + } + return false +} + +// filter to account for packages which are jira client packages but have a CPE that will match against jira +func disallowJiraClientServerMismatch(cpe pkg.CPE, p pkg.Package) bool { + // jira / atlassian should not apply to clients + if cpe.Product == "jira" && strings.Contains(strings.ToLower(p.Name), "client") { + if cpe.Vendor == wfn.Any || cpe.Vendor == "jira" || cpe.Vendor == "atlassian" { + return true + } + } + return false +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/filter_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/filter_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d57bc8b72150033cc0db2d859fe0c7b0f841078c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/filter_test.go @@ -0,0 +1,167 @@ +package cpe + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_disallowJenkinsServerCPEForPluginPackage(t *testing.T) { + tests := []struct { + name string + cpe pkg.CPE + pkg pkg.Package + expected bool + }{ + { + name: "go case (filter out)", + cpe: pkg.MustCPE("cpe:2.3:a:name:jenkins:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Type: pkg.JenkinsPluginPkg, + }, + expected: true, + }, + { + name: "ignore jenkins plugins with unique name", + cpe: pkg.MustCPE("cpe:2.3:a:name:ci-jenkins:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Type: pkg.JenkinsPluginPkg, + }, + expected: false, + }, + { + name: "ignore java packages", + cpe: pkg.MustCPE("cpe:2.3:a:name:jenkins:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Type: pkg.JavaPkg, + }, + expected: false, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, disallowJenkinsServerCPEForPluginPackage(test.cpe, test.pkg)) + }) + } +} + +func Test_disallowJenkinsCPEsNotAssociatedWithJenkins(t *testing.T) { + tests := []struct { + name string + cpe pkg.CPE + pkg pkg.Package + expected bool + }{ + { + name: "filter out mismatched name (cloudbees vendor)", + cpe: pkg.MustCPE("cpe:2.3:a:cloudbees:jenkins:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "not-j*nkins", + Type: pkg.JavaPkg, + }, + expected: true, + }, + { + name: "filter out mismatched name (jenkins vendor)", + cpe: pkg.MustCPE("cpe:2.3:a:jenkins:jenkins:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "not-j*nkins", + Type: pkg.JavaPkg, + }, + expected: true, + }, + { + name: "filter out mismatched name (any vendor)", + cpe: pkg.MustCPE("cpe:2.3:a:*:jenkins:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "not-j*nkins", + Type: pkg.JavaPkg, + }, + expected: true, + }, + { + name: "ignore packages with the name jenkins", + cpe: pkg.MustCPE("cpe:2.3:a:*:jenkins:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "jenkins-thing", + Type: pkg.JavaPkg, + }, + expected: false, + }, + { + name: "ignore product names that are not exactly 'jenkins'", + cpe: pkg.MustCPE("cpe:2.3:a:*:jenkins-something-else:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "not-j*nkins", + Type: pkg.JavaPkg, + }, + expected: false, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, disallowJenkinsCPEsNotAssociatedWithJenkins(test.cpe, test.pkg)) + }) + } +} + +func Test_disallowJiraClientServerMismatch(t *testing.T) { + tests := []struct { + name string + cpe pkg.CPE + pkg pkg.Package + expected bool + }{ + { + name: "filter out mismatched name (atlassian vendor)", + cpe: pkg.MustCPE("cpe:2.3:a:atlassian:jira:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "something-client", + Type: pkg.JavaPkg, + }, + expected: true, + }, + { + name: "filter out mismatched name (jira vendor)", + cpe: pkg.MustCPE("cpe:2.3:a:jira:jira:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "something-client", + Type: pkg.JavaPkg, + }, + expected: true, + }, + { + name: "filter out mismatched name (any vendor)", + cpe: pkg.MustCPE("cpe:2.3:a:*:jira:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "something-client", + Type: pkg.JavaPkg, + }, + expected: true, + }, + { + name: "ignore package names that do not have 'client'", + cpe: pkg.MustCPE("cpe:2.3:a:*:jira:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "jira-thing", + Type: pkg.JavaPkg, + }, + expected: false, + }, + { + name: "ignore product names that are not exactly 'jira'", + cpe: pkg.MustCPE("cpe:2.3:a:*:jira-something-else:3.2:*:*:*:*:*:*:*"), + pkg: pkg.Package{ + Name: "not-j*ra", + Type: pkg.JavaPkg, + }, + expected: false, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, disallowJiraClientServerMismatch(test.cpe, test.pkg)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/generate.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/generate.go new file mode 100644 index 0000000000000000000000000000000000000000..a93bf343a40dd2e106971d055d2db50f910561ed --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/generate.go @@ -0,0 +1,239 @@ +package cpe + +import ( + "bufio" + "bytes" + "fmt" + "sort" + "strings" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/pkg" + "github.com/facebookincubator/nvdtools/wfn" +) + +func newCPE(product, vendor, version, targetSW string) *wfn.Attributes { + cpe := *(wfn.NewAttributesWithAny()) + cpe.Part = "a" + cpe.Product = product + cpe.Vendor = vendor + cpe.Version = version + cpe.TargetSW = targetSW + if pkg.ValidateCPEString(pkg.CPEString(cpe)) != nil { + return nil + } + return &cpe +} + +// Generate Create a list of CPEs for a given package, trying to guess the vendor, product tuple. We should be trying to +// generate the minimal set of representative CPEs, which implies that optional fields should not be included +// (such as target SW). +func Generate(p pkg.Package) []pkg.CPE { + vendors := candidateVendors(p) + products := candidateProducts(p) + if len(products) == 0 { + return nil + } + + keys := internal.NewStringSet() + cpes := make([]pkg.CPE, 0) + for _, product := range products { + for _, vendor := range vendors { + // prevent duplicate entries... + key := fmt.Sprintf("%s|%s|%s", product, vendor, p.Version) + if keys.Contains(key) { + continue + } + keys.Add(key) + // add a new entry... + if cpe := newCPE(product, vendor, p.Version, wfn.Any); cpe != nil { + cpes = append(cpes, *cpe) + } + } + } + + // filter out any known combinations that don't accurately represent this package + cpes = filter(cpes, p, cpeFilters...) + + sort.Sort(pkg.CPEBySpecificity(cpes)) + + return cpes +} + +func candidateVendors(p pkg.Package) []string { + // in ecosystems where the packaging metadata does not have a clear field to indicate a vendor (or a field that + // could be interpreted indirectly as such) the project name tends to be a common stand in. Examples of this + // are the elasticsearch gem, xstream jar, and rack gem... all of these cases you can find vulnerabilities + // with CPEs where the vendor is the product name and doesn't appear to be derived from any available package + // metadata. + vendors := newFieldCandidateSet(candidateProducts(p)...) + + switch p.Language { + case pkg.Ruby: + vendors.addValue("ruby-lang") + case pkg.Go: + // replace all candidates with only the golang-specific helper + vendors.clear() + + vendor := candidateVendorForGo(p.Name) + if vendor != "" { + vendors.addValue(vendor) + } + } + + // some ecosystems do not have enough metadata to determine the vendor accurately, in which case we selectively + // allow * as a candidate. Note: do NOT allow Java packages to have * vendors. + switch p.Language { + case pkg.Ruby, pkg.JavaScript: + vendors.addValue(wfn.Any) + } + + switch p.MetadataType { + case pkg.RpmMetadataType: + vendors.union(candidateVendorsForRPM(p)) + case pkg.GemMetadataType: + vendors.union(candidateVendorsForRuby(p)) + case pkg.PythonPackageMetadataType: + vendors.union(candidateVendorsForPython(p)) + case pkg.JavaMetadataType: + vendors.union(candidateVendorsForJava(p)) + } + + // try swapping hyphens for underscores, vice versa, and removing separators altogether + addDelimiterVariations(vendors) + + // generate sub-selections of each candidate based on separators (e.g. jenkins-ci -> [jenkins, jenkins-ci]) + addAllSubSelections(vendors) + + // add more candidates based on the package info for each vendor candidate + for _, vendor := range vendors.uniqueValues() { + vendors.addValue(findAdditionalVendors(defaultCandidateAdditions, p.Type, p.Name, vendor)...) + } + + return vendors.uniqueValues() +} + +func candidateProducts(p pkg.Package) []string { + products := newFieldCandidateSet(p.Name) + + switch { + case p.Language == pkg.Python: + if !strings.HasPrefix(p.Name, "python") { + products.addValue("python-" + p.Name) + } + case p.Language == pkg.Java || p.MetadataType == pkg.JavaMetadataType: + products.addValue(candidateProductsForJava(p)...) + case p.Language == pkg.Go: + // replace all candidates with only the golang-specific helper + products.clear() + + prod := candidateProductForGo(p.Name) + if prod != "" { + products.addValue(prod) + } + } + // it is never OK to have candidates with these values ["" and "*"] (since CPEs will match any other value) + products.removeByValue("") + products.removeByValue("*") + + // try swapping hyphens for underscores, vice versa, and removing separators altogether + addDelimiterVariations(products) + + // add known candidate additions + products.addValue(findAdditionalProducts(defaultCandidateAdditions, p.Type, p.Name)...) + + return products.uniqueValues() +} + +func addAllSubSelections(fields fieldCandidateSet) { + candidatesForVariations := fields.copy() + candidatesForVariations.removeWhere(subSelectionsDisallowed) + + for _, candidate := range candidatesForVariations.values() { + fields.addValue(generateSubSelections(candidate)...) + } +} + +// generateSubSelections attempts to split a field by hyphens and underscores and return a list of sensible sub-selections +// that can be used as product or vendor candidates. E.g. jenkins-ci-tools -> [jenkins-ci-tools, jenkins-ci, jenkins]. +func generateSubSelections(field string) (results []string) { + scanner := bufio.NewScanner(strings.NewReader(field)) + scanner.Split(scanByHyphenOrUnderscore) + var lastToken uint8 + for scanner.Scan() { + rawCandidate := scanner.Text() + if len(rawCandidate) == 0 { + break + } + + // trim any number of hyphen or underscore that is prefixed/suffixed on the given candidate. Since + // scanByHyphenOrUnderscore preserves delimiters (hyphens and underscores) they are guaranteed to be at least + // prefixed. + candidate := strings.TrimFunc(rawCandidate, trimHyphenOrUnderscore) + + // capture the result (if there is content) + if len(candidate) > 0 { + if len(results) > 0 { + results = append(results, results[len(results)-1]+string(lastToken)+candidate) + } else { + results = append(results, candidate) + } + } + + // keep track of the trailing separator for the next loop + lastToken = rawCandidate[len(rawCandidate)-1] + } + return results +} + +// trimHyphenOrUnderscore is a character filter function for use with strings.TrimFunc in order to remove any hyphen or underscores. +func trimHyphenOrUnderscore(r rune) bool { + switch r { + case '-', '_': + return true + } + return false +} + +// scanByHyphenOrUnderscore splits on hyphen or underscore and includes the separator in the split +func scanByHyphenOrUnderscore(data []byte, atEOF bool) (advance int, token []byte, err error) { + if atEOF && len(data) == 0 { + return 0, nil, nil + } + if i := bytes.IndexAny(data, "-_"); i >= 0 { + return i + 1, data[0 : i+1], nil + } + + if atEOF { + return len(data), data, nil + } + + return 0, nil, nil +} + +func addDelimiterVariations(fields fieldCandidateSet) { + candidatesForVariations := fields.copy() + candidatesForVariations.removeWhere(delimiterVariationsDisallowed) + + for _, candidate := range candidatesForVariations.list() { + field := candidate.value + hasHyphen := strings.Contains(field, "-") + hasUnderscore := strings.Contains(field, "_") + + if hasHyphen { + // provide variations of hyphen candidates with an underscore + newValue := strings.ReplaceAll(field, "-", "_") + underscoreCandidate := candidate + underscoreCandidate.value = newValue + fields.add(underscoreCandidate) + } + + if hasUnderscore { + // provide variations of underscore candidates with a hyphen + newValue := strings.ReplaceAll(field, "_", "-") + hyphenCandidate := candidate + hyphenCandidate.value = newValue + fields.add(hyphenCandidate) + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/generate_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/generate_test.go new file mode 100644 index 0000000000000000000000000000000000000000..52676b5285f7f2a36d938ab86a5306d9df0adf15 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/generate_test.go @@ -0,0 +1,907 @@ +package cpe + +import ( + "fmt" + "sort" + "strings" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/scylladb/go-set" + "github.com/scylladb/go-set/strset" + "github.com/stretchr/testify/assert" +) + +func TestGeneratePackageCPEs(t *testing.T) { + tests := []struct { + name string + p pkg.Package + expected []string + }{ + { + name: "hyphen replacement", + p: pkg.Package{ + Name: "name-part", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Python, + Type: pkg.DebPkg, + }, + expected: []string{ + "cpe:2.3:a:name-part:name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name-part:name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name-part:python-name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name-part:python_name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:python-name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:python_name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name_part:name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name_part:name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name_part:python-name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name_part:python_name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name-part:name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name-part:name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name-part:python-name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name-part:python_name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name:name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name:name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name:python-name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name:python_name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python:name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python:name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python:python-name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python:python_name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name:name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name:name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name:python-name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name:python_name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name_part:name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name_part:name_part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name_part:python-name-part:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name_part:python_name_part:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "python language", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Python, + Type: pkg.DebPkg, + MetadataType: pkg.PythonPackageMetadataType, + Metadata: pkg.PythonPackageMetadata{ + Author: "alex goodman", + AuthorEmail: "william.goodman@anchore.com", + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:python-name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:python_name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name:python-name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python-name:python_name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python:python-name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python:python_name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name:python-name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:python_name:python_name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:alex_goodman:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:alex_goodman:python-name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:alex_goodman:python_name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:william-goodman:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:william-goodman:python-name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:william-goodman:python_name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:william_goodman:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:william_goodman:python-name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:william_goodman:python_name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "javascript language", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.JavaScript, + Type: pkg.DebPkg, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:*:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "ruby language", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Ruby, + Type: pkg.DebPkg, + MetadataType: pkg.GemMetadataType, + Metadata: pkg.GemMetadata{ + Authors: []string{ + "someones name", + "someones.elses.name@gmail.com", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:*:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:ruby-lang:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:ruby:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:ruby_lang:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:someones-elses-name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:someones-name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:someones_elses_name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:someones_name:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "java language", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JavaPkg, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "java language with groupID", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "org.sonatype.nexus", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:nexus:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:nexus:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:nexus:nexus:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:sonatype:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:sonatype:nexus:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "java with URL in metadata", // regression: https://github.com/anchore/grype/issues/417 + p: pkg.Package{ + Name: "wstx-asl", + Version: "3.2.7", + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Ant-Version": "Apache Ant 1.6.5", + "Built-By": "tatu", + "Created-By": "1.4.2_03-b02 (Sun Microsystems Inc.)", + "Implementation-Title": "WoodSToX XML-processor", + "Implementation-Vendor": "woodstox.codehaus.org", + "Implementation-Version": "3.2.7", + "Manifest-Version": "1.0", + "Specification-Title": "StAX 1.0 API", + "Specification-Vendor": "http://jcp.org/en/jsr/detail?id=173", + "Specification-Version": "1.0", + }, + }, + }, + }, + expected: []string{ + "cpe:2.3:a:woodstox_codehaus_org:wstx-asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:woodstox_codehaus_org:wstx_asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:woodstox-codehaus-org:wstx_asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:woodstox-codehaus-org:wstx-asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:wstx_asl:wstx-asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:wstx-asl:wstx-asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:wstx-asl:wstx_asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:wstx_asl:wstx_asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:wstx:wstx_asl:3.2.7:*:*:*:*:*:*:*", + "cpe:2.3:a:wstx:wstx-asl:3.2.7:*:*:*:*:*:*:*", + }, + }, + { + name: "jenkins package identified via pkg type", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JenkinsPluginPkg, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "java language - multi tier manifest fields", + p: pkg.Package{ + Name: "cxf-rt-bindings-xml", + Version: "3.3.10", + FoundBy: "java-cataloger", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: "/opt/jboss/keycloak/modules/system/layers/base/org/apache/cxf/impl/main/cxf-rt-bindings-xml-3.3.10.jar", + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Automatic-Module-Name": "org.apache.cxf.binding.xml", + "Bnd-LastModified": "1615836524860", + "Build-Jdk": "1.8.0_261", + "Built-By": "dkulp", + "Bundle-ActivationPolicy": "lazy", + "Bundle-Description": "Apache CXF Runtime XML Binding", + "Bundle-DocURL": "http://cxf.apache.org", + "Bundle-License": "https://www.apache.org/licenses/LICENSE-2.0.txt", + "Bundle-ManifestVersion": "2", + "Bundle-Name": "Apache CXF Runtime XML Binding", + "Bundle-SymbolicName": "org.apache.cxf.cxf-rt-bindings-xml", + "Bundle-Vendor": "The Apache Software Foundation", + "Bundle-Version": "3.3.10", + "Created-By": "Apache Maven Bundle Plugin", + "Export-Package": "org.apache.cxf.binding.xml;version=\"3.3.10\",org.apache.cxf.binding.xml.wsdl11;version=\"3.3.10\",org.apache.cxf.binding.xml.interceptor;version=\"3.3.10\",org.apache.cxf.bindings.xformat;version=\"3.3.10\"", + "Implementation-Vendor": "The Apache Software Foundation", + "Implementation-Vendor-Id": "org.apache", + "Implementation-Version": "3.3.10", + "Import-Package": "javax.xml.bind;version=\"[0,3)\",javax.xml.bind.annotation;version=\"[0,3)\",javax.wsdl;resolution:=optional,javax.wsdl.extensions;resolution:=optional,javax.wsdl.extensions.http;resolution:=optional,javax.xml.namespace,javax.xml.stream,org.apache.cxf;version=\"[3.3,4)\",org.apache.cxf.binding;version=\"[3.3,4)\",org.apache.cxf.binding.xml,org.apache.cxf.binding.xml.interceptor,org.apache.cxf.bindings.xformat,org.apache.cxf.common.i18n;version=\"[3.3,4)\",org.apache.cxf.common.injection;version=\"[3.3,4)\",org.apache.cxf.common.logging;version=\"[3.3,4)\",org.apache.cxf.common.util;version=\"[3.3,4)\",org.apache.cxf.endpoint;version=\"[3.3,4)\",org.apache.cxf.helpers;version=\"[3.3,4)\",org.apache.cxf.interceptor;version=\"[3.3,4)\",org.apache.cxf.message;version=\"[3.3,4)\",org.apache.cxf.service.model;version=\"[3.3,4)\",org.apache.cxf.staxutils;version=\"[3.3,4)\",org.apache.cxf.tools.common;version=\"[3.3,4)\";resolution:=optional,org.apache.cxf.tools.validator;version=\"[3.3,4)\";resolution:=optional,org.apache.cxf.transport;version=\"[3.3,4)\",org.apache.cxf.wsdl;version=\"[3.3,4)\";resolution:=optional,org.apache.cxf.wsdl.http;version=\"[3.3,4)\",org.apache.cxf.wsdl.interceptors;version=\"[3.3,4)\";resolution:=optional,org.w3c.dom", + "Manifest-Version": "1.0", + "Require-Capability": "osgi.ee;filter:=\"(&(osgi.ee=JavaSE)(version=1.8))\"", + "Specification-Vendor": "The Apache Software Foundation", + "Specification-Version": "3.3.10", + "Tool": "Bnd-4.2.0.201903051501", + }, + }, + PomProperties: &pkg.PomProperties{ + Path: "META-INF/maven/org.apache.cxf/cxf-rt-bindings-xml/pom.properties", + GroupID: "org.apache.cxf", + ArtifactID: "cxf-rt-bindings-xml", + Version: "3.3.10", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:apache-software-foundation:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:apache-software-foundation:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:apache-software-foundation:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:apache:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:apache:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:apache:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:apache_software_foundation:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:apache_software_foundation:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:apache_software_foundation:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt-bindings-xml:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt-bindings-xml:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt-bindings-xml:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt-bindings:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt-bindings:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt-bindings:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf-rt:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt_bindings:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt_bindings:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt_bindings:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt_bindings_xml:cxf-rt-bindings-xml:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt_bindings_xml:cxf:3.3.10:*:*:*:*:*:*:*", + "cpe:2.3:a:cxf_rt_bindings_xml:cxf_rt_bindings_xml:3.3.10:*:*:*:*:*:*:*", + }, + }, + { + name: "rpm vendor selection", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: pkg.RpmMetadata{ + Vendor: "some-vendor", + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:some-vendor:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:some_vendor:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "rpm with epoch", + p: pkg.Package{ + Name: "name", + Version: "1:3.2", + FoundBy: "some-analyzer", + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: pkg.RpmMetadata{ + Vendor: "some-vendor", + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:1\\:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:some-vendor:name:1\\:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:some_vendor:name:1\\:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "deb with epoch", + p: pkg.Package{ + Name: "name", + Version: "1:3.2", + FoundBy: "some-analyzer", + Type: pkg.DebPkg, + MetadataType: pkg.DpkgMetadataType, + Metadata: pkg.DpkgMetadata{}, + }, + expected: []string{ + "cpe:2.3:a:name:name:1\\:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "cloudbees jenkins package identified via groupId", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JenkinsPluginPkg, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "com.cloudbees.jenkins.plugins", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "jenkins.io package identified via groupId prefix", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JenkinsPluginPkg, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "io.jenkins.plugins.name.something", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:name:something:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:something:name:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:something:something:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "jenkins.io package identified via groupId", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JenkinsPluginPkg, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "io.jenkins.plugins", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "jenkins-ci.io package identified via groupId", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JenkinsPluginPkg, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "io.jenkins-ci.plugins", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "jenkins-ci.org package identified via groupId", + p: pkg.Package{ + Name: "name", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JenkinsPluginPkg, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "org.jenkins-ci.plugins", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "jira-atlassian filtering", + p: pkg.Package{ + Name: "jira_client_core", + Version: "3.2", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "org.atlassian.jira", + ArtifactID: "jira_client_core", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:atlassian:jira-client-core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:atlassian:jira_client_core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira-client-core:jira-client-core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira-client-core:jira:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira-client-core:jira_client_core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira-client:jira-client-core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira-client:jira:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira-client:jira_client_core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira:jira-client-core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira:jira_client_core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira_client:jira-client-core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira_client:jira:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira_client:jira_client_core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira_client_core:jira-client-core:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira_client_core:jira:3.2:*:*:*:*:*:*:*", + "cpe:2.3:a:jira_client_core:jira_client_core:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "jenkins filtering", + p: pkg.Package{ + Name: "cloudbees-installation-manager", + Version: "2.89.0.33", + FoundBy: "some-analyzer", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "com.cloudbees.jenkins.modules", + ArtifactID: "cloudbees-installation-manager", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:cloudbees-installation-manager:cloudbees-installation-manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees-installation-manager:cloudbees_installation_manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees-installation:cloudbees-installation-manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees-installation:cloudbees_installation_manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees:cloudbees-installation-manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees:cloudbees_installation_manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees_installation:cloudbees-installation-manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees_installation:cloudbees_installation_manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees_installation_manager:cloudbees-installation-manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:cloudbees_installation_manager:cloudbees_installation_manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins:cloudbees-installation-manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins:cloudbees_installation_manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:modules:cloudbees-installation-manager:2.89.0.33:*:*:*:*:*:*:*", + "cpe:2.3:a:modules:cloudbees_installation_manager:2.89.0.33:*:*:*:*:*:*:*", + }, + }, + { + name: "go product and vendor candidates are wired up", + p: pkg.Package{ + Name: "github.com/someone/something", + Version: "3.2", + FoundBy: "go-cataloger", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + expected: []string{ + "cpe:2.3:a:someone:something:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "go product with vendor candidates and an extra sub-item", + p: pkg.Package{ + Name: "github.com/someone/something/more", + Version: "3.2", + FoundBy: "go-cataloger", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + expected: []string{ + "cpe:2.3:a:someone:something\\/more:3.2:*:*:*:*:*:*:*", + }, + }, + { + name: "generate no CPEs for indeterminate golang package name", + p: pkg.Package{ + Name: "github.com/what", + Version: "3.2", + FoundBy: "go-cataloger", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + expected: []string{}, + }, + { + name: "regression: handlebars within java archive", + p: pkg.Package{ + Name: "handlebars", + Version: "3.0.8", + Type: pkg.JavaPkg, + Language: pkg.Java, + FoundBy: "java-cataloger", + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Extension-Name": "handlebars", + "Group-Id": "org.jenkins-ci.ui", + "Hudson-Version": "2.204", + "Implementation-Title": "handlebars", + "Implementation-Version": "3.0.8", + "Plugin-Version": "3.0.8", + "Short-Name": "handlebars", + }, + }, + PomProperties: &pkg.PomProperties{ + GroupID: "org.jenkins-ci.ui", + ArtifactID: "handlebars", + Version: "3.0.8", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:handlebars:handlebars:3.0.8:*:*:*:*:*:*:*", + "cpe:2.3:a:handlebarsjs:handlebars:3.0.8:*:*:*:*:*:*:*", // important! + "cpe:2.3:a:jenkins-ci:handlebars:3.0.8:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins:handlebars:3.0.8:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins_ci:handlebars:3.0.8:*:*:*:*:*:*:*", + "cpe:2.3:a:ui:handlebars:3.0.8:*:*:*:*:*:*:*", + }, + }, + { + name: "regression: jenkins plugin active-directory", + p: pkg.Package{ + Name: "active-directory", + Version: "2.25.1", + Type: pkg.JenkinsPluginPkg, + FoundBy: "java-cataloger", + Language: pkg.Java, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Extension-Name": "active-directory", + "Group-Id": "org.jenkins-ci.plugins", + }, + }, + PomProperties: &pkg.PomProperties{ + GroupID: "org.jenkins-ci.plugins", + ArtifactID: "org.jenkins-ci.plugins", + Version: "2.25.1", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:active-directory:active-directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:active-directory:active_directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:active:active-directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:active:active_directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:active_directory:active-directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:active_directory:active_directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins-ci:active-directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins-ci:active_directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins:active-directory:2.25.1:*:*:*:*:*:*:*", // important! + "cpe:2.3:a:jenkins:active_directory:2.25.1:*:*:*:*:*:*:*", // important! + "cpe:2.3:a:jenkins_ci:active-directory:2.25.1:*:*:*:*:*:*:*", + "cpe:2.3:a:jenkins_ci:active_directory:2.25.1:*:*:*:*:*:*:*", + }, + }, + { + name: "regression: special characters in CPE should result in no generation", + p: pkg.Package{ + Name: "bundler", + Version: "2.1.4", + Type: pkg.GemPkg, + FoundBy: "gem-cataloger", + Language: pkg.Ruby, + MetadataType: pkg.GemMetadataType, + Metadata: pkg.GemMetadata{ + Name: "bundler", + Version: "2.1.4", + Authors: []string{ + "jessica lynn suttles", + "stephanie morillo", + "david rodríguez", + "andré medeiros", + }, + }, + }, + expected: []string{ + "cpe:2.3:a:*:bundler:2.1.4:*:*:*:*:*:*:*", + "cpe:2.3:a:bundler:bundler:2.1.4:*:*:*:*:*:*:*", + "cpe:2.3:a:ruby-lang:bundler:2.1.4:*:*:*:*:*:*:*", + "cpe:2.3:a:ruby:bundler:2.1.4:*:*:*:*:*:*:*", + "cpe:2.3:a:ruby_lang:bundler:2.1.4:*:*:*:*:*:*:*", + "cpe:2.3:a:jessica-lynn-suttles:bundler:2.1.4:*:*:*:*:*:*:*", + "cpe:2.3:a:jessica_lynn_suttles:bundler:2.1.4:*:*:*:*:*:*:*", + "cpe:2.3:a:stephanie-morillo:bundler:2.1.4:*:*:*:*:*:*:*", + "cpe:2.3:a:stephanie_morillo:bundler:2.1.4:*:*:*:*:*:*:*", + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := Generate(test.p) + + expectedCpeSet := set.NewStringSet(test.expected...) + actualCpeSet := set.NewStringSet() + for _, a := range actual { + actualCpeSet.Add(pkg.CPEString(a)) + } + + extra := strset.Difference(actualCpeSet, expectedCpeSet).List() + sort.Strings(extra) + if len(extra) > 0 { + t.Errorf("found extra CPEs:") + } + for _, d := range extra { + fmt.Printf(" %q,\n", d) + } + + missing := strset.Difference(expectedCpeSet, actualCpeSet).List() + sort.Strings(missing) + if len(missing) > 0 { + t.Errorf("missing CPEs:") + } + for _, d := range missing { + fmt.Printf(" %q,\n", d) + } + }) + } +} + +func TestCandidateProducts(t *testing.T) { + tests := []struct { + name string + p pkg.Package + expected []string + }{ + { + name: "apache-cassandra", + p: pkg.Package{ + Name: "apache-cassandra", + Type: pkg.JavaPkg, + }, + expected: []string{"cassandra" /* <-- known good names | default guess --> */, "apache-cassandra", "apache_cassandra"}, + }, + { + name: "springframework", + p: pkg.Package{ + Name: "springframework", + Type: pkg.JavaPkg, + }, + expected: []string{"spring_framework", "springsource_spring_framework" /* <-- known good names | default guess --> */, "springframework"}, + }, + { + name: "java", + p: pkg.Package{ + Name: "some-java-package-with-group-id", + Type: pkg.JavaPkg, + Language: pkg.Java, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "com.apple.itunes", + }, + }, + }, + expected: []string{"itunes", "some-java-package-with-group-id", "some_java_package_with_group_id"}, + }, + { + name: "java-with-asterisk", + p: pkg.Package{ + Name: "some-java-package-with-group-id", + Type: pkg.JavaPkg, + Language: pkg.Java, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "com.apple.itunes.*", + }, + }, + }, + expected: []string{"itunes", "some-java-package-with-group-id", "some_java_package_with_group_id"}, + }, + { + name: "jenkins-plugin", + p: pkg.Package{ + Name: "some-jenkins-plugin", + Type: pkg.JenkinsPluginPkg, + Language: pkg.Java, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "com.cloudbees.jenkins.plugins", + }, + }, + }, + expected: []string{"some-jenkins-plugin", "some_jenkins_plugin", "jenkins"}, + }, + { + name: "javascript", + p: pkg.Package{ + Name: "handlebars.js", + Type: pkg.NpmPkg, + }, + expected: []string{"handlebars" /* <-- known good names | default guess --> */, "handlebars.js"}, + }, + { + name: "gem", + p: pkg.Package{ + Name: "RedCloth", + Type: pkg.GemPkg, + }, + expected: []string{"redcloth_library" /* <-- known good names | default guess --> */, "RedCloth"}, + }, + { + name: "python", + p: pkg.Package{ + Name: "python-rrdtool", + Type: pkg.PythonPkg, + }, + expected: []string{"rrdtool" /* <-- known good names | default guess --> */, "python-rrdtool", "python_rrdtool"}, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.ElementsMatch(t, test.expected, candidateProducts(test.p)) + }) + } +} + +func TestCandidateVendor(t *testing.T) { + tests := []struct { + name string + p pkg.Package + expected []string + }{ + { + name: "elasticsearch", + p: pkg.Package{ + Name: "elasticsearch", + Type: pkg.JavaPkg, + }, + expected: []string{"elastic" /* <-- known good names | default guess --> */, "elasticsearch"}, + }, + { + name: "log4j", + p: pkg.Package{ + Name: "log4j", + Type: pkg.JavaPkg, + }, + expected: []string{"apache" /* <-- known good names | default guess --> */, "log4j"}, + }, + } + + for _, test := range tests { + t.Run(fmt.Sprintf("%+v %+v", test.p, test.expected), func(t *testing.T) { + assert.ElementsMatch(t, test.expected, candidateVendors(test.p)) + }) + } +} + +func Test_generateSubSelections(t *testing.T) { + tests := []struct { + field string + expected []string + }{ + { + field: "jenkins", + expected: []string{"jenkins"}, + }, + { + field: "jenkins-ci", + expected: []string{"jenkins", "jenkins-ci"}, + }, + { + field: "jenkins--ci", + expected: []string{"jenkins", "jenkins-ci"}, + }, + { + field: "jenkins_ci_tools", + expected: []string{"jenkins", "jenkins_ci", "jenkins_ci_tools"}, + }, + { + field: "-jenkins", + expected: []string{"jenkins"}, + }, + { + field: "jenkins_", + expected: []string{"jenkins"}, + }, + { + field: "", + expected: nil, + }, + { + field: "-", + expected: nil, + }, + { + field: "_", + expected: nil, + }, + } + for _, test := range tests { + t.Run(test.field, func(t *testing.T) { + assert.ElementsMatch(t, test.expected, generateSubSelections(test.field)) + }) + } +} + +func Test_addSeparatorVariations(t *testing.T) { + tests := []struct { + input []string + expected []string + }{ + { + input: []string{"jenkins-ci"}, + expected: []string{"jenkins-ci", "jenkins_ci"}, //, "jenkinsci"}, + }, + { + input: []string{"jenkins_ci"}, + expected: []string{"jenkins_ci", "jenkins-ci"}, //, "jenkinsci"}, + }, + { + input: []string{"jenkins"}, + expected: []string{"jenkins"}, + }, + { + input: []string{"jenkins-ci", "circle-ci"}, + expected: []string{"jenkins-ci", "jenkins_ci", "circle-ci", "circle_ci"}, //, "jenkinsci", "circleci"}, + }, + } + for _, test := range tests { + t.Run(strings.Join(test.input, ","), func(t *testing.T) { + val := newFieldCandidateSet(test.input...) + addDelimiterVariations(val) + assert.ElementsMatch(t, test.expected, val.values()) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/go.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/go.go new file mode 100644 index 0000000000000000000000000000000000000000..0d9487017e22a271817c85fbb02ffcc0feefd8db --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/go.go @@ -0,0 +1,61 @@ +package cpe + +import ( + "net/url" + "strings" +) + +// candidateProductForGo attempts to find a single product name in a best-effort attempt. This implementation prefers +// to return no vendor over returning potentially nonsensical results. +func candidateProductForGo(name string) string { + // note: url.Parse requires a scheme for correct processing, which a golang module will not have, so one is provided. + u, err := url.Parse("http://" + name) + if err != nil { + return "" + } + + cleanPath := strings.Trim(u.Path, "/") + pathElements := strings.Split(cleanPath, "/") + + switch u.Host { + case "golang.org", "gopkg.in": + return cleanPath + case "google.golang.org": + return pathElements[0] + } + + if len(pathElements) < 2 { + return "" + } + + // returning the rest of the path here means longer CPEs, it helps avoiding false-positives + // ref: https://github.com/anchore/grype/issues/676 + return strings.Join(pathElements[1:], "/") +} + +// candidateVendorForGo attempts to find a single vendor name in a best-effort attempt. This implementation prefers +// to return no vendor over returning potentially nonsensical results. +func candidateVendorForGo(name string) string { + // note: url.Parse requires a scheme for correct processing, which a golang module will not have, so one is provided. + u, err := url.Parse("http://" + name) + if err != nil { + return "" + } + + cleanPath := strings.Trim(u.Path, "/") + + switch u.Host { + case "google.golang.org": + return "google" + case "golang.org": + return "golang" + case "gopkg.in": + return "" + } + + pathElements := strings.Split(cleanPath, "/") + if len(pathElements) < 2 { + return "" + } + return pathElements[0] +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/go_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/go_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e65ef545cf49ea80ea253504d3b499dfadc97ac5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/go_test.go @@ -0,0 +1,103 @@ +package cpe + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestCandidateProductForGo(t *testing.T) { + tests := []struct { + pkg string + expected string + }{ + { + pkg: "github.com/someone/something", + expected: "something", + }, + { + pkg: "golang.org/x/xerrors", + expected: "x/xerrors", + }, + { + pkg: "gopkg.in/yaml.v2", + expected: "yaml.v2", + }, + { + pkg: "place", + expected: "", + }, + { + pkg: "place.com/", + expected: "", + }, + { + pkg: "place.com/someone-or-thing", + expected: "", + }, + { + pkg: "google.golang.org/genproto/googleapis/rpc/status", + expected: "genproto", + }, + { + pkg: "github.com/someone/something/long/package/name", + expected: "something/long/package/name", + }, + { + pkg: "", + expected: "", + }, + } + + for _, test := range tests { + t.Run(test.pkg, func(t *testing.T) { + assert.Equal(t, test.expected, candidateProductForGo(test.pkg)) + }) + } +} + +func TestCandidateVendorForGo(t *testing.T) { + tests := []struct { + pkg string + expected string + }{ + { + pkg: "github.com/someone/something", + expected: "someone", + }, + { + pkg: "golang.org/x/xerrors", + expected: "golang", + }, + { + pkg: "gopkg.in/yaml.v2", + expected: "", + }, + { + pkg: "place", + expected: "", + }, + { + pkg: "place.com/", + expected: "", + }, + { + pkg: "place.com/someone-or-thing", + expected: "", + }, + { + pkg: "google.golang.org/genproto/googleapis/rpc/status", + expected: "google", + }, + { + pkg: "github.com/someone/something/long/package/name", + expected: "someone", + }, + } + + for _, test := range tests { + t.Run(test.pkg, func(t *testing.T) { + assert.Equal(t, test.expected, candidateVendorForGo(test.pkg)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/java.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/java.go new file mode 100644 index 0000000000000000000000000000000000000000..552e04f4e27b6fbe638fc3b64a0c43c5d8a59bd4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/java.go @@ -0,0 +1,295 @@ +package cpe + +import ( + "strings" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/pkg" + "github.com/scylladb/go-set/strset" +) + +var ( + forbiddenProductGroupIDFields = strset.New("plugin", "plugins", "client") + forbiddenVendorGroupIDFields = strset.New("plugin", "plugins") + + domains = []string{ + "com", + "org", + "net", + "io", + "be", + } + + primaryJavaManifestGroupIDFields = []string{ + "Extension-Name", + "Specification-Vendor", + "Implementation-Vendor", + "Bundle-SymbolicName", + "Implementation-Vendor-Id", + "Implementation-Title", + "Bundle-Activator", + } + secondaryJavaManifestGroupIDFields = []string{ + "Automatic-Module-Name", + "Main-Class", + "Package", + } + javaManifestNameFields = []string{ + "Specification-Vendor", + "Implementation-Vendor", + } +) + +func candidateProductsForJava(p pkg.Package) []string { + return productsFromArtifactAndGroupIDs(artifactIDFromJavaPackage(p), GroupIDsFromJavaPackage(p)) +} + +func candidateVendorsForJava(p pkg.Package) fieldCandidateSet { + gidVendors := vendorsFromGroupIDs(GroupIDsFromJavaPackage(p)) + nameVendors := vendorsFromJavaManifestNames(p) + return newFieldCandidateSetFromSets(gidVendors, nameVendors) +} + +func vendorsFromJavaManifestNames(p pkg.Package) fieldCandidateSet { + vendors := newFieldCandidateSet() + + metadata, ok := p.Metadata.(pkg.JavaMetadata) + if !ok { + return vendors + } + + if metadata.Manifest == nil { + return vendors + } + + for _, name := range javaManifestNameFields { + if metadata.Manifest.Main != nil { + if value, exists := metadata.Manifest.Main[name]; exists { + if !startsWithTopLevelDomain(value) { + vendors.add(fieldCandidate{ + value: normalizePersonName(value), + disallowSubSelections: true, + }) + } + } + } + if metadata.Manifest.NamedSections != nil { + for _, section := range metadata.Manifest.NamedSections { + if section == nil { + continue + } + if value, exists := section[name]; exists { + if !startsWithTopLevelDomain(value) { + vendors.add(fieldCandidate{ + value: normalizePersonName(value), + disallowSubSelections: true, + }) + } + } + } + } + } + + return vendors +} + +func vendorsFromGroupIDs(groupIDs []string) fieldCandidateSet { + vendors := newFieldCandidateSet() + for _, groupID := range groupIDs { + for i, field := range strings.Split(groupID, ".") { + field = strings.TrimSpace(field) + + if len(field) == 0 { + continue + } + + if forbiddenVendorGroupIDFields.Has(strings.ToLower(field)) { + continue + } + + if i == 0 { + continue + } + + vendors.addValue(field) + } + } + + return vendors +} + +func productsFromArtifactAndGroupIDs(artifactID string, groupIDs []string) []string { + products := strset.New() + if artifactID != "" { + products.Add(artifactID) + } + + for _, groupID := range groupIDs { + isPlugin := strings.Contains(artifactID, "plugin") || strings.Contains(groupID, "plugin") + + for i, field := range strings.Split(groupID, ".") { + field = strings.TrimSpace(field) + + if len(field) == 0 { + continue + } + + // don't add this field as a name if the name is implying the package is a plugin or client + if forbiddenProductGroupIDFields.Has(strings.ToLower(field)) { + continue + } + + if i <= 1 { + continue + } + + // umbrella projects tend to have sub components that either start or end with the project name. We expect + // to identify fields that may represent the umbrella project, and not fields that indicate auxiliary + // information about the package. + couldBeProjectName := strings.HasPrefix(artifactID, field) || strings.HasSuffix(artifactID, field) + if artifactID == "" || (couldBeProjectName && !isPlugin) { + products.Add(field) + } + } + } + + return products.List() +} + +func artifactIDFromJavaPackage(p pkg.Package) string { + metadata, ok := p.Metadata.(pkg.JavaMetadata) + if !ok { + return "" + } + + if metadata.PomProperties == nil { + return "" + } + + artifactID := strings.TrimSpace(metadata.PomProperties.ArtifactID) + if startsWithTopLevelDomain(artifactID) && len(strings.Split(artifactID, ".")) > 1 { + // there is a strong indication that the artifact ID is really a group ID, don't use it + return "" + } + return artifactID +} + +func GroupIDsFromJavaPackage(p pkg.Package) (groupIDs []string) { + metadata, ok := p.Metadata.(pkg.JavaMetadata) + if !ok { + return nil + } + + groupIDs = append(groupIDs, groupIDsFromPomProperties(metadata.PomProperties)...) + groupIDs = append(groupIDs, groupIDsFromPomProject(metadata.PomProject)...) + groupIDs = append(groupIDs, groupIDsFromJavaManifest(metadata.Manifest)...) + + return groupIDs +} + +func groupIDsFromPomProperties(properties *pkg.PomProperties) (groupIDs []string) { + if properties == nil { + return nil + } + + if startsWithTopLevelDomain(properties.GroupID) { + groupIDs = append(groupIDs, cleanGroupID(properties.GroupID)) + } + + // sometimes the publisher puts the group ID in the artifact ID field unintentionally + if startsWithTopLevelDomain(properties.ArtifactID) && len(strings.Split(properties.ArtifactID, ".")) > 1 { + // there is a strong indication that the artifact ID is really a group ID + groupIDs = append(groupIDs, cleanGroupID(properties.ArtifactID)) + } + + return groupIDs +} + +func groupIDsFromPomProject(project *pkg.PomProject) (groupIDs []string) { + if project == nil { + return nil + } + + // extract the project info... + groupIDs = addGroupIDsFromGroupIDsAndArtifactID(project.GroupID, project.ArtifactID) + + if project.Parent == nil { + return groupIDs + } + + // extract the parent project info... + groupIDs = append(groupIDs, addGroupIDsFromGroupIDsAndArtifactID(project.Parent.GroupID, project.Parent.ArtifactID)...) + + return groupIDs +} + +func addGroupIDsFromGroupIDsAndArtifactID(groupID, artifactID string) (groupIDs []string) { + if startsWithTopLevelDomain(groupID) { + groupIDs = append(groupIDs, cleanGroupID(groupID)) + } + + // sometimes the publisher puts the group ID in the artifact ID field unintentionally + if startsWithTopLevelDomain(artifactID) && len(strings.Split(artifactID, ".")) > 1 { + // there is a strong indication that the artifact ID is really a group ID + groupIDs = append(groupIDs, cleanGroupID(artifactID)) + } + return groupIDs +} + +func groupIDsFromJavaManifest(manifest *pkg.JavaManifest) []string { + if manifest == nil { + return nil + } + + // try the common manifest fields first for a set of candidates + groupIDs := getManifestFieldGroupIDs(manifest, primaryJavaManifestGroupIDFields) + + if len(groupIDs) != 0 { + return groupIDs + } + + // if we haven't found anything yet, let's try a last ditch effort: + // attempt to get group-id-like info from the MANIFEST.MF "Automatic-Module-Name" and "Extension-Name" field. + // for more info see pkg:maven/commons-io/commons-io@2.8.0 within cloudbees/cloudbees-core-mm:2.263.4.2 + // at /usr/share/jenkins/jenkins.war:WEB-INF/plugins/analysis-model-api.hpi:WEB-INF/lib/commons-io-2.8.0.jar + // as well as the ant package from cloudbees/cloudbees-core-mm:2.277.2.4-ra. + return getManifestFieldGroupIDs(manifest, secondaryJavaManifestGroupIDFields) +} + +func getManifestFieldGroupIDs(manifest *pkg.JavaManifest, fields []string) (groupIDs []string) { + if manifest == nil { + return nil + } + + for _, name := range fields { + if value, exists := manifest.Main[name]; exists { + if startsWithTopLevelDomain(value) { + groupIDs = append(groupIDs, cleanGroupID(value)) + } + } + for _, section := range manifest.NamedSections { + if value, exists := section[name]; exists { + if startsWithTopLevelDomain(value) { + groupIDs = append(groupIDs, cleanGroupID(value)) + } + } + } + } + + return groupIDs +} + +func cleanGroupID(groupID string) string { + return strings.TrimSpace(removeOSCIDirectives(groupID)) +} + +func removeOSCIDirectives(groupID string) string { + // for example: + // org.bar;uses:=“org.foo” -> org.bar + // more about OSGI directives see https://spring.io/blog/2008/10/20/understanding-the-osgi-uses-directive/ + return strings.Split(groupID, ";")[0] +} + +func startsWithTopLevelDomain(value string) bool { + return internal.HasAnyOfPrefixes(value, domains...) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/java_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/java_test.go new file mode 100644 index 0000000000000000000000000000000000000000..0f87e5b56fe5f2485c9d4aa4958eda4e93c57631 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/java_test.go @@ -0,0 +1,428 @@ +package cpe + +import ( + "strings" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_productsFromArtifactAndGroupIDs(t *testing.T) { + tests := []struct { + groupIDs []string + artifactID string + expected []string + }{ + { + groupIDs: []string{"org.sonatype.nexus"}, + artifactID: "nexus-extender", + expected: []string{"nexus", "nexus-extender"}, + }, + { + groupIDs: []string{"org.sonatype.nexus"}, + expected: []string{"nexus"}, + }, + { + groupIDs: []string{"org.jenkins-ci.plugins"}, + artifactID: "ant", + expected: []string{"ant"}, + }, + { + groupIDs: []string{"org.jenkins-ci.plugins"}, + artifactID: "antisamy-markup-formatter", + expected: []string{"antisamy-markup-formatter"}, + }, + { + groupIDs: []string{"io.jenkins.plugins"}, + artifactID: "aws-global-configuration", + expected: []string{"aws-global-configuration"}, + }, + { + groupIDs: []string{"com.cloudbees.jenkins.plugins"}, + artifactID: "cloudbees-servicenow-jenkins-plugin", + expected: []string{"cloudbees-servicenow-jenkins-plugin"}, + }, + { + groupIDs: []string{"com.atlassian.confluence.plugins"}, + artifactID: "confluence-mobile-plugin", + expected: []string{"confluence-mobile-plugin"}, + }, + { + groupIDs: []string{"com.atlassian.confluence.plugins"}, + artifactID: "confluence-view-file-macro", + expected: []string{"confluence-view-file-macro"}, + }, + { + groupIDs: []string{"com.google.guava"}, + artifactID: "failureaccess", + expected: []string{"failureaccess"}, + }, + } + for _, test := range tests { + t.Run(strings.Join(test.groupIDs, ",")+":"+test.artifactID, func(t *testing.T) { + actual := productsFromArtifactAndGroupIDs(test.artifactID, test.groupIDs) + assert.ElementsMatch(t, test.expected, actual, "different products") + }) + } +} + +func Test_candidateProductsForJava(t *testing.T) { + tests := []struct { + name string + pkg pkg.Package + expected []string + }{ + { + name: "duplicate groupID in artifactID field", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "org.sonatype.nexus", + ArtifactID: "org.sonatype.nexus", + }, + }, + }, + expected: []string{"nexus"}, + }, + { + name: "detect groupID-like value in artifactID field", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + ArtifactID: "org.sonatype.nexus", + }, + }, + }, + expected: []string{"nexus"}, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := candidateProductsForJava(test.pkg) + assert.ElementsMatch(t, test.expected, actual, "different products") + }) + } +} + +func Test_vendorsFromGroupIDs(t *testing.T) { + tests := []struct { + groupID string + expected []string + }{ + { + groupID: "org.sonatype.nexus", + expected: []string{"sonatype", "nexus"}, + }, + { + groupID: "org.jenkins-ci.plugins", + expected: []string{"jenkins-ci"}, + }, + { + groupID: "io.jenkins.plugins", + expected: []string{"jenkins"}, + }, + { + groupID: "com.cloudbees.jenkins.plugins", + expected: []string{"cloudbees", "jenkins"}, + }, + { + groupID: "com.atlassian.confluence.plugins", + expected: []string{"atlassian", "confluence"}, + }, + { + groupID: "com.google.guava", + expected: []string{"google", "guava"}, + }, + } + for _, test := range tests { + t.Run(test.groupID, func(t *testing.T) { + assert.ElementsMatch(t, test.expected, vendorsFromGroupIDs([]string{test.groupID}).values(), "different vendors") + }) + } +} + +func Test_groupIDsFromJavaPackage(t *testing.T) { + tests := []struct { + name string + pkg pkg.Package + expects []string + }{ + { + name: "go case", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: "io.jenkins-ci.plugin.thing;version='[2,3)'", + }, + }, + }, + expects: []string{"io.jenkins-ci.plugin.thing"}, + }, + { + name: "from artifactID", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + ArtifactID: "io.jenkins-ci.plugin.thing; version='[2,3)' ; org.something.else", + }, + }, + }, + expects: []string{"io.jenkins-ci.plugin.thing"}, + }, + { + name: "from main Extension-Name field", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Extension-Name": "io.jenkins-ci.plugin.thing", + }, + }, + }, + }, + expects: []string{"io.jenkins-ci.plugin.thing"}, + }, + { + name: "from named section Extension-Name field", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + NamedSections: map[string]map[string]string{ + "section": { + "Extension-Name": "io.jenkins-ci.plugin.thing", + }, + }, + }, + }, + }, + expects: []string{"io.jenkins-ci.plugin.thing"}, + }, + { + name: "from main field - tier 1", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + // positive cases + // tier 1 + "Extension-Name": "io.jenkins-ci.plugin.1", + "Specification-Vendor": "io.jenkins-ci.plugin.2", + "Implementation-Vendor": "io.jenkins-ci.plugin.3", + "Bundle-SymbolicName": "io.jenkins-ci.plugin.4", + "Implementation-Vendor-Id": "io.jenkins-ci.plugin.5", + "Implementation-Title": "io.jenkins-ci.plugin.6", + "Bundle-Activator": "io.jenkins-ci.plugin.7", + // tier 2 + "Automatic-Module-Name": "io.jenkins-ci.plugin.8", + "Main-Class": "io.jenkins-ci.plugin.9", + "Package": "io.jenkins-ci.plugin.10", + }, + }, + }, + }, + expects: []string{ + "io.jenkins-ci.plugin.1", + "io.jenkins-ci.plugin.2", + "io.jenkins-ci.plugin.3", + "io.jenkins-ci.plugin.4", + "io.jenkins-ci.plugin.5", + "io.jenkins-ci.plugin.6", + "io.jenkins-ci.plugin.7", + }, + }, + { + name: "from main field - tier 2", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + // positive cases + "Automatic-Module-Name": "io.jenkins-ci.plugin.8", + "Main-Class": "io.jenkins-ci.plugin.9", + "Package": "io.jenkins-ci.plugin.10", + }, + }, + }, + }, + expects: []string{ + "io.jenkins-ci.plugin.8", + "io.jenkins-ci.plugin.9", + "io.jenkins-ci.plugin.10", + }, + }, + { + name: "from main field - negative cases", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + // negative cases + "Extension-Name": "not.a-group.id", + "bogus": "io.jenkins-ci.plugin.please-dont-find-me", + }, + }, + }, + }, + expects: nil, + }, + { + name: "from named section field - tier 1", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + NamedSections: map[string]map[string]string{ + "section": { + // positive cases + // tier 1 + "Extension-Name": "io.jenkins-ci.plugin.1", + "Specification-Vendor": "io.jenkins-ci.plugin.2", + "Implementation-Vendor": "io.jenkins-ci.plugin.3", + "Bundle-SymbolicName": "io.jenkins-ci.plugin.4", + "Implementation-Vendor-Id": "io.jenkins-ci.plugin.5", + "Implementation-Title": "io.jenkins-ci.plugin.6", + "Bundle-Activator": "io.jenkins-ci.plugin.7", + // tier 2 + "Automatic-Module-Name": "io.jenkins-ci.plugin.8", + "Main-Class": "io.jenkins-ci.plugin.9", + "Package": "io.jenkins-ci.plugin.10", + }, + }, + }, + }, + }, + expects: []string{ + "io.jenkins-ci.plugin.1", + "io.jenkins-ci.plugin.2", + "io.jenkins-ci.plugin.3", + "io.jenkins-ci.plugin.4", + "io.jenkins-ci.plugin.5", + "io.jenkins-ci.plugin.6", + "io.jenkins-ci.plugin.7", + }, + }, + { + name: "from named section field - negative cases", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + NamedSections: map[string]map[string]string{ + "section": { + // negative cases + "Extension-Name": "not.a-group.id", + "bogus": "io.jenkins-ci.plugin.please-dont-find-me", + }, + }, + }, + }, + }, + expects: nil, + }, + { + name: "no manifest or pom info", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{}, + }, + expects: nil, + }, + { + name: "no java info", + pkg: pkg.Package{}, + expects: nil, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.ElementsMatch(t, test.expects, GroupIDsFromJavaPackage(test.pkg)) + }) + } +} + +func Test_artifactIDFromJavaPackage(t *testing.T) { + tests := []struct { + name string + pkg pkg.Package + expects string + }{ + { + name: "go case", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + ArtifactID: "cloudbees-installation-manager", + }, + }, + }, + expects: "cloudbees-installation-manager", + }, + { + name: "ignore groupID-like things", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + ArtifactID: "io.jenkins-ci.plugin.thing", + }, + }, + }, + expects: "", + }, + { + name: "no java info", + pkg: pkg.Package{}, + expects: "", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expects, artifactIDFromJavaPackage(test.pkg)) + }) + } +} + +func Test_vendorsFromJavaManifestNames(t *testing.T) { + tests := []struct { + name string + pkg pkg.Package + expects []string + }{ + { + name: "from manifest named section fields", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + NamedSections: map[string]map[string]string{ + "section": { + // positive cases + "Specification-Vendor": "Alex Goodman", + "Implementation-Vendor": "William Goodman", + }, + }, + }, + }, + }, + expects: []string{"alex_goodman", "william_goodman"}, + }, + { + name: "from manifest named section fields - negative cases", + pkg: pkg.Package{ + Metadata: pkg.JavaMetadata{ + Manifest: &pkg.JavaManifest{ + NamedSections: map[string]map[string]string{ + "section": { + // negative cases + "Specification-Vendor": "io.jenkins-ci.plugin.thing", + "Implementation-Vendor-ID": "William Goodman", + }, + }, + }, + }, + }, + expects: nil, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.ElementsMatch(t, test.expects, vendorsFromJavaManifestNames(test.pkg).values()) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/python.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/python.go new file mode 100644 index 0000000000000000000000000000000000000000..fca061035d5a9882ee033e1e35243ede8a12bf9e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/python.go @@ -0,0 +1,29 @@ +package cpe + +import "github.com/anchore/syft/syft/pkg" + +func candidateVendorsForPython(p pkg.Package) fieldCandidateSet { + metadata, ok := p.Metadata.(pkg.PythonPackageMetadata) + if !ok { + return nil + } + + vendors := newFieldCandidateSet() + + if metadata.Author != "" { + vendors.add(fieldCandidate{ + value: normalizePersonName(metadata.Author), + disallowSubSelections: true, + disallowDelimiterVariations: true, + }) + } + + if metadata.AuthorEmail != "" { + vendors.add(fieldCandidate{ + value: normalizePersonName(stripEmailSuffix(metadata.AuthorEmail)), + disallowSubSelections: true, + }) + } + + return vendors +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/rpm.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/rpm.go new file mode 100644 index 0000000000000000000000000000000000000000..d8c31654445828c788d2f57b2f9284c82d45d213 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/rpm.go @@ -0,0 +1,21 @@ +package cpe + +import "github.com/anchore/syft/syft/pkg" + +func candidateVendorsForRPM(p pkg.Package) fieldCandidateSet { + metadata, ok := p.Metadata.(pkg.RpmMetadata) + if !ok { + return nil + } + + vendors := newFieldCandidateSet() + + if metadata.Vendor != "" { + vendors.add(fieldCandidate{ + value: normalizeName(metadata.Vendor), + disallowSubSelections: true, + }) + } + + return vendors +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/ruby.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/ruby.go new file mode 100644 index 0000000000000000000000000000000000000000..b89e2f6da89d0f69548fe6b9a0ddb934f3326192 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/ruby.go @@ -0,0 +1,21 @@ +package cpe + +import "github.com/anchore/syft/syft/pkg" + +func candidateVendorsForRuby(p pkg.Package) fieldCandidateSet { + metadata, ok := p.Metadata.(pkg.GemMetadata) + if !ok { + return nil + } + + vendors := newFieldCandidateSet() + + for _, author := range metadata.Authors { + // author could be a name or an email + vendors.add(fieldCandidate{ + value: normalizePersonName(stripEmailSuffix(author)), + disallowSubSelections: true, + }) + } + return vendors +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/utils.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/utils.go new file mode 100644 index 0000000000000000000000000000000000000000..e048063d98c545ce8be6060c94d1dd3edc9f96b7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/utils.go @@ -0,0 +1,21 @@ +package cpe + +import "strings" + +func stripEmailSuffix(email string) string { + return strings.Split(email, "@")[0] +} + +func normalizePersonName(name string) string { + name = strings.TrimSpace(strings.ToLower(name)) + for _, value := range []string{"-", " ", "."} { + name = strings.ReplaceAll(name, value, "_") + } + return strings.TrimPrefix(name, "the_") +} + +func normalizeName(name string) string { + name = strings.Split(name, ",")[0] + name = strings.TrimSpace(strings.ToLower(name)) + return strings.ReplaceAll(name, " ", "") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/utils_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/utils_test.go new file mode 100644 index 0000000000000000000000000000000000000000..8e3c3cbc6c8b39e1554ee9f491c1dac2f06ba905 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/cpe/utils_test.go @@ -0,0 +1,71 @@ +package cpe + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func Test_normalizeName(t *testing.T) { + tests := []struct { + input string + expects string + }{ + { + // note: extra spaces + input: " Alex Goodman ", + expects: "alexgoodman", + }, + { + input: "Alex Goodman, LLC", + expects: "alexgoodman", + }, + { + input: "alex.goodman", + expects: "alex.goodman", + }, + } + for _, test := range tests { + t.Run(test.input, func(t *testing.T) { + assert.Equal(t, test.expects, normalizeName(test.input)) + }) + } +} + +func Test_normalizePersonName(t *testing.T) { + tests := []struct { + input string + expects string + }{ + { + // note: extra spaces + input: " Alex Goodman ", + expects: "alex_goodman", + }, + { + input: "Alex Goodman", + expects: "alex_goodman", + }, + { + input: "Alex.Goodman", + expects: "alex_goodman", + }, + { + input: "Alex.Goodman", + expects: "alex_goodman", + }, + { + input: "AlexGoodman", + expects: "alexgoodman", + }, + { + input: "The Apache Software Foundation", + expects: "apache_software_foundation", + }, + } + for _, test := range tests { + t.Run(test.input, func(t *testing.T) { + assert.Equal(t, test.expects, normalizePersonName(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/generic_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/generic_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..5de3666bffab4c58c77c0940f765f18e69b0d577 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/generic_cataloger.go @@ -0,0 +1,136 @@ +/* +Package common provides generic utilities used by multiple catalogers. +*/ +package common + +import ( + "fmt" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +// GenericCataloger implements the Catalog interface and is responsible for dispatching the proper parser function for +// a given path or glob pattern. This is intended to be reusable across many package cataloger types. +type GenericCataloger struct { + globParsers map[string]ParserFn + pathParsers map[string]ParserFn + postProcessors []PostProcessFunc + upstreamCataloger string +} + +type PostProcessFunc func(resolver source.FileResolver, location source.Location, p *pkg.Package) error + +// NewGenericCataloger if provided path-to-parser-function and glob-to-parser-function lookups creates a GenericCataloger +func NewGenericCataloger(pathParsers map[string]ParserFn, globParsers map[string]ParserFn, upstreamCataloger string, postProcessors ...PostProcessFunc) *GenericCataloger { + return &GenericCataloger{ + globParsers: globParsers, + pathParsers: pathParsers, + postProcessors: postProcessors, + upstreamCataloger: upstreamCataloger, + } +} + +// Name returns a string that uniquely describes the upstream cataloger that this Generic Cataloger represents. +func (c *GenericCataloger) Name() string { + return c.upstreamCataloger +} + +// Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing the catalog source. +func (c *GenericCataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + var packages []pkg.Package + var relationships []artifact.Relationship + + for location, parser := range c.selectFiles(resolver) { + contentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + // TODO: fail or log? + return nil, nil, fmt.Errorf("unable to fetch contents at location=%v: %w", location, err) + } + + discoveredPackages, discoveredRelationships, err := parser(location.RealPath, contentReader) + internal.CloseAndLogError(contentReader, location.VirtualPath) + if err != nil { + // TODO: should we fail? or only log? + log.Warnf("cataloger '%s' failed to parse entries at location=%+v: %+v", c.upstreamCataloger, location, err) + continue + } + + pkgsForRemoval := make(map[artifact.ID]struct{}) + var cleanedRelationships []artifact.Relationship + for _, p := range discoveredPackages { + p.FoundBy = c.upstreamCataloger + p.Locations.Add(location) + p.SetID() + // doing it here so all packages have an ID, + // IDs are later used to remove relationships + if !pkg.IsValid(p) { + pkgsForRemoval[p.ID()] = struct{}{} + continue + } + + for _, postProcess := range c.postProcessors { + err = postProcess(resolver, location, p) + if err != nil { + return nil, nil, err + } + } + + packages = append(packages, *p) + } + + cleanedRelationships = removeRelationshipsWithArtifactIDs(pkgsForRemoval, discoveredRelationships) + relationships = append(relationships, cleanedRelationships...) + } + return packages, relationships, nil +} + +func removeRelationshipsWithArtifactIDs(artifactsToExclude map[artifact.ID]struct{}, relationships []artifact.Relationship) []artifact.Relationship { + if len(artifactsToExclude) == 0 || len(relationships) == 0 { + // no removal to do + return relationships + } + + var cleanedRelationships []artifact.Relationship + for _, r := range relationships { + _, removeTo := artifactsToExclude[r.To.ID()] + _, removaFrom := artifactsToExclude[r.From.ID()] + if !removeTo && !removaFrom { + cleanedRelationships = append(cleanedRelationships, r) + } + } + + return cleanedRelationships +} + +// SelectFiles takes a set of file trees and resolves and file references of interest for future cataloging +func (c *GenericCataloger) selectFiles(resolver source.FilePathResolver) map[source.Location]ParserFn { + var parserByLocation = make(map[source.Location]ParserFn) + + // select by exact path + for path, parser := range c.pathParsers { + files, err := resolver.FilesByPath(path) + if err != nil { + log.Warnf("cataloger failed to select files by path: %+v", err) + } + for _, f := range files { + parserByLocation[f] = parser + } + } + + // select by glob pattern + for globPattern, parser := range c.globParsers { + fileMatches, err := resolver.FilesByGlob(globPattern) + if err != nil { + log.Warnf("failed to find files by glob: %s", globPattern) + } + for _, f := range fileMatches { + parserByLocation[f] = parser + } + } + + return parserByLocation +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/generic_cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/generic_cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..6e6a2c7292c652c0632ed287c0f2fc193d85146e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/generic_cataloger_test.go @@ -0,0 +1,176 @@ +package common + +import ( + "fmt" + "io" + "io/ioutil" + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +func TestGenericCataloger(t *testing.T) { + allParsedPathes := make(map[string]bool) + parser := func(path string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + allParsedPathes[path] = true + contents, err := ioutil.ReadAll(reader) + require.NoError(t, err) + + p := &pkg.Package{Name: string(contents)} + r := artifact.Relationship{From: p, To: p, + Type: artifact.ContainsRelationship, + } + + return []*pkg.Package{p}, []artifact.Relationship{r}, nil + } + + globParsers := map[string]ParserFn{ + "**/a-path.txt": parser, + "**/empty.txt": parser, + } + pathParsers := map[string]ParserFn{ + "test-fixtures/another-path.txt": parser, + "test-fixtures/last/path.txt": parser, + } + upstream := "some-other-cataloger" + + expectedSelection := []string{"test-fixtures/last/path.txt", "test-fixtures/another-path.txt", "test-fixtures/a-path.txt", "test-fixtures/empty.txt"} + resolver := source.NewMockResolverForPaths(expectedSelection...) + cataloger := NewGenericCataloger(pathParsers, globParsers, upstream) + + actualPkgs, relationships, err := cataloger.Catalog(resolver) + assert.NoError(t, err) + + expectedPkgs := make(map[string]pkg.Package) + for _, path := range expectedSelection { + require.True(t, allParsedPathes[path]) + expectedPkgs[path] = pkg.Package{ + FoundBy: upstream, + Name: fmt.Sprintf("%s file contents!", path), + } + } + + assert.Len(t, allParsedPathes, len(expectedSelection)) + // empty.txt won't become a package + assert.Len(t, actualPkgs, len(expectedPkgs)-1) + // right now, a relationship is created for each package, but if the relationship includes an invalid package it should be dropped. + assert.Len(t, relationships, len(actualPkgs)) + + for _, p := range actualPkgs { + ref := p.Locations.ToSlice()[0] + exP, ok := expectedPkgs[ref.RealPath] + if !ok { + t.Errorf("missing expected pkg: ref=%+v", ref) + continue + } + + if p.FoundBy != exP.FoundBy { + t.Errorf("bad upstream: %s", p.FoundBy) + } + + if exP.Name != p.Name { + t.Errorf("bad contents mapping: %+v", p.Locations) + } + } +} + +func Test_removeRelationshipsWithArtifactIDs(t *testing.T) { + one := &pkg.Package{Name: "one", Version: "1.0"} + two := &pkg.Package{Name: "two", Version: "1.0"} + three := &pkg.Package{Name: "three", Version: "1.0"} + four := &pkg.Package{Name: "four", Version: "bla"} + five := &pkg.Package{Name: "five", Version: "1.0"} + + pkgs := make([]artifact.Identifiable, 0) + for _, p := range []*pkg.Package{one, two, three, four, five} { + // IDs are necessary for comparison + p.SetID() + pkgs = append(pkgs, p) + } + + type args struct { + remove map[artifact.ID]struct{} + relationships []artifact.Relationship + } + tests := []struct { + name string + args args + want []artifact.Relationship + }{ + { + name: "nothing-to-remove", + args: args{ + relationships: []artifact.Relationship{ + {From: one, To: two}, + }, + }, + want: []artifact.Relationship{ + {From: one, To: two}, + }, + }, + { + name: "remove-all-relationships", + args: args{ + remove: map[artifact.ID]struct{}{ + one.ID(): {}, + three.ID(): {}, + }, + relationships: []artifact.Relationship{ + {From: one, To: two}, + {From: two, To: three}, + {From: three, To: four}, + }, + }, + want: []artifact.Relationship(nil), + }, + { + name: "remove-half-of-relationships", + args: args{ + remove: map[artifact.ID]struct{}{ + one.ID(): {}, + }, + relationships: []artifact.Relationship{ + {From: one, To: two}, + {From: one, To: three}, + {From: two, To: three}, + {From: three, To: four}, + }, + }, + want: []artifact.Relationship{ + {From: two, To: three}, + {From: three, To: four}, + }, + }, + { + name: "remove-repeated-relationships", + args: args{ + remove: map[artifact.ID]struct{}{ + one.ID(): {}, + two.ID(): {}, + }, + relationships: []artifact.Relationship{ + {From: one, To: two}, + {From: one, To: three}, + {From: two, To: three}, + {From: two, To: three}, + {From: three, To: four}, + {From: four, To: five}, + }, + }, + want: []artifact.Relationship{ + {From: three, To: four}, + {From: four, To: five}, + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + assert.Equalf(t, tt.want, removeRelationshipsWithArtifactIDs(tt.args.remove, tt.args.relationships), "removeRelationshipsWithArtifactIDs(%v, %v)", tt.args.remove, tt.args.relationships) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/parser.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/parser.go new file mode 100644 index 0000000000000000000000000000000000000000..b79834dbd1ce2fdbe5a9dae9417645816c6f993f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/parser.go @@ -0,0 +1,11 @@ +package common + +import ( + "io" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" +) + +// ParserFn standardizes a function signature for parser functions that accept the virtual file path (not usable for file reads) and contents and return any discovered packages from that file +type ParserFn func(string, io.Reader) ([]*pkg.Package, []artifact.Relationship, error) diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/a-path.txt b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/a-path.txt new file mode 100644 index 0000000000000000000000000000000000000000..67e9540341af9f83d155bd4a48bfbc7bdede539e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/a-path.txt @@ -0,0 +1 @@ +test-fixtures/a-path.txt file contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/another-path.txt b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/another-path.txt new file mode 100644 index 0000000000000000000000000000000000000000..0d654f8fe86300e10b405eb23cc256f8046204df --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/another-path.txt @@ -0,0 +1 @@ +test-fixtures/another-path.txt file contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/empty.txt b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/empty.txt new file mode 100644 index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/last/path.txt b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/last/path.txt new file mode 100644 index 0000000000000000000000000000000000000000..3d4a165ab882b9e058445e56736c64633e13a443 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/common/test-fixtures/last/path.txt @@ -0,0 +1 @@ +test-fixtures/last/path.txt file contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/config.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/config.go new file mode 100644 index 0000000000000000000000000000000000000000..478fc292d111ad54711f5359cfc4c4a7a42dbb3b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/config.go @@ -0,0 +1,23 @@ +package cataloger + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/java" +) + +type Config struct { + Search SearchConfig + Catalogers []string +} + +func DefaultConfig() Config { + return Config{ + Search: DefaultSearchConfig(), + } +} + +func (c Config) Java() java.Config { + return java.Config{ + SearchUnindexedArchives: c.Search.IncludeUnindexedArchives, + SearchIndexedArchives: c.Search.IncludeIndexedArchives, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..a8f02877d1140556736f28dbaa5d8cb25c38278c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/cataloger.go @@ -0,0 +1,14 @@ +package cpp + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewConanfileCataloger returns a new C++ Conanfile cataloger object. +func NewConanfileCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/conanfile.txt": parseConanfile, + } + + return common.NewGenericCataloger(nil, globParsers, "conan-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/parse_conanfile.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/parse_conanfile.go new file mode 100644 index 0000000000000000000000000000000000000000..d3a6481bd39f9556c321473942694a3548b3fec1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/parse_conanfile.go @@ -0,0 +1,60 @@ +package cpp + +import ( + "bufio" + "errors" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseConanfile + +type Conanfile struct { + Requires []string `toml:"requires"` +} + +// parseConanfile is a parser function for conanfile.txt contents, returning all packages discovered. +func parseConanfile(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + r := bufio.NewReader(reader) + inRequirements := false + pkgs := []*pkg.Package{} + for { + line, err := r.ReadString('\n') + switch { + case errors.Is(io.EOF, err): + return pkgs, nil, nil + case err != nil: + return nil, nil, fmt.Errorf("failed to parse conanfile.txt file: %w", err) + } + + switch { + case strings.Contains(line, "[requires]"): + inRequirements = true + case strings.ContainsAny(line, "[]#"): + inRequirements = false + } + + splits := strings.Split(strings.TrimSpace(line), "/") + if len(splits) < 2 || !inRequirements { + continue + } + pkgName, pkgVersion := splits[0], splits[1] + pkgs = append(pkgs, &pkg.Package{ + Name: pkgName, + Version: pkgVersion, + Language: pkg.CPP, + Type: pkg.ConanPkg, + MetadataType: pkg.ConanaMetadataType, + Metadata: pkg.ConanMetadata{ + Name: pkgName, + Version: pkgVersion, + }, + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/parse_conanfile_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/parse_conanfile_test.go new file mode 100644 index 0000000000000000000000000000000000000000..bdcb0322b9157cdf9a18eccb920afcef7dfe07f6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/parse_conanfile_test.go @@ -0,0 +1,96 @@ +package cpp + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseConanfile(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "catch2", + Version: "2.13.8", + Language: pkg.CPP, + Type: pkg.ConanPkg, + MetadataType: pkg.ConanaMetadataType, + Metadata: pkg.ConanMetadata{ + Name: "catch2", + Version: "2.13.8", + }, + }, + { + Name: "docopt.cpp", + Version: "0.6.3", + Language: pkg.CPP, + Type: pkg.ConanPkg, + MetadataType: pkg.ConanaMetadataType, + Metadata: pkg.ConanMetadata{ + Name: "docopt.cpp", + Version: "0.6.3", + }, + }, + { + Name: "fmt", + Version: "8.1.1", + Language: pkg.CPP, + Type: pkg.ConanPkg, + MetadataType: pkg.ConanaMetadataType, + Metadata: pkg.ConanMetadata{ + Name: "fmt", + Version: "8.1.1", + }, + }, + { + Name: "spdlog", + Version: "1.9.2", + Language: pkg.CPP, + Type: pkg.ConanPkg, + MetadataType: pkg.ConanaMetadataType, + Metadata: pkg.ConanMetadata{ + Name: "spdlog", + Version: "1.9.2", + }, + }, + { + Name: "sdl", + Version: "2.0.20", + Language: pkg.CPP, + Type: pkg.ConanPkg, + MetadataType: pkg.ConanaMetadataType, + Metadata: pkg.ConanMetadata{ + Name: "sdl", + Version: "2.0.20", + }, + }, + { + Name: "fltk", + Version: "1.3.8", + Language: pkg.CPP, + Type: pkg.ConanPkg, + MetadataType: pkg.ConanaMetadataType, + Metadata: pkg.ConanMetadata{ + Name: "fltk", + Version: "1.3.8", + }, + }, + } + + fixture, err := os.Open("test-fixtures/conanfile.txt") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseConanfile(fixture.Name(), fixture) + if err != nil { + t.Error(err) + } + + differences := deep.Equal(expected, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/test-fixtures/conanfile.txt b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/test-fixtures/conanfile.txt new file mode 100644 index 0000000000000000000000000000000000000000..c265b1328f21908b3d2672e6fb1be11b3f19cca4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/cpp/test-fixtures/conanfile.txt @@ -0,0 +1,12 @@ +# Docs at https://docs.conan.io/en/latest/reference/conanfile_txt.html + +[requires] +catch2/2.13.8 +docopt.cpp/0.6.3 +fmt/8.1.1 +spdlog/1.9.2 +sdl/2.0.20 +fltk/1.3.8 + +[generators] +cmake_find_package_multi diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..30fd9203ff78cbbf07592463d5c9f4ce9b74ca79 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/cataloger.go @@ -0,0 +1,14 @@ +package dart + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewPubspecLockCataloger returns a new Dartlang cataloger object base on pubspec lock files. +func NewPubspecLockCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/pubspec.lock": parsePubspecLock, + } + + return common.NewGenericCataloger(nil, globParsers, "dartlang-lock-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/parse_pubspec_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/parse_pubspec_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..2ecd8177c68bd54ea1fe8a3a7bf7d973e1d5c35c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/parse_pubspec_lock.go @@ -0,0 +1,96 @@ +package dart + +import ( + "fmt" + "io" + "net/url" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "gopkg.in/yaml.v2" +) + +// integrity check +var _ common.ParserFn = parsePubspecLock + +const defaultPubRegistry string = "https://pub.dartlang.org" + +type pubspecLock struct { + Packages map[string]pubspecLockPackage `yaml:"packages"` + Sdks map[string]string `yaml:"sdks"` +} + +type pubspecLockPackage struct { + Dependency string `yaml:"dependency" mapstructure:"dependency"` + Description pubspecLockDescription `yaml:"description" mapstructure:"description"` + Source string `yaml:"source" mapstructure:"source"` + Version string `yaml:"version" mapstructure:"version"` +} + +type pubspecLockDescription struct { + Name string `yaml:"name" mapstructure:"name"` + URL string `yaml:"url" mapstructure:"url"` + Path string `yaml:"path" mapstructure:"path"` + Ref string `yaml:"ref" mapstructure:"ref"` + ResolvedRef string `yaml:"resolved-ref" mapstructure:"resolved-ref"` +} + +func parsePubspecLock(path string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + var packages []*pkg.Package + + dec := yaml.NewDecoder(reader) + + var p pubspecLock + if err := dec.Decode(&p); err != nil { + return nil, nil, fmt.Errorf("failed to parse pubspec.lock file: %w", err) + } + + for name, pubPkg := range p.Packages { + packages = append(packages, newPubspecLockPackage(name, pubPkg)) + } + + return packages, nil, nil +} + +func newPubspecLockPackage(name string, p pubspecLockPackage) *pkg.Package { + return &pkg.Package{ + Name: name, + Version: p.Version, + Language: pkg.Dart, + Type: pkg.DartPubPkg, + MetadataType: pkg.DartPubMetadataType, + Metadata: &pkg.DartPubMetadata{ + Name: name, + Version: p.Version, + HostedURL: p.getHostedURL(), + VcsURL: p.getVcsURL(), + }, + } +} + +func (p *pubspecLockPackage) getVcsURL() string { + if p.Source == "git" { + if p.Description.Path == "." { + return fmt.Sprintf("%s@%s", p.Description.URL, p.Description.ResolvedRef) + } + + return fmt.Sprintf("%s@%s#%s", p.Description.URL, p.Description.ResolvedRef, p.Description.Path) + } + + return "" +} + +func (p *pubspecLockPackage) getHostedURL() string { + if p.Source == "hosted" && p.Description.URL != defaultPubRegistry { + u, err := url.Parse(p.Description.URL) + if err != nil { + log.Debugf("Unable to parse registry url %w", err) + return p.Description.URL + } + return u.Host + } + + return "" +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/parse_pubspec_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/parse_pubspec_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..f881524c82d62b00a0d981252e4c59df48ccd88e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/parse_pubspec_lock_test.go @@ -0,0 +1,99 @@ +package dart + +import ( + "os" + "testing" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/pkg" +) + +func assertPackagesEqual(t *testing.T, actual []*pkg.Package, expected map[string]*pkg.Package) { + assert.Len(t, actual, len(expected)) +} + +func TestParsePubspecLock(t *testing.T) { + expected := map[string]*pkg.Package{ + "ale": { + Name: "ale", + Version: "3.3.0", + Language: pkg.Dart, + Type: pkg.DartPubPkg, + MetadataType: pkg.DartPubMetadataType, + Metadata: pkg.DartPubMetadata{ + Name: "ale", + Version: "3.3.0", + HostedURL: "pub.hosted.org", + }, + }, + "analyzer": { + Name: "analyzer", + Version: "0.40.7", + Language: pkg.Dart, + Type: pkg.DartPubPkg, + MetadataType: pkg.DartPubMetadataType, + Metadata: pkg.DartPubMetadata{ + Name: "analyzer", + Version: "0.40.7", + }, + }, + "ansicolor": { + Name: "ansicolor", + Version: "1.1.1", + Language: pkg.Dart, + Type: pkg.DartPubPkg, + MetadataType: pkg.DartPubMetadataType, + Metadata: pkg.DartPubMetadata{ + Name: "ansicolor", + Version: "1.1.1", + }, + }, + "archive": { + Name: "archive", + Version: "2.0.13", + Language: pkg.Dart, + Type: pkg.DartPubPkg, + MetadataType: pkg.DartPubMetadataType, + Metadata: pkg.DartPubMetadata{ + Name: "archive", + Version: "2.0.13", + }, + }, + "args": { + Name: "args", + Version: "1.6.0", + Language: pkg.Dart, + Type: pkg.DartPubPkg, + MetadataType: pkg.DartPubMetadataType, + Metadata: pkg.DartPubMetadata{ + Name: "args", + Version: "1.6.0", + }, + }, + "key_binder": { + Name: "key_binder", + Version: "1.11.20", + Language: pkg.Dart, + Type: pkg.DartPubPkg, + MetadataType: pkg.DartPubMetadataType, + Metadata: pkg.DartPubMetadata{ + Name: "key_binder", + Version: "1.11.20", + VcsURL: "git@github.com:Workiva/key_binder.git#3f7b3a6350e73c7dcac45301c0e18fbd42af02f7", + }, + }, + } + + fixture, err := os.Open("test-fixtures/pubspec.lock") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, _, err := parsePubspecLock(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse pubspec.lock: %+v", err) + } + + assertPackagesEqual(t, actual, expected) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/test-fixtures/pubspec.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/test-fixtures/pubspec.lock new file mode 100644 index 0000000000000000000000000000000000000000..c7b912f1aefc8d55726d5007112903b5f162d3bb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dart/test-fixtures/pubspec.lock @@ -0,0 +1,49 @@ +# Generated by pub +# See https://dart.dev/tools/pub/glossary#lockfile +packages: + ale: + dependency: transitive + description: + name: ale + url: "https://pub.hosted.org" + source: hosted + version: "3.3.0" + analyzer: + dependency: transitive + description: + name: analyzer + url: "https://pub.dartlang.org" + source: hosted + version: "0.40.7" + ansicolor: + dependency: transitive + description: + name: ansicolor + url: "https://pub.dartlang.org" + source: hosted + version: "1.1.1" + archive: + dependency: transitive + description: + name: archive + url: "https://pub.dartlang.org" + source: hosted + version: "2.0.13" + args: + dependency: transitive + description: + name: args + url: "https://pub.dartlang.org" + source: hosted + version: "1.6.0" + key_binder: + dependency: "direct main" + description: + path: "." + ref: HEAD + resolved-ref: "3f7b3a6350e73c7dcac45301c0e18fbd42af02f7" + url: "git@github.com:Workiva/key_binder.git" + source: git + version: "1.11.20" +sdks: + dart: ">=2.12.0 <3.0.0" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..4b9146fd73b9b97325d72c78dd5d5c39b422ecb0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/cataloger.go @@ -0,0 +1,234 @@ +/* +Package dpkg provides a concrete Cataloger implementation for Debian package DB status files. +*/ +package deb + +import ( + "fmt" + "io" + "path" + "path/filepath" + "sort" + + "github.com/anchore/syft/internal" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +const ( + md5sumsExt = ".md5sums" + conffilesExt = ".conffiles" + docsPath = "/usr/share/doc" +) + +type Cataloger struct{} + +// NewDpkgdbCataloger returns a new Deb package cataloger object. +func NewDpkgdbCataloger() *Cataloger { + return &Cataloger{} +} + +// Name returns a string that uniquely describes a cataloger +func (c *Cataloger) Name() string { + return "dpkgdb-cataloger" +} + +// Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing dpkg support files. +func (c *Cataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + dbFileMatches, err := resolver.FilesByGlob(pkg.DpkgDBGlob) + if err != nil { + return nil, nil, fmt.Errorf("failed to find dpkg status files's by glob: %w", err) + } + + var allPackages []pkg.Package + for _, dbLocation := range dbFileMatches { + dbContents, err := resolver.FileContentsByLocation(dbLocation) + if err != nil { + return nil, nil, err + } + + pkgs, err := parseDpkgStatus(dbContents) + internal.CloseAndLogError(dbContents, dbLocation.VirtualPath) + if err != nil { + log.Warnf("dpkg cataloger: unable to catalog package=%+v: %w", dbLocation.RealPath, err) + continue + } + + for i := range pkgs { + p := &pkgs[i] + p.FoundBy = c.Name() + p.Locations.Add(dbLocation) + + // the current entry only has what may have been listed in the status file, however, there are additional + // files that are listed in multiple other locations. We should retrieve them all and merge the file lists + // together. + mergeFileListing(resolver, dbLocation, p) + + // fetch additional data from the copyright file to derive the license information + addLicenses(resolver, dbLocation, p) + + p.SetID() + } + + allPackages = append(allPackages, pkgs...) + } + return allPackages, nil, nil +} + +func addLicenses(resolver source.FileResolver, dbLocation source.Location, p *pkg.Package) { + // get license information from the copyright file + copyrightReader, copyrightLocation := fetchCopyrightContents(resolver, dbLocation, p) + + if copyrightReader != nil && copyrightLocation != nil { + defer internal.CloseAndLogError(copyrightReader, copyrightLocation.VirtualPath) + // attach the licenses + p.Licenses = parseLicensesFromCopyright(copyrightReader) + + // keep a record of the file where this was discovered + p.Locations.Add(*copyrightLocation) + } +} + +func mergeFileListing(resolver source.FileResolver, dbLocation source.Location, p *pkg.Package) { + metadata := p.Metadata.(pkg.DpkgMetadata) + + // get file listing (package files + additional config files) + files, infoLocations := getAdditionalFileListing(resolver, dbLocation, p) +loopNewFiles: + for _, newFile := range files { + for _, existingFile := range metadata.Files { + if existingFile.Path == newFile.Path { + // skip adding this file since it already exists + continue loopNewFiles + } + } + metadata.Files = append(metadata.Files, newFile) + } + + // sort files by path + sort.SliceStable(metadata.Files, func(i, j int) bool { + return metadata.Files[i].Path < metadata.Files[j].Path + }) + + // persist alterations + p.Metadata = metadata + + // persist location information from each new source of information + p.Locations.Add(infoLocations...) +} + +func getAdditionalFileListing(resolver source.FileResolver, dbLocation source.Location, p *pkg.Package) ([]pkg.DpkgFileRecord, []source.Location) { + // ensure the default value for a collection is never nil since this may be shown as JSON + var files = make([]pkg.DpkgFileRecord, 0) + var locations []source.Location + + md5Reader, md5Location := fetchMd5Contents(resolver, dbLocation, p) + + if md5Reader != nil && md5Location != nil { + defer internal.CloseAndLogError(md5Reader, md5Location.VirtualPath) + // attach the file list + files = append(files, parseDpkgMD5Info(md5Reader)...) + + // keep a record of the file where this was discovered + locations = append(locations, *md5Location) + } + + conffilesReader, conffilesLocation := fetchConffileContents(resolver, dbLocation, p) + + if conffilesReader != nil && conffilesLocation != nil { + defer internal.CloseAndLogError(conffilesReader, conffilesLocation.VirtualPath) + // attach the file list + files = append(files, parseDpkgConffileInfo(conffilesReader)...) + + // keep a record of the file where this was discovered + locations = append(locations, *conffilesLocation) + } + + return files, locations +} + +func fetchMd5Contents(resolver source.FileResolver, dbLocation source.Location, p *pkg.Package) (io.ReadCloser, *source.Location) { + var md5Reader io.ReadCloser + var err error + + parentPath := filepath.Dir(dbLocation.RealPath) + + // look for /var/lib/dpkg/info/NAME:ARCH.md5sums + name := md5Key(p) + location := resolver.RelativeFileByPath(dbLocation, path.Join(parentPath, "info", name+md5sumsExt)) + + if location == nil { + // the most specific key did not work, fallback to just the name + // look for /var/lib/dpkg/info/NAME.md5sums + location = resolver.RelativeFileByPath(dbLocation, path.Join(parentPath, "info", p.Name+md5sumsExt)) + } + + // this is unexpected, but not a show-stopper + if location != nil { + md5Reader, err = resolver.FileContentsByLocation(*location) + if err != nil { + log.Warnf("failed to fetch deb md5 contents (package=%s): %+v", p.Name, err) + } + } + + return md5Reader, location +} + +func fetchConffileContents(resolver source.FileResolver, dbLocation source.Location, p *pkg.Package) (io.ReadCloser, *source.Location) { + var reader io.ReadCloser + var err error + + parentPath := filepath.Dir(dbLocation.RealPath) + + // look for /var/lib/dpkg/info/NAME:ARCH.conffiles + name := md5Key(p) + location := resolver.RelativeFileByPath(dbLocation, path.Join(parentPath, "info", name+conffilesExt)) + + if location == nil { + // the most specific key did not work, fallback to just the name + // look for /var/lib/dpkg/info/NAME.conffiles + location = resolver.RelativeFileByPath(dbLocation, path.Join(parentPath, "info", p.Name+conffilesExt)) + } + + // this is unexpected, but not a show-stopper + if location != nil { + reader, err = resolver.FileContentsByLocation(*location) + if err != nil { + log.Warnf("failed to fetch deb conffiles contents (package=%s): %+v", p.Name, err) + } + } + + return reader, location +} + +func fetchCopyrightContents(resolver source.FileResolver, dbLocation source.Location, p *pkg.Package) (io.ReadCloser, *source.Location) { + // look for /usr/share/docs/NAME/copyright files + name := p.Name + copyrightPath := path.Join(docsPath, name, "copyright") + location := resolver.RelativeFileByPath(dbLocation, copyrightPath) + + // we may not have a copyright file for each package, ignore missing files + if location == nil { + return nil, nil + } + + reader, err := resolver.FileContentsByLocation(*location) + if err != nil { + log.Warnf("failed to fetch deb copyright contents (package=%s): %w", p.Name, err) + } + + return reader, location +} + +func md5Key(p *pkg.Package) string { + metadata := p.Metadata.(pkg.DpkgMetadata) + + contentKey := p.Name + if metadata.Architecture != "" && metadata.Architecture != "all" { + contentKey = contentKey + ":" + metadata.Architecture + } + return contentKey +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4373f5620acc9a310582197166563fa84fe6ee34 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/cataloger_test.go @@ -0,0 +1,140 @@ +package deb + +import ( + "github.com/stretchr/testify/assert" + "testing" + + "github.com/anchore/syft/syft/file" + + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/go-test/deep" +) + +func TestDpkgCataloger(t *testing.T) { + tests := []struct { + name string + sources map[string][]string + expected []pkg.Package + }{ + { + name: "go-case", + sources: map[string][]string{ + "libpam-runtime": { + "/var/lib/dpkg/status", + "/var/lib/dpkg/info/libpam-runtime.md5sums", + "/var/lib/dpkg/info/libpam-runtime.conffiles", + "/usr/share/doc/libpam-runtime/copyright", + }, + }, + expected: []pkg.Package{ + { + Name: "libpam-runtime", + Version: "1.1.8-3.6", + FoundBy: "dpkgdb-cataloger", + Licenses: []string{"GPL-1", "GPL-2", "LGPL-2.1"}, + Type: pkg.DebPkg, + MetadataType: pkg.DpkgMetadataType, + Metadata: pkg.DpkgMetadata{ + Package: "libpam-runtime", + Source: "pam", + Version: "1.1.8-3.6", + Architecture: "all", + Maintainer: "Steve Langasek ", + InstalledSize: 1016, + Description: `Runtime support for the PAM library + Contains configuration files and directories required for + authentication to work on Debian systems. This package is required + on almost all installations.`, + Files: []pkg.DpkgFileRecord{ + { + Path: "/etc/pam.conf", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "87fc76f18e98ee7d3848f6b81b3391e5", + }, + IsConfigFile: true, + }, + { + Path: "/etc/pam.d/other", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "31aa7f2181889ffb00b87df4126d1701", + }, + IsConfigFile: true, + }, + {Path: "/lib/x86_64-linux-gnu/libz.so.1.2.11", Digest: &file.Digest{ + Algorithm: "md5", + Value: "55f905631797551d4d936a34c7e73474", + }}, + {Path: "/usr/share/doc/zlib1g/changelog.Debian.gz", Digest: &file.Digest{ + Algorithm: "md5", + Value: "cede84bda30d2380217f97753c8ccf3a", + }}, + {Path: "/usr/share/doc/zlib1g/changelog.gz", Digest: &file.Digest{ + Algorithm: "md5", + Value: "f3c9dafa6da7992c47328b4464f6d122", + }}, + {Path: "/usr/share/doc/zlib1g/copyright", Digest: &file.Digest{ + Algorithm: "md5", + Value: "a4fae96070439a5209a62ae5b8017ab2", + }}, + }, + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + img := imagetest.GetFixtureImage(t, "docker-archive", "image-dpkg") + + s, err := source.NewFromImage(img, "") + if err != nil { + t.Fatal(err) + } + + c := NewDpkgdbCataloger() + + resolver, err := s.FileResolver(source.SquashedScope) + if err != nil { + t.Errorf("could not get resolver error: %+v", err) + } + + actual, _, err := c.Catalog(resolver) + if err != nil { + t.Fatalf("failed to catalog: %+v", err) + } + + if len(actual) != len(test.expected) { + for _, a := range actual { + t.Logf(" %+v", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(test.expected)) + } + + // test sources... + for idx := range actual { + a := &actual[idx] + // we will test the sources separately + var sourcesList = make([]string, len(a.Locations.ToSlice())) + for i, s := range a.Locations.ToSlice() { + sourcesList[i] = s.RealPath + } + a.Locations = source.NewLocationSet() + + assert.ElementsMatch(t, sourcesList, test.sources[a.Name]) + } + + // test remaining fields... + for _, d := range deep.Equal(actual, test.expected) { + t.Errorf("diff: %+v", d) + } + + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_copyright.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_copyright.go new file mode 100644 index 0000000000000000000000000000000000000000..20046391105d950d9a9eb3ed1d57944689fc5412 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_copyright.go @@ -0,0 +1,63 @@ +package deb + +import ( + "bufio" + "io" + "regexp" + "sort" + "strings" + + "github.com/anchore/syft/internal" +) + +// For more information see: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/#license-syntax + +var ( + licensePattern = regexp.MustCompile(`^License: (?P\S*)`) + commonLicensePathPattern = regexp.MustCompile(`/usr/share/common-licenses/(?P[0-9A-Za-z_.\-]+)`) +) + +func parseLicensesFromCopyright(reader io.Reader) []string { + findings := internal.NewStringSet() + scanner := bufio.NewScanner(reader) + + for scanner.Scan() { + line := scanner.Text() + if value := findLicenseClause(licensePattern, "license", line); value != "" { + findings.Add(value) + } + if value := findLicenseClause(commonLicensePathPattern, "license", line); value != "" { + findings.Add(value) + } + } + + results := findings.ToSlice() + + sort.Strings(results) + + return results +} + +func findLicenseClause(pattern *regexp.Regexp, valueGroup, line string) string { + matchesByGroup := internal.MatchNamedCaptureGroups(pattern, line) + + candidate, ok := matchesByGroup[valueGroup] + if !ok { + return "" + } + + return ensureIsSingleLicense(candidate) +} + +func ensureIsSingleLicense(candidate string) (license string) { + candidate = strings.TrimSpace(candidate) + if strings.Contains(candidate, " or ") || strings.Contains(candidate, " and ") { + // this is a multi-license summary, ignore this as other recurrent license lines should cover this + return + } + if candidate != "" && strings.ToLower(candidate) != "none" { + // the license may be at the end of a sentence, clean . characters + license = strings.TrimSuffix(candidate, ".") + } + return license +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_copyright_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_copyright_test.go new file mode 100644 index 0000000000000000000000000000000000000000..c6cd0c0c9f3684a2f43eb48ea0550d6a917d5be0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_copyright_test.go @@ -0,0 +1,68 @@ +package deb + +import ( + "os" + "testing" + + "github.com/go-test/deep" +) + +func TestParseLicensesFromCopyright(t *testing.T) { + tests := []struct { + fixture string + expected []string + }{ + { + fixture: "test-fixtures/copyright/libc6", + // note: there are other licenses in this file that are not matched --we don't do full text license identification yet + expected: []string{"GPL-2", "LGPL-2.1"}, + }, + { + fixture: "test-fixtures/copyright/trilicense", + expected: []string{"GPL-2", "LGPL-2.1", "MPL-1.1"}, + }, + { + fixture: "test-fixtures/copyright/liblzma5", + expected: []string{"Autoconf", "GPL-2", "GPL-2+", "GPL-3", "LGPL-2", "LGPL-2.1", "LGPL-2.1+", "PD", "PD-debian", "config-h", "noderivs", "permissive-fsf", "permissive-nowarranty", "probably-PD"}, + }, + { + fixture: "test-fixtures/copyright/libaudit-common", + expected: []string{"GPL-1", "GPL-2", "LGPL-2.1"}, + }, + { + fixture: "test-fixtures/copyright/python", + // note: this should not capture #, Permission, This, see ... however it's not clear how to fix this (this is probably good enough) + expected: []string{"#", "Apache", "Apache-2", "Apache-2.0", "Expat", "GPL-2", "ISC", "LGPL-2.1+", "PSF-2", "Permission", "Python", "This", "see"}, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + file, err := os.Open(test.fixture) + if err != nil { + t.Fatal("Unable to read: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + actual := parseLicensesFromCopyright(file) + + if len(actual) != len(test.expected) { + for _, a := range actual { + t.Logf(" %+v", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(test.expected)) + } + + diffs := deep.Equal(actual, test.expected) + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_info_files.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_info_files.go new file mode 100644 index 0000000000000000000000000000000000000000..105c47da956317159d64d849e25b01ce30f82224 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_info_files.go @@ -0,0 +1,74 @@ +package deb + +import ( + "bufio" + "io" + "strings" + + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" +) + +func parseDpkgMD5Info(reader io.Reader) (findings []pkg.DpkgFileRecord) { + scanner := bufio.NewScanner(reader) + + for scanner.Scan() { + line := scanner.Text() + fields := strings.SplitN(line, " ", 2) + if len(fields) == 2 { + path := strings.TrimSpace(fields[1]) + if !strings.HasPrefix(path, "/") { + path = "/" + path + } + findings = append(findings, pkg.DpkgFileRecord{ + Path: path, + Digest: &file.Digest{ + Algorithm: "md5", + Value: strings.TrimSpace(fields[0]), + }, + }) + } + } + return findings +} + +func parseDpkgConffileInfo(reader io.Reader) (findings []pkg.DpkgFileRecord) { + scanner := bufio.NewScanner(reader) + + for scanner.Scan() { + line := strings.Trim(scanner.Text(), " \n") + fields := strings.SplitN(line, " ", 2) + + if line == "" { + continue + } + + var path string + if len(fields) >= 1 { + path = strings.TrimSpace(fields[0]) + if !strings.HasPrefix(path, "/") { + path = "/" + path + } + } + + var digest *file.Digest + if len(fields) >= 2 { + digest = &file.Digest{ + Algorithm: "md5", + Value: strings.TrimSpace(fields[1]), + } + } + + if path != "" { + record := pkg.DpkgFileRecord{ + Path: path, + IsConfigFile: true, + } + if digest != nil { + record.Digest = digest + } + findings = append(findings, record) + } + } + return findings +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_info_files_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_info_files_test.go new file mode 100644 index 0000000000000000000000000000000000000000..c345c714eabb0198e04ae217bd071ec52fe50888 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_info_files_test.go @@ -0,0 +1,120 @@ +package deb + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/file" + + "github.com/go-test/deep" + + "github.com/anchore/syft/syft/pkg" +) + +func TestMD5SumInfoParsing(t *testing.T) { + tests := []struct { + fixture string + expected []pkg.DpkgFileRecord + }{ + { + fixture: "test-fixtures/info/zlib1g.md5sums", + expected: []pkg.DpkgFileRecord{ + {Path: "/lib/x86_64-linux-gnu/libz.so.1.2.11", Digest: &file.Digest{ + Algorithm: "md5", + Value: "55f905631797551d4d936a34c7e73474", + }}, + {Path: "/usr/share/doc/zlib1g/changelog.Debian.gz", Digest: &file.Digest{ + Algorithm: "md5", + Value: "cede84bda30d2380217f97753c8ccf3a", + }}, + {Path: "/usr/share/doc/zlib1g/changelog.gz", Digest: &file.Digest{ + Algorithm: "md5", + Value: "f3c9dafa6da7992c47328b4464f6d122", + }}, + {Path: "/usr/share/doc/zlib1g/copyright", Digest: &file.Digest{ + Algorithm: "md5", + Value: "a4fae96070439a5209a62ae5b8017ab2", + }}, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + file, err := os.Open(test.fixture) + if err != nil { + t.Fatal("Unable to read: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + actual := parseDpkgMD5Info(file) + + if len(actual) != len(test.expected) { + for _, a := range actual { + t.Logf(" %+v", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(test.expected)) + } + + diffs := deep.Equal(actual, test.expected) + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + + }) + } +} + +func TestConffileInfoParsing(t *testing.T) { + tests := []struct { + fixture string + expected []pkg.DpkgFileRecord + }{ + { + fixture: "test-fixtures/info/util-linux.conffiles", + expected: []pkg.DpkgFileRecord{ + {Path: "/etc/default/hwclock", IsConfigFile: true}, + {Path: "/etc/init.d/hwclock.sh", IsConfigFile: true}, + {Path: "/etc/pam.d/runuser", IsConfigFile: true}, + {Path: "/etc/pam.d/runuser-l", IsConfigFile: true}, + {Path: "/etc/pam.d/su", IsConfigFile: true}, + {Path: "/etc/pam.d/su-l", IsConfigFile: true}, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + file, err := os.Open(test.fixture) + if err != nil { + t.Fatal("Unable to read: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + actual := parseDpkgConffileInfo(file) + + if len(actual) != len(test.expected) { + for _, a := range actual { + t.Logf(" %+v", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(test.expected)) + } + + diffs := deep.Equal(actual, test.expected) + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_status.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_status.go new file mode 100644 index 0000000000000000000000000000000000000000..3be24015163a91f924a5fdf3bc75142725fc900d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_status.go @@ -0,0 +1,180 @@ +package deb + +import ( + "bufio" + "errors" + "fmt" + "io" + "regexp" + "strings" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" + "github.com/dustin/go-humanize" + "github.com/mitchellh/mapstructure" +) + +var ( + errEndOfPackages = fmt.Errorf("no more packages to read") + sourceRegexp = regexp.MustCompile(`(?P\S+)( \((?P.*)\))?`) +) + +func newDpkgPackage(d pkg.DpkgMetadata) *pkg.Package { + return &pkg.Package{ + Name: d.Package, + Version: d.Version, + Type: pkg.DebPkg, + MetadataType: pkg.DpkgMetadataType, + Metadata: d, + } +} + +// parseDpkgStatus is a parser function for Debian DB status contents, returning all Debian packages listed. +func parseDpkgStatus(reader io.Reader) ([]pkg.Package, error) { + buffedReader := bufio.NewReader(reader) + var packages []pkg.Package + + continueProcessing := true + for continueProcessing { + entry, err := parseDpkgStatusEntry(buffedReader) + if err != nil { + if errors.Is(err, errEndOfPackages) { + continueProcessing = false + } else { + return nil, err + } + } + + p := newDpkgPackage(entry) + if pkg.IsValid(p) { + packages = append(packages, *p) + } + } + + return packages, nil +} + +// parseDpkgStatusEntry returns an individual Dpkg entry, or returns errEndOfPackages if there are no more packages to parse from the reader. +func parseDpkgStatusEntry(reader *bufio.Reader) (pkg.DpkgMetadata, error) { + var retErr error + dpkgFields, err := extractAllFields(reader) + if err != nil { + if !errors.Is(err, errEndOfPackages) { + return pkg.DpkgMetadata{}, err + } + retErr = err + } + + entry := pkg.DpkgMetadata{ + // ensure the default value for a collection is never nil since this may be shown as JSON + Files: make([]pkg.DpkgFileRecord, 0), + } + err = mapstructure.Decode(dpkgFields, &entry) + if err != nil { + return pkg.DpkgMetadata{}, err + } + + name, version := extractSourceVersion(entry.Source) + if version != "" { + entry.SourceVersion = version + entry.Source = name + } + + // there may be an optional conffiles section that we should persist as files + if conffilesSection, exists := dpkgFields["Conffiles"]; exists && conffilesSection != nil { + if sectionStr, ok := conffilesSection.(string); ok { + entry.Files = parseDpkgConffileInfo(strings.NewReader(sectionStr)) + } + } + + return entry, retErr +} + +func extractAllFields(reader *bufio.Reader) (map[string]interface{}, error) { + dpkgFields := make(map[string]interface{}) + var key string + + for { + line, err := reader.ReadString('\n') + if err != nil { + if err == io.EOF { + return dpkgFields, errEndOfPackages + } + return nil, err + } + + line = strings.TrimRight(line, "\n") + + // empty line indicates end of entry + if len(line) == 0 { + // if the entry has not started, keep parsing lines + if len(dpkgFields) == 0 { + continue + } + break + } + + switch { + case strings.HasPrefix(line, " "): + // a field-body continuation + if len(key) == 0 { + return nil, fmt.Errorf("no match for continuation: line: '%s'", line) + } + + val, ok := dpkgFields[key] + if !ok { + return nil, fmt.Errorf("no previous key exists, expecting: %s", key) + } + // concatenate onto previous value + val = fmt.Sprintf("%s\n %s", val, strings.TrimSpace(line)) + dpkgFields[key] = val + default: + // parse a new key + var val interface{} + key, val, err = handleNewKeyValue(line) + if err != nil { + log.Warnf("parsing dpkg status: extracting key-value from line: %s err: %v", line, err) + continue + } + + if _, ok := dpkgFields[key]; ok { + return nil, fmt.Errorf("duplicate key discovered: %s", key) + } + dpkgFields[key] = val + } + } + return dpkgFields, nil +} + +// If the source entry string is of the form " ()" then parse and return the components, if +// of the "" form, then return name and nil +func extractSourceVersion(source string) (string, string) { + // special handling for the Source field since it has formatted data + match := internal.MatchNamedCaptureGroups(sourceRegexp, source) + return match["name"], match["version"] +} + +// handleNewKeyValue parse a new key-value pair from the given unprocessed line +func handleNewKeyValue(line string) (key string, val interface{}, err error) { + if i := strings.Index(line, ":"); i > 0 { + key = strings.TrimSpace(line[0:i]) + // mapstruct cant handle "-" + key = strings.ReplaceAll(key, "-", "") + val := strings.TrimSpace(line[i+1:]) + + // further processing of values based on the key that was discovered + switch key { + case "InstalledSize": + s, err := humanize.ParseBytes(val) + if err != nil { + return "", nil, fmt.Errorf("bad installed-size value=%q: %w", val, err) + } + return key, int(s), nil + default: + return key, val, nil + } + } + + return "", nil, fmt.Errorf("cannot parse field from line: '%s'", line) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_status_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_status_test.go new file mode 100644 index 0000000000000000000000000000000000000000..ed1dd9487422df3b11d7ae90724d7586dd4ac239 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/parse_dpkg_status_test.go @@ -0,0 +1,437 @@ +package deb + +import ( + "bufio" + "errors" + "fmt" + "os" + "path/filepath" + "strings" + "testing" + + "github.com/anchore/syft/syft/file" + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func compareEntries(t *testing.T, left, right pkg.DpkgMetadata) { + t.Helper() + if diff := deep.Equal(left, right); diff != nil { + t.Error(diff) + } +} + +func TestSinglePackage(t *testing.T) { + tests := []struct { + name string + expected pkg.DpkgMetadata + fixturePath string + }{ + { + name: "Test Single Package", + fixturePath: filepath.Join("test-fixtures", "status", "single"), + expected: pkg.DpkgMetadata{ + Package: "apt", + Source: "apt-dev", + Version: "1.8.2", + Architecture: "amd64", + InstalledSize: 4064, + Maintainer: "APT Development Team ", + Description: `commandline package manager + This package provides commandline tools for searching and + managing as well as querying information about packages + as a low-level access to all features of the libapt-pkg library. + . + These include: + * apt-get for retrieval of packages and information about them + from authenticated sources and for installation, upgrade and + removal of packages together with their dependencies + * apt-cache for querying available information about installed + as well as installable packages + * apt-cdrom to use removable media as a source for packages + * apt-config as an interface to the configuration settings + * apt-key as an interface to manage authentication keys`, + Files: []pkg.DpkgFileRecord{ + { + Path: "/etc/apt/apt.conf.d/01autoremove", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "76120d358bc9037bb6358e737b3050b5", + }, + IsConfigFile: true, + }, + { + Path: "/etc/cron.daily/apt-compat", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "49e9b2cfa17849700d4db735d04244f3", + }, + IsConfigFile: true, + }, + { + Path: "/etc/kernel/postinst.d/apt-auto-removal", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "4ad976a68f045517cf4696cec7b8aa3a", + }, + IsConfigFile: true, + }, + { + Path: "/etc/logrotate.d/apt", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "179f2ed4f85cbaca12fa3d69c2a4a1c3", + }, + IsConfigFile: true, + }, + }, + }, + }, + { + name: "parse storage notation", + fixturePath: filepath.Join("test-fixtures", "status", "installed-size-4KB"), + expected: pkg.DpkgMetadata{ + Package: "apt", + Source: "apt-dev", + Version: "1.8.2", + Architecture: "amd64", + InstalledSize: 4000, + Maintainer: "APT Development Team ", + Description: `commandline package manager + This package provides commandline tools for searching and + managing as well as querying information about packages + as a low-level access to all features of the libapt-pkg library. + . + These include: + * apt-get for retrieval of packages and information about them + from authenticated sources and for installation, upgrade and + removal of packages together with their dependencies + * apt-cache for querying available information about installed + as well as installable packages + * apt-cdrom to use removable media as a source for packages + * apt-config as an interface to the configuration settings + * apt-key as an interface to manage authentication keys`, + }, + }} + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + file, err := os.Open(test.fixturePath) + if err != nil { + t.Fatal("Unable to read test_fixtures/single: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + reader := bufio.NewReader(file) + + entry, err := parseDpkgStatusEntry(reader) + if err != nil { + t.Fatal("Unable to read file contents: ", err) + } + + compareEntries(t, entry, test.expected) + }) + } +} + +func TestMultiplePackages(t *testing.T) { + tests := []struct { + name string + expected []pkg.DpkgMetadata + }{ + { + name: "Test Multiple Package", + expected: []pkg.DpkgMetadata{ + { + Package: "no-version", + Files: []pkg.DpkgFileRecord{}, + }, + { + Package: "tzdata", + Version: "2020a-0+deb10u1", + Source: "tzdata-dev", + Architecture: "all", + InstalledSize: 3036, + Maintainer: "GNU Libc Maintainers ", + Description: `time zone and daylight-saving time data + This package contains data required for the implementation of + standard local time for many representative locations around the + globe. It is updated periodically to reflect changes made by + political bodies to time zone boundaries, UTC offsets, and + daylight-saving rules.`, + Files: []pkg.DpkgFileRecord{}, + }, + { + Package: "util-linux", + Version: "2.33.1-0.1", + Architecture: "amd64", + InstalledSize: 4327, + Maintainer: "LaMont Jones ", + Description: `miscellaneous system utilities + This package contains a number of important utilities, most of which + are oriented towards maintenance of your system. Some of the more + important utilities included in this package allow you to view kernel + messages, create new filesystems, view block device information, + interface with real time clock, etc.`, + Files: []pkg.DpkgFileRecord{ + { + Path: "/etc/default/hwclock", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "3916544450533eca69131f894db0ca12", + }, + IsConfigFile: true, + }, + { + Path: "/etc/init.d/hwclock.sh", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "1ca5c0743fa797ffa364db95bb8d8d8e", + }, + IsConfigFile: true, + }, + { + Path: "/etc/pam.d/runuser", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "b8b44b045259525e0fae9e38fdb2aeeb", + }, + IsConfigFile: true, + }, + { + Path: "/etc/pam.d/runuser-l", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "2106ea05877e8913f34b2c77fa02be45", + }, + IsConfigFile: true, + }, + { + Path: "/etc/pam.d/su", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "ce6dcfda3b190a27a455bb38a45ff34a", + }, + IsConfigFile: true, + }, + { + Path: "/etc/pam.d/su-l", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "756fef5687fecc0d986e5951427b0c4f", + }, + IsConfigFile: true, + }, + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + file, err := os.Open("test-fixtures/status/multiple") + if err != nil { + t.Fatal("Unable to read: ", err) + } + defer func() { + err := file.Close() + if err != nil { + t.Fatal("closing file failed:", err) + } + }() + + pkgs, err := parseDpkgStatus(file) + if err != nil { + t.Fatal("Unable to read file contents: ", err) + } + + if len(pkgs) != 3 { + t.Fatalf("unexpected number of entries: %d", len(pkgs)) + } + + for idx, entry := range pkgs { + compareEntries(t, entry.Metadata.(pkg.DpkgMetadata), test.expected[idx]) + } + + }) + } +} + +func TestSourceVersionExtract(t *testing.T) { + tests := []struct { + name string + input string + expected []string + }{ + { + name: "name and version", + input: "test (1.2.3)", + expected: []string{"test", "1.2.3"}, + }, + { + name: "only name", + input: "test", + expected: []string{"test", ""}, + }, + { + name: "empty", + input: "", + expected: []string{"", ""}, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + name, version := extractSourceVersion(test.input) + + if name != test.expected[0] { + t.Errorf("mismatch name for %q : %q!=%q", test.input, name, test.expected[0]) + } + + if version != test.expected[1] { + t.Errorf("mismatch version for %q : %q!=%q", test.input, version, test.expected[1]) + } + + }) + } +} + +func assertAs(expected error) assert.ErrorAssertionFunc { + return func(t assert.TestingT, err error, i ...interface{}) bool { + return assert.ErrorAs(t, err, &expected) + } +} + +func Test_parseDpkgStatus(t *testing.T) { + tests := []struct { + name string + input string + want []pkg.Package + wantErr assert.ErrorAssertionFunc + }{ + { + name: "no more packages", + input: `Package: apt`, + wantErr: assert.NoError, + }, + { + name: "duplicated key", + input: `Package: apt +Package: apt-get + +`, + wantErr: assertAs(errors.New("duplicate key discovered: Package")), + }, + { + name: "no match for continuation", + input: ` Package: apt + +`, + wantErr: assertAs(errors.New("no match for continuation: line: ' Package: apt'")), + }, + { + name: "find keys", + input: `Package: apt +Status: install ok installed +Installed-Size: 10kib + +`, + want: []pkg.Package{ + { + Name: "apt", + Type: "deb", + MetadataType: "DpkgMetadata", + Metadata: pkg.DpkgMetadata{ + Package: "apt", + InstalledSize: 10240, + Files: []pkg.DpkgFileRecord{}, + }, + }, + }, + wantErr: assert.NoError, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + r := bufio.NewReader(strings.NewReader(tt.input)) + got, err := parseDpkgStatus(r) + tt.wantErr(t, err, fmt.Sprintf("parseDpkgStatus")) + assert.Equal(t, tt.want, got) + }) + } +} + +func Test_handleNewKeyValue(t *testing.T) { + tests := []struct { + name string + line string + wantKey string + wantVal interface{} + wantErr assert.ErrorAssertionFunc + }{ + { + name: "cannot parse field", + line: "blabla", + wantErr: assertAs(errors.New("cannot parse field from line: 'blabla'")), + }, + { + name: "parse field", + line: "key: val", + wantKey: "key", + wantVal: "val", + wantErr: assert.NoError, + }, + { + name: "parse installed size", + line: "InstalledSize: 128", + wantKey: "InstalledSize", + wantVal: 128, + wantErr: assert.NoError, + }, + { + name: "parse installed kib size", + line: "InstalledSize: 1kib", + wantKey: "InstalledSize", + wantVal: 1024, + wantErr: assert.NoError, + }, + { + name: "parse installed kb size", + line: "InstalledSize: 1kb", + wantKey: "InstalledSize", + wantVal: 1000, + wantErr: assert.NoError, + }, + { + name: "parse installed-size mb", + line: "Installed-Size: 1 mb", + wantKey: "InstalledSize", + wantVal: 1000000, + wantErr: assert.NoError, + }, + { + name: "fail parsing installed-size", + line: "Installed-Size: 1bla", + wantKey: "", + wantErr: assertAs(fmt.Errorf("unhandled size name: %s", "bla")), + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + gotKey, gotVal, err := handleNewKeyValue(tt.line) + tt.wantErr(t, err, fmt.Sprintf("handleNewKeyValue(%v)", tt.line)) + + assert.Equalf(t, tt.wantKey, gotKey, "handleNewKeyValue(%v)", tt.line) + assert.Equalf(t, tt.wantVal, gotVal, "handleNewKeyValue(%v)", tt.line) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/libaudit-common b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/libaudit-common new file mode 100644 index 0000000000000000000000000000000000000000..363b056eb51ddc1a4f55ab3fecf13e2c60ab1147 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/libaudit-common @@ -0,0 +1,43 @@ +Format: http://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ +Upstream-Name: auditd +Source: https://people.redhat.com/sgrubb/audit/ + +Files: * +Copyright: 2012-2016 Steve Grubb + 2006-2012 Rik Faith +License: GPL-2 + +Files: src/libev/* +Copyright: 2007-2009 Marc Alexamder Lehmann +License: GPL-2 + +Files: lib/* +Copyright: 2005-2008 Steve Grubb +License: LGPL-2.1 + The audit daemon's library libaudit.* is released under LGPL + so that it may be linked with 3rd party software. + . + On Debian systems, refer to /usr/share/common-licenses/LGPL-2.1 + for the complete text of the GNU Lesser General Public License. + +Files: debian/* +Copyright: 2007-2011 Philipp Matthias Hahn + 2012-2016 Laurent Bigonville +License: GPL-2 + +License: GPL-2 + This package is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License version 2, + as published by the Free Software Foundation. + . + This package is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + . + You should have received a copy of the GNU General Public License + along with this package; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + . + On Debian systems, the complete text of the GNU General + Public License can be found in `/usr/share/common-licenses/GPL-1'. diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/libc6 b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/libc6 new file mode 100644 index 0000000000000000000000000000000000000000..203faf1b327e79d54b8d45cf1b9c6217715dd74c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/libc6 @@ -0,0 +1,509 @@ +This is the Debian prepackaged version of the GNU C Library version 2.23. + +It was put together by the GNU Libc Maintainers +from + +* Most of the GNU C library is under the following copyright: + + Copyright (C) 1991-2015 Free Software Foundation, Inc. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, write to the Free + Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA + 02110-1301 USA + + On Debian systems, the complete text of the GNU Library + General Public License can be found in `/usr/share/common-licenses/LGPL-2.1'. + +* The utilities associated with GNU C library is under the following + copyright: + + Copyright (C) 1991-2015 Free Software Foundation, Inc. + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software Foundation, + Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + + On Debian systems, the complete text of the GNU Library + General Public License can be found in `/usr/share/common-licenses/GPL-2'. + +* All code incorporated from 4.4 BSD is distributed under the following + license: + + Copyright (C) 1991 Regents of the University of California. + All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + 3. [This condition was removed.] + 4. Neither the name of the University nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + SUCH DAMAGE. + +* The DNS resolver code, taken from BIND 4.9.5, is copyrighted both by + UC Berkeley and by Digital Equipment Corporation. The DEC portions + are under the following license: + + Portions Copyright (C) 1993 by Digital Equipment Corporation. + + Permission to use, copy, modify, and distribute this software for any + purpose with or without fee is hereby granted, provided that the above + copyright notice and this permission notice appear in all copies, and + that the name of Digital Equipment Corporation not be used in + advertising or publicity pertaining to distribution of the document or + software without specific, written prior permission. + + THE SOFTWARE IS PROVIDED ``AS IS'' AND DIGITAL EQUIPMENT CORP. + DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL + DIGITAL EQUIPMENT CORPORATION BE LIABLE FOR ANY SPECIAL, DIRECT, + INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING + FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, + NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION + WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + +* The ISC portions are under the following license: + + Portions Copyright (c) 1996-1999 by Internet Software Consortium. + + Permission to use, copy, modify, and distribute this software for any + purpose with or without fee is hereby granted, provided that the above + copyright notice and this permission notice appear in all copies. + + THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM DISCLAIMS + ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES + OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE + CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL + DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR + PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS + ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS + SOFTWARE. + +* The Sun RPC support (from rpcsrc-4.0) is covered by the following + license: + + Copyright (c) 2010, Oracle America, Inc. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are + met: + + * Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above + copyright notice, this list of conditions and the following + disclaimer in the documentation and/or other materials + provided with the distribution. + * Neither the name of the "Oracle America, Inc." nor the names of its + contributors may be used to endorse or promote products derived + from this software without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE + GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +* The following CMU license covers some of the support code for Mach, + derived from Mach 3.0: + + Mach Operating System + Copyright (C) 1991,1990,1989 Carnegie Mellon University + All Rights Reserved. + + Permission to use, copy, modify and distribute this software and its + documentation is hereby granted, provided that both the copyright + notice and this permission notice appear in all copies of the + software, derivative works or modified versions, and any portions + thereof, and that both notices appear in supporting documentation. + + CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS ``AS IS'' + CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR + ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE. + + Carnegie Mellon requests users of this software to return to + + Software Distribution Coordinator + School of Computer Science + Carnegie Mellon University + Pittsburgh PA 15213-3890 + + or Software.Distribution@CS.CMU.EDU any improvements or + extensions that they make and grant Carnegie Mellon the rights to + redistribute these changes. + +* The file if_ppp.h is under the following CMU license: + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + 3. Neither the name of the University nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY CARNEGIE MELLON UNIVERSITY AND + CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE FOR ANY + DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE + GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER + IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR + OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN + IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +* The following license covers the files from Intel's "Highly Optimized + Mathematical Functions for Itanium" collection: + + Intel License Agreement + + Copyright (c) 2000, Intel Corporation + + All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are + met: + + * Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + * Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + * The name of Intel Corporation may not be used to endorse or promote + products derived from this software without specific prior written + permission. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL OR + CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +* The files inet/getnameinfo.c and sysdeps/posix/getaddrinfo.c are copyright + (C) by Craig Metz and are distributed under the following license: + + /* The Inner Net License, Version 2.00 + + The author(s) grant permission for redistribution and use in source and + binary forms, with or without modification, of the software and documentation + provided that the following conditions are met: + + 0. If you receive a version of the software that is specifically labelled + as not being for redistribution (check the version message and/or README), + you are not permitted to redistribute that version of the software in any + way or form. + 1. All terms of the all other applicable copyrights and licenses must be + followed. + 2. Redistributions of source code must retain the authors' copyright + notice(s), this list of conditions, and the following disclaimer. + 3. Redistributions in binary form must reproduce the authors' copyright + notice(s), this list of conditions, and the following disclaimer in the + documentation and/or other materials provided with the distribution. + 4. [The copyright holder has authorized the removal of this clause.] + 5. Neither the name(s) of the author(s) nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY ITS AUTHORS AND CONTRIBUTORS ``AS IS'' AND ANY + EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE FOR ANY + DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON + ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + If these license terms cause you a real problem, contact the author. */ + +* The file sunrpc/des_impl.c is copyright Eric Young: + + Copyright (C) 1992 Eric Young + Collected from libdes and modified for SECURE RPC by Martin Kuck 1994 + This file is distributed under the terms of the GNU Lesser General + Public License, version 2.1 or later - see the file COPYING.LIB for details. + If you did not receive a copy of the license with this program, please + see to obtain a copy. + +* The libidn code is copyright Simon Josefsson, with portions copyright + The Internet Society, Tom Tromey and Red Hat, Inc.: + + Copyright (C) 2002, 2003, 2004, 2011 Simon Josefsson + + This file is part of GNU Libidn. + + GNU Libidn is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + GNU Libidn is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with GNU Libidn; if not, see . + +* The following notice applies to portions of libidn/nfkc.c: + + This file contains functions from GLIB, including gutf8.c and + gunidecomp.c, all licensed under LGPL and copyright hold by: + + Copyright (C) 1999, 2000 Tom Tromey + Copyright 2000 Red Hat, Inc. + +* The following applies to portions of libidn/punycode.c and + libidn/punycode.h: + + This file is derived from RFC 3492bis written by Adam M. Costello. + + Disclaimer and license: Regarding this entire document or any + portion of it (including the pseudocode and C code), the author + makes no guarantees and is not responsible for any damage resulting + from its use. The author grants irrevocable permission to anyone + to use, modify, and distribute it in any way that does not diminish + the rights of anyone else to use, modify, and distribute it, + provided that redistributed derivative works do not contain + misleading author or version information. Derivative works need + not be licensed under similar terms. + + Copyright (C) The Internet Society (2003). All Rights Reserved. + + This document and translations of it may be copied and furnished to + others, and derivative works that comment on or otherwise explain it + or assist in its implementation may be prepared, copied, published + and distributed, in whole or in part, without restriction of any + kind, provided that the above copyright notice and this paragraph are + included on all such copies and derivative works. However, this + document itself may not be modified in any way, such as by removing + the copyright notice or references to the Internet Society or other + Internet organizations, except as needed for the purpose of + developing Internet standards in which case the procedures for + copyrights defined in the Internet Standards process must be + followed, or as required to translate it into languages other than + English. + + The limited permissions granted above are perpetual and will not be + revoked by the Internet Society or its successors or assigns. + + This document and the information contained herein is provided on an + "AS IS" basis and THE INTERNET SOCIETY AND THE INTERNET ENGINEERING + TASK FORCE DISCLAIMS ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING + BUT NOT LIMITED TO ANY WARRANTY THAT THE USE OF THE INFORMATION + HEREIN WILL NOT INFRINGE ANY RIGHTS OR ANY IMPLIED WARRANTIES OF + MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + +* The file inet/rcmd.c is under a UCB copyright and the following: + + Copyright (C) 1998 WIDE Project. + All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + 3. Neither the name of the project nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND + ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE + FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + SUCH DAMAGE. + + * The file posix/runtests.c is copyright Tom Lord: + + Copyright 1995 by Tom Lord + + All Rights Reserved + + Permission to use, copy, modify, and distribute this software and its + documentation for any purpose and without fee is hereby granted, + provided that the above copyright notice appear in all copies and that + both that copyright notice and this permission notice appear in + supporting documentation, and that the name of the copyright holder not be + used in advertising or publicity pertaining to distribution of the + software without specific, written prior permission. + + Tom Lord DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + EVENT SHALL TOM LORD BE LIABLE FOR ANY SPECIAL, INDIRECT OR + CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF + USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR + OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR + PERFORMANCE OF THIS SOFTWARE. + +* The posix/rxspencer tests are copyright Henry Spencer: + + Copyright 1992, 1993, 1994, 1997 Henry Spencer. All rights reserved. + This software is not subject to any license of the American Telephone + and Telegraph Company or of the Regents of the University of California. + + Permission is granted to anyone to use this software for any purpose on + any computer system, and to alter it and redistribute it, subject + to the following restrictions: + + 1. The author is not responsible for the consequences of use of this + software, no matter how awful, even if they arise from flaws in it. + + 2. The origin of this software must not be misrepresented, either by + explicit claim or by omission. Since few users ever read sources, + credits must appear in the documentation. + + 3. Altered versions must be plainly marked as such, and must not be + misrepresented as being the original software. Since few users + ever read sources, credits must appear in the documentation. + + 4. This notice may not be removed or altered. + +* The file posix/PCRE.tests is copyright University of Cambridge: + + Copyright (c) 1997-2003 University of Cambridge + + Permission is granted to anyone to use this software for any purpose on any + computer system, and to redistribute it freely, subject to the following + restrictions: + + 1. This software is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + + 2. The origin of this software must not be misrepresented, either by + explicit claim or by omission. In practice, this means that if you use + PCRE in software that you distribute to others, commercially or + otherwise, you must put a sentence like this + + Regular expression support is provided by the PCRE library package, + which is open source software, written by Philip Hazel, and copyright + by the University of Cambridge, England. + + somewhere reasonably visible in your documentation and in any relevant + files or online help data or similar. A reference to the ftp site for + the source, that is, to + + ftp://ftp.csx.cam.ac.uk/pub/software/programming/pcre/ + + should also be given in the documentation. However, this condition is not + intended to apply to whole chains of software. If package A includes PCRE, + it must acknowledge it, but if package B is software that includes package + A, the condition is not imposed on package B (unless it uses PCRE + independently). + + 3. Altered versions must be plainly marked as such, and must not be + misrepresented as being the original software. + + 4. If PCRE is embedded in any software that is released under the GNU + General Purpose Licence (GPL), or Lesser General Purpose Licence (LGPL), + then the terms of that licence shall supersede any condition above with + which it is incompatible. + +* Files from Sun fdlibm are copyright Sun Microsystems, Inc.: + + Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved. + + Developed at SunPro, a Sun Microsystems, Inc. business. + Permission to use, copy, modify, and distribute this + software is freely granted, provided that this notice + is preserved. + +* Part of stdio-common/tst-printf.c is copyright C E Chew: + + (C) Copyright C E Chew + + Feel free to copy, use and distribute this software provided: + + 1. you do not pretend that you wrote it + 2. you leave this copyright notice intact. + +* Various long double libm functions are copyright Stephen L. Moshier: + + Copyright 2001 by Stephen L. Moshier + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, see + . */ \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/liblzma5 b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/liblzma5 new file mode 100644 index 0000000000000000000000000000000000000000..3327901154fd81cb2cdeb83c1ac6fe02388b079b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/liblzma5 @@ -0,0 +1,383 @@ +Format: http://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ +Upstream-Name: XZ Utils +Upstream-Contact: + Lasse Collin + http://tukaani.org/xz/lists.html +Source: + http://tukaani.org/xz + http://git.tukaani.org/xz.git +Comment: + XZ Utils is developed and maintained upstream by Lasse Collin. Major + portions are based on code by other authors; see AUTHORS for details. + Most of the source has been put into the public domain, but some files + have not (details below). + . + This file describes the source package. The binary packages contain + some files derived from other works: for example, images in the API + documentation come from Doxygen. +License: + Different licenses apply to different files in this package. Here + is a rough summary of which licenses apply to which parts of this + package (but check the individual files to be sure!): + . + - liblzma is in the public domain. + . + - xz, xzdec, and lzmadec command line tools are in the public + domain unless GNU getopt_long had to be compiled and linked + in from the lib directory. The getopt_long code is under + GNU LGPLv2.1+. + . + - The scripts to grep, diff, and view compressed files have been + adapted from gzip. These scripts and their documentation are + under GNU GPLv2+. + . + - All the documentation in the doc directory and most of the + XZ Utils specific documentation files in other directories + are in the public domain. + . + - Translated messages are in the public domain. + . + - The build system contains public domain files, and files that + are under GNU GPLv2+ or GNU GPLv3+. None of these files end up + in the binaries being built. + . + - Test files and test code in the tests directory, and debugging + utilities in the debug directory are in the public domain. + . + - The extra directory may contain public domain files, and files + that are under various free software licenses. + . + You can do whatever you want with the files that have been put into + the public domain. If you find public domain legally problematic, + take the previous sentence as a license grant. If you still find + the lack of copyright legally problematic, you have too many + lawyers. + . + As usual, this software is provided "as is", without any warranty. + . + If you copy significant amounts of public domain code from XZ Utils + into your project, acknowledging this somewhere in your software is + polite (especially if it is proprietary, non-free software), but + naturally it is not legally required. Here is an example of a good + notice to put into "about box" or into documentation: + . + This software includes code from XZ Utils . + . + The following license texts are included in the following files: + - COPYING.LGPLv2.1: GNU Lesser General Public License version 2.1 + - COPYING.GPLv2: GNU General Public License version 2 + - COPYING.GPLv3: GNU General Public License version 3 + . + Note that the toolchain (compiler, linker etc.) may add some code + pieces that are copyrighted. Thus, it is possible that e.g. liblzma + binary wouldn't actually be in the public domain in its entirety + even though it contains no copyrighted code from the XZ Utils source + package. + . + If you have questions, don't hesitate to ask the author(s) for more + information. + +Files: * +Copyright: 2006-2012, Lasse Collin + 1999-2008, Igor Pavlov + 2006, Ville Koskinen + 1998, Steve Reid + 2000, Wei Dai + 2003, Kevin Springle + 2009, Jonathan Nieder + 2010, Anders F Björklund +License: PD + This file has been put in the public domain. + You can do whatever you want with this file. +Comment: + From: Lasse Collin + To: Jonathan Nieder + Subject: Re: XZ utils for Debian + Date: Sun, 19 Jul 2009 13:28:23 +0300 + Message-Id: <200907191328.23816.lasse.collin@tukaani.org> + . + [...] + . + > AUTHORS, ChangeLog, COPYING, README, THANKS, TODO, + > dos/README, windows/README + . + COPYING says that most docs are in the public domain. Maybe that's not + clear enough, but on the other hand it looks a bit stupid to put + copyright information in tiny and relatively small docs like README. + . + I don't dare to say that _all_ XZ Utils specific docs are in the public + domain unless otherwise mentioned in the file. I'm including PDF files + generated by groff + ps2pdf, and some day I might include Doxygen- + generated HTML docs too. Those don't include any copyright notices, but + it seems likely that groff + ps2pdf or at least Doxygen put some + copyrighted content into the generated files. + +Files: INSTALL NEWS PACKAGERS + windows/README-Windows.txt + windows/INSTALL-Windows.txt +Copyright: 2009-2010, Lasse Collin +License: probably-PD + See the note on AUTHORS, README, and so on above. + +Files: src/scripts/* lib/* extra/scanlzma/scanlzma.c +Copyright: © 1993, Jean-loup Gailly + © 1989-1994, 1996-1999, 2001-2007, Free Software Foundation, Inc. + © 2006 Timo Lindfors + 2005, Charles Levert + 2005, 2009, Lasse Collin + 2009, Andrew Dudman +Other-Authors: Paul Eggert, Ulrich Drepper +License: GPL-2+ + +Files: src/scripts/Makefile.am src/scripts/xzless.1 +Copyright: 2009, Andrew Dudman + 2009, Lasse Collin +License: PD + This file has been put in the public domain. + You can do whatever you want with this file. + +Files: doc/examples/xz_pipe_comp.c doc/examples/xz_pipe_decomp.c +Copyright: 2010, Daniel Mealha Cabrita +License: PD + Not copyrighted -- provided to the public domain. + +Files: lib/getopt.c lib/getopt1.c lib/getopt.in.h +Copyright: © 1987-2007 Free Software Foundation, Inc. +Other-Authors: Ulrich Drepper +License: LGPL-2.1+ + +Files: m4/getopt.m4 m4/posix-shell.m4 +Copyright: © 2002-2006, 2008 Free Software Foundation, Inc. + © 2007-2008 Free Software Foundation, Inc. +Other-Authors: Bruno Haible, Paul Eggert +License: permissive-fsf + +Files: m4/acx_pthread.m4 +Copyright: © 2008, Steven G. Johnson +License: Autoconf + +Files: Doxyfile.in +Copyright: © 1997-2007 by Dimitri van Heesch +Origin: Doxygen 1.4.7 +License: GPL-2 + +Files: src/liblzma/check/crc32_table_?e.h + src/liblzma/check/crc64_table_?e.h + src/liblzma/lzma/fastpos_table.c + src/liblzma/rangecoder/price_table.c +Copyright: none, automatically generated data +Generated-With: + src/liblzma/check/crc32_tablegen.c + src/liblzma/check/crc64_tablegen.c + src/liblzma/lzma/fastpos_tablegen.c + src/liblzma/rangecoder/price_tablegen.c +License: none + No copyright to license. + +Files: .gitignore m4/.gitignore po/.gitignore po/LINGUAS po/POTFILES.in +Copyright: none; these are just short lists. +License: none + No copyright to license. + +Files: tests/compress_prepared_bcj_* +Copyright: 2008-2009, Lasse Collin +Source-Code: tests/bcj_test.c +License: PD + This file has been put into the public domain. + You can do whatever you want with this file. +Comment: + changelog.gz (commit 975d8fd) explains: + . + Recreated the BCJ test files for x86 and SPARC. The old files + were linked with crt*.o, which are copyrighted, and thus the + old test files were not in the public domain as a whole. They + are freely distributable though, but it is better to be careful + and avoid including any copyrighted pieces in the test files. + The new files are just compiled and assembled object files, + and thus don't contain any copyrighted code. + +Files: po/cs.po po/de.po po/fr.po +Copyright: 2010, Marek Černocký + 2010, Andre Noll + 2011, Adrien Nader +License: PD + This file is put in the public domain. + +Files: po/it.po po/pl.po +Copyright: 2009, 2010, Gruppo traduzione italiano di Ubuntu-it + 2010, Lorenzo De Liso + 2009, 2010, 2011, Milo Casagrande + 2011, Jakub Bogusz +License: PD + This file is in the public domain + +Files: INSTALL.generic +Copyright: © 1994, 1995, 1996, 1999, 2000, 2001, 2002, 2004, 2005, + 2006, 2007, 2008, 2009, 2010 Free Software Foundation, Inc. +License: permissive-nowarranty + +Files: dos/config.h +Copyright: © 1992, 1993, 1994, 1999, 2000, 2001, 2002, 2005 + Free Software Foundation, Inc. + 2007-2010, Lasse Collin +Other-Authors: Roland McGrath, Akim Demaille, Paul Eggert, + David Mackenzie, Bruno Haible, and many others. +Origin: configure.ac from XZ Utils, + visibility.m4 serial 1 (gettext-0.15), + Autoconf 2.52g +License: config-h + configure.ac: + . + # Author: Lasse Collin + # + # This file has been put into the public domain. + # You can do whatever you want with this file. + . + visibility.m4: + . + dnl Copyright (C) 2005 Free Software Foundation, Inc. + dnl This file is free software; the Free Software Foundation + dnl gives unlimited permission to copy and/or distribute it, + dnl with or without modifications, as long as this notice is preserved. + . + dnl From Bruno Haible. + . + comments from Autoconf 2.52g: + . + # Copyright 1992, 1993, 1994, 1999, 2000, 2001, 2002 + # Free Software Foundation, Inc. + . + [...] + . + # As a special exception, the Free Software Foundation gives unlimited + # permission to copy, distribute and modify the configure scripts that + # are the output of Autoconf. You need not follow the terms of the GNU + # General Public License when using or distributing such scripts, even + # though portions of the text of Autoconf appear in them. The GNU + # General Public License (GPL) does govern all other use of the material + # that constitutes the Autoconf program. + . + On Debian systems, the complete text of the GNU General Public + License version 2 can be found in ‘/usr/share/common-licenses/GPL-2’. + dos/config.h was generated with autoheader, which tells Autoconf to + output a script to generate a config.h file and then runs it. + +Files: po/Makevars +Origin: gettext-runtime/po/Makevars (gettext-0.12) +Copyright: © 2003 Free Software Foundation, Inc. +Authors: Bruno Haible +License: LGPL-2.1+ + The gettext-runtime package is under the LGPL, see files intl/COPYING.LIB-2.0 + and intl/COPYING.LIB-2.1. + . + On Debian systems, the complete text of intl/COPYING.LIB-2.0 from + gettext-runtime 0.12 can be found in ‘/usr/share/common-licenses/LGPL-2’ + and the text of intl/COPYING.LIB-2.1 can be found in + ‘/usr/share/common-licenses/LGPL-2.1’. + . + po/Makevars consists mostly of helpful comments and does not contain a + copyright and license notice. + +Files: COPYING.GPLv2 COPYING.GPLv3 COPYING.LGPLv2.1 +Copyright: © 1989, 1991, 1999, 2007 Free Software Foundation, Inc. +License: noderivs + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + +Files: debian/* +Copyright: 2009-2012, Jonathan Nieder +License: PD-debian + The Debian packaging files are in the public domain. + You may freely use, modify, distribute, and relicense them. + +License: LGPL-2.1+ + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1, or (at your option) + any later version. + . + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU Lesser General Public License for more details. + . + You should have received a copy of the GNU Lesser General Public License along + with this program; if not, write to the Free Software Foundation, + Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + . + On Debian systems, the complete text of the GNU Lesser General Public + License version 2.1 can be found in ‘/usr/share/common-licenses/LGPL-2.1’. + +License: GPL-2 + Permission to use, copy, modify, and distribute this software and its + documentation under the terms of the GNU General Public License is + hereby granted. No representations are made about the suitability of + this software for any purpose. It is provided "as is" without express + or implied warranty. See the GNU General Public License for more + details. + . + Documents produced by doxygen are derivative works derived from the + input used in their production; they are not affected by this license. + . + On Debian systems, the complete text of the version of the GNU General + Public License distributed with Doxygen can be found in + ‘/usr/share/common-licenses/GPL-2’. + +License: GPL-2+ + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2, or (at your option) + any later version. + . + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + . + You should have received a copy of the GNU General Public License along + with this program; if not, write to the Free Software Foundation, + Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + . + On Debian systems, the complete text of the GNU General Public License + version 2 can be found in ‘/usr/share/common-licenses/GPL-2’. + +License: Autoconf + This program is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation, either version 3 of the License, or (at your + option) any later version. + . + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General + Public License for more details. + . + You should have received a copy of the GNU General Public License along + with this program. If not, see . + . + As a special exception, the respective Autoconf Macro's copyright owner + gives unlimited permission to copy, distribute and modify the configure + scripts that are the output of Autoconf when processing the Macro. You + need not follow the terms of the GNU General Public License when using + or distributing such scripts, even though portions of the text of the + Macro appear in them. The GNU General Public License (GPL) does govern + all other use of the material that constitutes the Autoconf Macro. + . + This special exception to the GPL applies to versions of the Autoconf + Macro released by the Autoconf Archive. When you make and distribute a + modified version of the Autoconf Macro, you may extend this special + exception to the GPL to apply to your modified version as well. + . + On Debian systems, the complete text of the GNU General Public + License version 3 can be found in ‘/usr/share/common-licenses/GPL-3’. + +License: permissive-fsf + This file is free software; the Free Software Foundation + gives unlimited permission to copy and/or distribute it, + with or without modifications, as long as this notice is preserved. + +License: permissive-nowarranty + Copying and distribution of this file, with or without modification, + are permitted in any medium without royalty provided the copyright + notice and this notice are preserved. This file is offered as-is, + without warranty of any kind. diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/python b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/python new file mode 100644 index 0000000000000000000000000000000000000000..ca85f656fb8aabcc6727eb0c81e3ba06e3d5f132 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/python @@ -0,0 +1,958 @@ +This package was put together by Klee Dienes from +sources from ftp.python.org:/pub/python, based on the Debianization by +the previous maintainers Bernd S. Brentrup and +Bruce Perens. Current maintainer is Matthias Klose . + +It was downloaded from http://python.org/ + +Copyright: + +Upstream Author: Guido van Rossum and others. + +License: + +The following text includes the Python license and licenses and +acknowledgements for incorporated software. The licenses can be read +in the HTML and texinfo versions of the documentation as well, after +installing the pythonx.y-doc package. Licenses for files not licensed +under the Python Licenses are found at the end of this file. + + +Python License +============== + +A. HISTORY OF THE SOFTWARE +========================== + +Python was created in the early 1990s by Guido van Rossum at Stichting +Mathematisch Centrum (CWI, see http://www.cwi.nl) in the Netherlands +as a successor of a language called ABC. Guido remains Python's +principal author, although it includes many contributions from others. + +In 1995, Guido continued his work on Python at the Corporation for +National Research Initiatives (CNRI, see http://www.cnri.reston.va.us) +in Reston, Virginia where he released several versions of the +software. + +In May 2000, Guido and the Python core development team moved to +BeOpen.com to form the BeOpen PythonLabs team. In October of the same +year, the PythonLabs team moved to Digital Creations (now Zope +Corporation, see http://www.zope.com). In 2001, the Python Software +Foundation (PSF, see http://www.python.org/psf/) was formed, a +non-profit organization created specifically to own Python-related +Intellectual Property. Zope Corporation is a sponsoring member of +the PSF. + +All Python releases are Open Source (see http://www.opensource.org for +the Open Source Definition). Historically, most, but not all, Python +releases have also been GPL-compatible; the table below summarizes +the various releases. + + Release Derived Year Owner GPL- + from compatible? (1) + + 0.9.0 thru 1.2 1991-1995 CWI yes + 1.3 thru 1.5.2 1.2 1995-1999 CNRI yes + 1.6 1.5.2 2000 CNRI no + 2.0 1.6 2000 BeOpen.com no + 1.6.1 1.6 2001 CNRI yes (2) + 2.1 2.0+1.6.1 2001 PSF no + 2.0.1 2.0+1.6.1 2001 PSF yes + 2.1.1 2.1+2.0.1 2001 PSF yes + 2.2 2.1.1 2001 PSF yes + 2.1.2 2.1.1 2002 PSF yes + 2.1.3 2.1.2 2002 PSF yes + 2.2.1 2.2 2002 PSF yes + 2.2.2 2.2.1 2002 PSF yes + 2.2.3 2.2.2 2003 PSF yes + 2.3 2.2.2 2002-2003 PSF yes + 2.3.1 2.3 2002-2003 PSF yes + 2.3.2 2.3.1 2002-2003 PSF yes + 2.3.3 2.3.2 2002-2003 PSF yes + 2.3.4 2.3.3 2004 PSF yes + 2.3.5 2.3.4 2005 PSF yes + 2.4 2.3 2004 PSF yes + 2.4.1 2.4 2005 PSF yes + 2.4.2 2.4.1 2005 PSF yes + 2.4.3 2.4.2 2006 PSF yes + 2.5 2.4 2006 PSF yes + 2.5.1 2.5 2007 PSF yes + 2.5.2 2.5.1 2008 PSF yes + 2.5.3 2.5.2 2008 PSF yes + 2.6 2.5 2008 PSF yes + 2.6.1 2.6 2008 PSF yes + 2.6.2 2.6.1 2009 PSF yes + 2.6.3 2.6.2 2009 PSF yes + 2.6.4 2.6.3 2009 PSF yes + 2.6.5 2.6.4 2010 PSF yes + 2.7 2.6 2010 PSF yes + +Footnotes: + +(1) GPL-compatible doesn't mean that we're distributing Python under + the GPL. All Python licenses, unlike the GPL, let you distribute + a modified version without making your changes open source. The + GPL-compatible licenses make it possible to combine Python with + other software that is released under the GPL; the others don't. + +(2) According to Richard Stallman, 1.6.1 is not GPL-compatible, + because its license has a choice of law clause. According to + CNRI, however, Stallman's lawyer has told CNRI's lawyer that 1.6.1 + is "not incompatible" with the GPL. + +Thanks to the many outside volunteers who have worked under Guido's +direction to make these releases possible. + + +B. TERMS AND CONDITIONS FOR ACCESSING OR OTHERWISE USING PYTHON +=============================================================== + +PYTHON SOFTWARE FOUNDATION LICENSE VERSION 2 +-------------------------------------------- + +1. This LICENSE AGREEMENT is between the Python Software Foundation +("PSF"), and the Individual or Organization ("Licensee") accessing and +otherwise using this software ("Python") in source or binary form and +its associated documentation. + +2. Subject to the terms and conditions of this License Agreement, PSF +hereby grants Licensee a nonexclusive, royalty-free, world-wide +license to reproduce, analyze, test, perform and/or display publicly, +prepare derivative works, distribute, and otherwise use Python +alone or in any derivative version, provided, however, that PSF's +License Agreement and PSF's notice of copyright, i.e., "Copyright (c) +2001, 2002, 2003, 2004, 2005, 2006, 2007 Python Software Foundation; +All Rights Reserved" are retained in Python alone or in any derivative +version prepared by Licensee. + +3. In the event Licensee prepares a derivative work that is based on +or incorporates Python or any part thereof, and wants to make +the derivative work available to others as provided herein, then +Licensee hereby agrees to include in any such work a brief summary of +the changes made to Python. + +4. PSF is making Python available to Licensee on an "AS IS" +basis. PSF MAKES NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR +IMPLIED. BY WAY OF EXAMPLE, BUT NOT LIMITATION, PSF MAKES NO AND +DISCLAIMS ANY REPRESENTATION OR WARRANTY OF MERCHANTABILITY OR FITNESS +FOR ANY PARTICULAR PURPOSE OR THAT THE USE OF PYTHON WILL NOT +INFRINGE ANY THIRD PARTY RIGHTS. + +5. PSF SHALL NOT BE LIABLE TO LICENSEE OR ANY OTHER USERS OF PYTHON +FOR ANY INCIDENTAL, SPECIAL, OR CONSEQUENTIAL DAMAGES OR LOSS AS +A RESULT OF MODIFYING, DISTRIBUTING, OR OTHERWISE USING PYTHON, +OR ANY DERIVATIVE THEREOF, EVEN IF ADVISED OF THE POSSIBILITY THEREOF. + +6. This License Agreement will automatically terminate upon a material +breach of its terms and conditions. + +7. Nothing in this License Agreement shall be deemed to create any +relationship of agency, partnership, or joint venture between PSF and +Licensee. This License Agreement does not grant permission to use PSF +trademarks or trade name in a trademark sense to endorse or promote +products or services of Licensee, or any third party. + +8. By copying, installing or otherwise using Python, Licensee +agrees to be bound by the terms and conditions of this License +Agreement. + + +BEOPEN.COM LICENSE AGREEMENT FOR PYTHON 2.0 +------------------------------------------- + +BEOPEN PYTHON OPEN SOURCE LICENSE AGREEMENT VERSION 1 + +1. This LICENSE AGREEMENT is between BeOpen.com ("BeOpen"), having an +office at 160 Saratoga Avenue, Santa Clara, CA 95051, and the +Individual or Organization ("Licensee") accessing and otherwise using +this software in source or binary form and its associated +documentation ("the Software"). + +2. Subject to the terms and conditions of this BeOpen Python License +Agreement, BeOpen hereby grants Licensee a non-exclusive, +royalty-free, world-wide license to reproduce, analyze, test, perform +and/or display publicly, prepare derivative works, distribute, and +otherwise use the Software alone or in any derivative version, +provided, however, that the BeOpen Python License is retained in the +Software, alone or in any derivative version prepared by Licensee. + +3. BeOpen is making the Software available to Licensee on an "AS IS" +basis. BEOPEN MAKES NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR +IMPLIED. BY WAY OF EXAMPLE, BUT NOT LIMITATION, BEOPEN MAKES NO AND +DISCLAIMS ANY REPRESENTATION OR WARRANTY OF MERCHANTABILITY OR FITNESS +FOR ANY PARTICULAR PURPOSE OR THAT THE USE OF THE SOFTWARE WILL NOT +INFRINGE ANY THIRD PARTY RIGHTS. + +4. BEOPEN SHALL NOT BE LIABLE TO LICENSEE OR ANY OTHER USERS OF THE +SOFTWARE FOR ANY INCIDENTAL, SPECIAL, OR CONSEQUENTIAL DAMAGES OR LOSS +AS A RESULT OF USING, MODIFYING OR DISTRIBUTING THE SOFTWARE, OR ANY +DERIVATIVE THEREOF, EVEN IF ADVISED OF THE POSSIBILITY THEREOF. + +5. This License Agreement will automatically terminate upon a material +breach of its terms and conditions. + +6. This License Agreement shall be governed by and interpreted in all +respects by the law of the State of California, excluding conflict of +law provisions. Nothing in this License Agreement shall be deemed to +create any relationship of agency, partnership, or joint venture +between BeOpen and Licensee. This License Agreement does not grant +permission to use BeOpen trademarks or trade names in a trademark +sense to endorse or promote products or services of Licensee, or any +third party. As an exception, the "BeOpen Python" logos available at +http://www.pythonlabs.com/logos.html may be used according to the +permissions granted on that web page. + +7. By copying, installing or otherwise using the software, Licensee +agrees to be bound by the terms and conditions of this License +Agreement. + + +CNRI LICENSE AGREEMENT FOR PYTHON 1.6.1 +--------------------------------------- + +1. This LICENSE AGREEMENT is between the Corporation for National +Research Initiatives, having an office at 1895 Preston White Drive, +Reston, VA 20191 ("CNRI"), and the Individual or Organization +("Licensee") accessing and otherwise using Python 1.6.1 software in +source or binary form and its associated documentation. + +2. Subject to the terms and conditions of this License Agreement, CNRI +hereby grants Licensee a nonexclusive, royalty-free, world-wide +license to reproduce, analyze, test, perform and/or display publicly, +prepare derivative works, distribute, and otherwise use Python 1.6.1 +alone or in any derivative version, provided, however, that CNRI's +License Agreement and CNRI's notice of copyright, i.e., "Copyright (c) +1995-2001 Corporation for National Research Initiatives; All Rights +Reserved" are retained in Python 1.6.1 alone or in any derivative +version prepared by Licensee. Alternately, in lieu of CNRI's License +Agreement, Licensee may substitute the following text (omitting the +quotes): "Python 1.6.1 is made available subject to the terms and +conditions in CNRI's License Agreement. This Agreement together with +Python 1.6.1 may be located on the Internet using the following +unique, persistent identifier (known as a handle): 1895.22/1013. This +Agreement may also be obtained from a proxy server on the Internet +using the following URL: http://hdl.handle.net/1895.22/1013". + +3. In the event Licensee prepares a derivative work that is based on +or incorporates Python 1.6.1 or any part thereof, and wants to make +the derivative work available to others as provided herein, then +Licensee hereby agrees to include in any such work a brief summary of +the changes made to Python 1.6.1. + +4. CNRI is making Python 1.6.1 available to Licensee on an "AS IS" +basis. CNRI MAKES NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR +IMPLIED. BY WAY OF EXAMPLE, BUT NOT LIMITATION, CNRI MAKES NO AND +DISCLAIMS ANY REPRESENTATION OR WARRANTY OF MERCHANTABILITY OR FITNESS +FOR ANY PARTICULAR PURPOSE OR THAT THE USE OF PYTHON 1.6.1 WILL NOT +INFRINGE ANY THIRD PARTY RIGHTS. + +5. CNRI SHALL NOT BE LIABLE TO LICENSEE OR ANY OTHER USERS OF PYTHON +1.6.1 FOR ANY INCIDENTAL, SPECIAL, OR CONSEQUENTIAL DAMAGES OR LOSS AS +A RESULT OF MODIFYING, DISTRIBUTING, OR OTHERWISE USING PYTHON 1.6.1, +OR ANY DERIVATIVE THEREOF, EVEN IF ADVISED OF THE POSSIBILITY THEREOF. + +6. This License Agreement will automatically terminate upon a material +breach of its terms and conditions. + +7. This License Agreement shall be governed by the federal +intellectual property law of the United States, including without +limitation the federal copyright law, and, to the extent such +U.S. federal law does not apply, by the law of the Commonwealth of +Virginia, excluding Virginia's conflict of law provisions. +Notwithstanding the foregoing, with regard to derivative works based +on Python 1.6.1 that incorporate non-separable material that was +previously distributed under the GNU General Public License (GPL), the +law of the Commonwealth of Virginia shall govern this License +Agreement only as to issues arising under or with respect to +Paragraphs 4, 5, and 7 of this License Agreement. Nothing in this +License Agreement shall be deemed to create any relationship of +agency, partnership, or joint venture between CNRI and Licensee. This +License Agreement does not grant permission to use CNRI trademarks or +trade name in a trademark sense to endorse or promote products or +services of Licensee, or any third party. + +8. By clicking on the "ACCEPT" button where indicated, or by copying, +installing or otherwise using Python 1.6.1, Licensee agrees to be +bound by the terms and conditions of this License Agreement. + + ACCEPT + + +CWI LICENSE AGREEMENT FOR PYTHON 0.9.0 THROUGH 1.2 +-------------------------------------------------- + +Copyright (c) 1991 - 1995, Stichting Mathematisch Centrum Amsterdam, +The Netherlands. All rights reserved. + +Permission to use, copy, modify, and distribute this software and its +documentation for any purpose and without fee is hereby granted, +provided that the above copyright notice appear in all copies and that +both that copyright notice and this permission notice appear in +supporting documentation, and that the name of Stichting Mathematisch +Centrum or CWI not be used in advertising or publicity pertaining to +distribution of the software without specific, written prior +permission. + +STICHTING MATHEMATISCH CENTRUM DISCLAIMS ALL WARRANTIES WITH REGARD TO +THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS, IN NO EVENT SHALL STICHTING MATHEMATISCH CENTRUM BE LIABLE +FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT +OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + + +Licenses and Acknowledgements for Incorporated Software +======================================================= + +Mersenne Twister +---------------- + +The `_random' module includes code based on a download from +`http://www.math.keio.ac.jp/~matumoto/MT2002/emt19937ar.html'. The +following are the verbatim comments from the original code: + + A C-program for MT19937, with initialization improved 2002/1/26. + Coded by Takuji Nishimura and Makoto Matsumoto. + + Before using, initialize the state by using init_genrand(seed) + or init_by_array(init_key, key_length). + + Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura, + All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + 3. The names of its contributors may not be used to endorse or promote + products derived from this software without specific prior written + permission. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED + TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + Any feedback is very welcome. + http://www.math.keio.ac.jp/matumoto/emt.html + email: matumoto@math.keio.ac.jp + + +Sockets +------- + +The `socket' module uses the functions, `getaddrinfo', and +`getnameinfo', which are coded in separate source files from the WIDE +Project, `http://www.wide.ad.jp/about/index.html'. + + Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. + All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + 3. Neither the name of the project nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND + GAI_ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE + FOR GAI_ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON GAI_ANY THEORY OF LIABILITY, WHETHER + IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + ARISING IN GAI_ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + OF THE POSSIBILITY OF SUCH DAMAGE. + + +Floating point exception control +-------------------------------- + +The source for the `fpectl' module includes the following notice: + + --------------------------------------------------------------------- + / Copyright (c) 1996. \ + | The Regents of the University of California. | + | All rights reserved. | + | | + | Permission to use, copy, modify, and distribute this software for | + | any purpose without fee is hereby granted, provided that this en- | + | tire notice is included in all copies of any software which is or | + | includes a copy or modification of this software and in all | + | copies of the supporting documentation for such software. | + | | + | This work was produced at the University of California, Lawrence | + | Livermore National Laboratory under contract no. W-7405-ENG-48 | + | between the U.S. Department of Energy and The Regents of the | + | University of California for the operation of UC LLNL. | + | | + | DISCLAIMER | + | | + | This software was prepared as an account of work sponsored by an | + | agency of the United States Government. Neither the United States | + | Government nor the University of California nor any of their em- | + | ployees, makes any warranty, express or implied, or assumes any | + | liability or responsibility for the accuracy, completeness, or | + | usefulness of any information, apparatus, product, or process | + | disclosed, or represents that its use would not infringe | + | privately-owned rights. Reference herein to any specific commer- | + | cial products, process, or service by trade name, trademark, | + | manufacturer, or otherwise, does not necessarily constitute or | + | imply its endorsement, recommendation, or favoring by the United | + | States Government or the University of California. The views and | + | opinions of authors expressed herein do not necessarily state or | + | reflect those of the United States Government or the University | + | of California, and shall not be used for advertising or product | + \ endorsement purposes. / + --------------------------------------------------------------------- + + +Cookie management +----------------- + +The `Cookie' module contains the following notice: + + Copyright 2000 by Timothy O'Malley + + All Rights Reserved + + Permission to use, copy, modify, and distribute this software + and its documentation for any purpose and without fee is hereby + granted, provided that the above copyright notice appear in all + copies and that both that copyright notice and this permission + notice appear in supporting documentation, and that the name of + Timothy O'Malley not be used in advertising or publicity + pertaining to distribution of the software without specific, written + prior permission. + + Timothy O'Malley DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS + SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY + AND FITNESS, IN NO EVENT SHALL Timothy O'Malley BE LIABLE FOR + ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, + WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS + ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR + PERFORMANCE OF THIS SOFTWARE. + + +Execution tracing +----------------- + +The `trace' module contains the following notice: + + portions copyright 2001, Autonomous Zones Industries, Inc., all rights... + err... reserved and offered to the public under the terms of the + Python 2.2 license. + Author: Zooko O'Whielacronx + http://zooko.com/ + mailto:zooko@zooko.com + + Copyright 2000, Mojam Media, Inc., all rights reserved. + Author: Skip Montanaro + + Copyright 1999, Bioreason, Inc., all rights reserved. + Author: Andrew Dalke + + Copyright 1995-1997, Automatrix, Inc., all rights reserved. + Author: Skip Montanaro + + Copyright 1991-1995, Stichting Mathematisch Centrum, all rights reserved. + + Permission to use, copy, modify, and distribute this Python software and + its associated documentation for any purpose without fee is hereby + granted, provided that the above copyright notice appears in all copies, + and that both that copyright notice and this permission notice appear in + supporting documentation, and that the name of neither Automatrix, + Bioreason or Mojam Media be used in advertising or publicity pertaining + to distribution of the software without specific, written prior + permission. + + +UUencode and UUdecode functions +------------------------------- + +The `uu' module contains the following notice: + + Copyright 1994 by Lance Ellinghouse + Cathedral City, California Republic, United States of America. + All Rights Reserved + Permission to use, copy, modify, and distribute this software and its + documentation for any purpose and without fee is hereby granted, + provided that the above copyright notice appear in all copies and that + both that copyright notice and this permission notice appear in + supporting documentation, and that the name of Lance Ellinghouse + not be used in advertising or publicity pertaining to distribution + of the software without specific, written prior permission. + LANCE ELLINGHOUSE DISCLAIMS ALL WARRANTIES WITH REGARD TO + THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS, IN NO EVENT SHALL LANCE ELLINGHOUSE CENTRUM BE LIABLE + FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT + OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + + Modified by Jack Jansen, CWI, July 1995: + - Use binascii module to do the actual line-by-line conversion + between ascii and binary. This results in a 1000-fold speedup. The C + version is still 5 times faster, though. + - Arguments more compliant with python standard + + +XML Remote Procedure Calls +-------------------------- + +The `xmlrpclib' module contains the following notice: + + The XML-RPC client interface is + + Copyright (c) 1999-2002 by Secret Labs AB + Copyright (c) 1999-2002 by Fredrik Lundh + + By obtaining, using, and/or copying this software and/or its + associated documentation, you agree that you have read, understood, + and will comply with the following terms and conditions: + + Permission to use, copy, modify, and distribute this software and + its associated documentation for any purpose and without fee is + hereby granted, provided that the above copyright notice appears in + all copies, and that both that copyright notice and this permission + notice appear in supporting documentation, and that the name of + Secret Labs AB or the author not be used in advertising or publicity + pertaining to distribution of the software without specific, written + prior permission. + + SECRET LABS AB AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD + TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANT- + ABILITY AND FITNESS. IN NO EVENT SHALL SECRET LABS AB OR THE AUTHOR + BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY + DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, + WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS + ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE + OF THIS SOFTWARE. + +Licenses for Software linked to +=============================== + +Note that the choice of GPL compatibility outlined above doesn't extend +to modules linked to particular libraries, since they change the +effective License of the module binary. + + +GNU Readline +------------ + +The 'readline' module makes use of GNU Readline. + + The GNU Readline Library is free software; you can redistribute it + and/or modify it under the terms of the GNU General Public License as + published by the Free Software Foundation; either version 2, or (at + your option) any later version. + + On Debian systems, you can find the complete statement in + /usr/share/doc/readline-common/copyright'. A copy of the GNU General + Public License is available in /usr/share/common-licenses/GPL-2'. + + +OpenSSL +------- + +The '_ssl' module makes use of OpenSSL. + + The OpenSSL toolkit stays under a dual license, i.e. both the + conditions of the OpenSSL License and the original SSLeay license + apply to the toolkit. Actually both licenses are BSD-style Open + Source licenses. Note that both licenses are incompatible with + the GPL. + + On Debian systems, you can find the complete license text in + /usr/share/doc/openssl/copyright'. + + +Files with other licenses than the Python License +------------------------------------------------- + +Files: Lib/profile.py Lib/pstats.py +Copyright: Disney Enterprises, Inc. All Rights Reserved. +License: # Licensed to PSF under a Contributor Agreement + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, + either express or implied. See the License for the specific language + overning permissions and limitations under the License. + + On Debian systems, the Apache 2.0 license can be found in + /usr/share/common-licenses/Apache-2.0. + +Files: Modules/zlib/* +Copyright: (C) 1995-2010 Jean-loup Gailly and Mark Adler +License: This software is provided 'as-is', without any express or implied + warranty. In no event will the authors be held liable for any damages + arising from the use of this software. + + Permission is granted to anyone to use this software for any purpose, + including commercial applications, and to alter it and redistribute it + freely, subject to the following restrictions: + + 1. The origin of this software must not be misrepresented; you must not + claim that you wrote the original software. If you use this software + in a product, an acknowledgment in the product documentation would be + appreciated but is not required. + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + 3. This notice may not be removed or altered from any source distribution. + + Jean-loup Gailly Mark Adler + jloup@gzip.org madler@alumni.caltech.edu + + If you use the zlib library in a product, we would appreciate *not* receiving + lengthy legal documents to sign. The sources are provided for free but without + warranty of any kind. The library has been entirely written by Jean-loup + Gailly and Mark Adler; it does not include third-party code. + +Files: Modules/_ctypes/libffi/* +Copyright: Copyright (C) 1996-2009 Red Hat, Inc and others. +License: Permission is hereby granted, free of charge, to any person obtaining + a copy of this software and associated documentation files (the + ``Software''), to deal in the Software without restriction, including + without limitation the rights to use, copy, modify, merge, publish, + distribute, sublicense, and/or sell copies of the Software, and to + permit persons to whom the Software is furnished to do so, subject to + the following conditions: + + The above copyright notice and this permission notice shall be included + in all copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND, + EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + DEALINGS IN THE SOFTWARE. + + Documentation: + Permission is granted to copy, distribute and/or modify this document + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 2, or (at your option) any + later version. A copy of the license is included in the + section entitled ``GNU General Public License''. + +Files: Modules/expat/* +Copyright: Copyright (c) 1998, 1999, 2000 Thai Open Source Software Center Ltd + and Clark Cooper + Copyright (c) 2001, 2002, 2003, 2004, 2005, 2006 Expat maintainers +License: Permission is hereby granted, free of charge, to any person obtaining + a copy of this software and associated documentation files (the + "Software"), to deal in the Software without restriction, including + without limitation the rights to use, copy, modify, merge, publish, + distribute, sublicense, and/or sell copies of the Software, and to + permit persons to whom the Software is furnished to do so, subject to + the following conditions: + + The above copyright notice and this permission notice shall be included + in all copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY + CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, + TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE + SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +Files: Misc/python-mode.el +Copyright: Copyright (C) 1992,1993,1994 Tim Peters +License: This software is provided as-is, without express or implied + warranty. Permission to use, copy, modify, distribute or sell this + software, without fee, for any purpose and by any individual or + organization, is hereby granted, provided that the above copyright + notice and this paragraph appear in all copies. + +Files: PC/_subprocess.c +Copyright: Copyright (c) 2004 by Fredrik Lundh + Copyright (c) 2004 by Secret Labs AB, http://www.pythonware.com + Copyright (c) 2004 by Peter Astrand +License: + * Permission to use, copy, modify, and distribute this software and + * its associated documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appears in + * all copies, and that both that copyright notice and this permission + * notice appear in supporting documentation, and that the name of the + * authors not be used in advertising or publicity pertaining to + * distribution of the software without specific, written prior + * permission. + * + * THE AUTHORS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. + * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY SPECIAL, INDIRECT OR + * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS + * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, + * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION + * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + +Files: PC/winsound.c +Copyright: Copyright (c) 1999 Toby Dickenson +License: * Permission to use this software in any way is granted without + * fee, provided that the copyright notice above appears in all + * copies. This software is provided "as is" without any warranty. + */ + +/* Modified by Guido van Rossum */ +/* Beep added by Mark Hammond */ +/* Win9X Beep and platform identification added by Uncle Timmy */ + +Files: Lib/ensurepip/_bundled/setuptools-*.whl +License: see above, some license as Python. + +Files: Lib/ensurepip/_bundled/pip-*.whl +Copyright: Copyright © 2008-2013 The pip developers: + Alex Grönholm + Alex Morega + Alexandre Conrad + Andrey Bulgakov + Antti Kaihola + Armin Ronacher + Aziz Köksal + Ben Rosser + Brian Rosner + Carl Meyer + Chris McDonough + Christian Oudard + Clay McClure + Cody Soyland + Daniel Holth + Dave Abrahams + David (d1b) + Dmitry Gladkov + Donald Stufft + Francesco + Geoffrey Lehée + Georgi Valkov + Hugo Lopes Tavares + Ian Bicking + Igor Sobreira + Ionel Maries Cristian + Jakub Vysoky + James Cleveland + Jannis Leidel + Jay Graves + John-Scott Atlakson + Jon Parise + Jonas Nockert + Josh Bronson + Kamal Bin Mustafa + Kelsey Hightower + Kenneth Belitzky + Kumar McMillan + Luke Macken + Masklinn + Marc Abramowitz + Marcus Smith + Markus Hametner + Matt Maker + Maxime R. + Miguel Araujo + Nick Stenning + Nowell Strite + Oliver Tonnhofer + Olivier Girardot + Patrick Jenkins + Paul Moore + Paul Nasrat + Paul Oswald + Paul van der Linden + Peter Waller + Phil Whelan + Piet Delport + Przemek Wrzos + Qiangning Hong + Rafael Caricio + Rene Dudfield + Roey Berman + Ronny Pfannschmidt + Rory McCann + Simon Cross + Stavros Korokithakis + Thomas Fenzl + Thomas Johansson + Vinay Sajip + Vitaly Babiy + W Trevor King + Wil Tan + Hsiaoming Yang +License: Expat + Permission is hereby granted, free of charge, to any person obtaining + a copy of this software and associated documentation files (the + "Software"), to deal in the Software without restriction, including + without limitation the rights to use, copy, modify, merge, publish, + distribute, sublicense, and/or sell copies of the Software, and to + permit persons to whom the Software is furnished to do so, subject to + the following conditions: + . + The above copyright notice and this permission notice shall be + included in all copies or substantial portions of the Software. + . + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE + LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/ipaddress.py +Copyright: 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013, 2014 Python Software Foundation; All Rights Reserved + 2007 Google Inc. +License: PSF-2 + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/retrying.py +Copyright: (c) 2013-2014, + (c) 2014, Derek Wilson + (c) 2014, Alex Kuang +License: Apache-2 + +License: Apache-2 + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + . + http://www.apache.org/licenses/LICENSE-2.0 + . + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + . + On Debian-based systems the full text of the Apache version 2.0 license + can be found in /usr/share/common-licenses/Apache-2.0. + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/six.py +Copyright: Copyright (c) 2010-2014 Benjamin Peterson +License: Expat + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/cachecontrol +Copyright: 2015 Eric Larson +License: Apache-2.0 + Copyright 2015 Eric Larson + . + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + . + http://www.apache.org/licenses/LICENSE-2.0 + . + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied. + . + See the License for the specific language governing permissions and + limitations under the License. + . + On Debian systems, the license is available at + /usr/share/common-licenses/Apache-2.0 + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/colorama +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/distlib +Copyright: Copyright (C) 2012-2013 The Python Software Foundation + Copyright (C) 2012-2013 Vinay Sajip +License: Python + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/html5lib +html5lib is Copyright (c) 2006 The Authors +Authors: + James Graham - james@hoppipolla.co.uk + Anne van Kesteren - annevankesteren@gmail.com + Lachlan Hunt - lachlan.hunt@lachy.id.au + Matt McDonald - kanashii@kanashii.ca + Sam Ruby - rubys@intertwingly.net + Ian Hickson (Google) - ian@hixie.ch + Thomas Broyer - t.broyer@gmail.com + +License: + +Permission is hereby granted, free of charge, to any person obtaining a copy of +this software and associated documentation files (the "Software"), to deal in +the Software without restriction, including without limitation the rights to +use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies +of the Software, and to permit persons to whom the Software is furnished to do +so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/lockfile +Copyright: + © 2014–2015 OpenStack Foundation + © 2007–2012 Skip Montanaro + © 2008–2014 Ben Finney +License: Expat + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/packaging +Copyright: Copyright (C) 2014 Donald Stufft + Copyright (C) 2012-2013 Vinay Sajip +License: Apache-2.0 + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/progress +Copyright: Copyright (c) 2012 Giorgos Verigakis +License: ISC + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/requests +Copyright: 2016, Kenneth Reitz +License: Apache + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/requests/packages/urllib3/* +Copyright: 2008-2016, Andrey Petrov +License: Expat + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/requests/packages/urllib3/packages/ordered_dict.py +Copyright: 2009, Raymond Hettinger +License: Expat + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/requests/packages/urllib3/packages/ssl_match_hostname/__init__.py +Copyright: 2011, Python Software Foundation +License: PSF-2 + +Files: Lib/ensurepip/_bundled/pip-*.whl/pip/_vendor/requests/packages/chardet/* +Copyright: 2006-2008, Mark Pilgrim + 2012-2013, Ian Cordasco +License: LGPL-2.1+ diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/trilicense b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/trilicense new file mode 100644 index 0000000000000000000000000000000000000000..33d768c58817f81667b489ca026200f50d66e4fc --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/copyright/trilicense @@ -0,0 +1,13 @@ +Files: src/js/editline/* +Copyright: 1993, John Doe + 1993, Joe Average +License: MPL-1.1 or GPL-2 or LGPL-2.1 + +License: MPL-1.1 + [LICENSE TEXT] + +License: GPL-2 + [LICENSE TEXT] + +License: LGPL-2.1 + [LICENSE TEXT] \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/image-dpkg/Dockerfile b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/image-dpkg/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..770e60b56041910528ff605926f15d2b18bb157f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/image-dpkg/Dockerfile @@ -0,0 +1,2 @@ +FROM scratch +COPY . . \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/image-dpkg/usr/share/doc/libpam-runtime/copyright b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/image-dpkg/usr/share/doc/libpam-runtime/copyright new file mode 100644 index 0000000000000000000000000000000000000000..363b056eb51ddc1a4f55ab3fecf13e2c60ab1147 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/image-dpkg/usr/share/doc/libpam-runtime/copyright @@ -0,0 +1,43 @@ +Format: http://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ +Upstream-Name: auditd +Source: https://people.redhat.com/sgrubb/audit/ + +Files: * +Copyright: 2012-2016 Steve Grubb + 2006-2012 Rik Faith +License: GPL-2 + +Files: src/libev/* +Copyright: 2007-2009 Marc Alexamder Lehmann +License: GPL-2 + +Files: lib/* +Copyright: 2005-2008 Steve Grubb +License: LGPL-2.1 + The audit daemon's library libaudit.* is released under LGPL + so that it may be linked with 3rd party software. + . + On Debian systems, refer to /usr/share/common-licenses/LGPL-2.1 + for the complete text of the GNU Lesser General Public License. + +Files: debian/* +Copyright: 2007-2011 Philipp Matthias Hahn + 2012-2016 Laurent Bigonville +License: GPL-2 + +License: GPL-2 + This package is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License version 2, + as published by the Free Software Foundation. + . + This package is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + . + You should have received a copy of the GNU General Public License + along with this package; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + . + On Debian systems, the complete text of the GNU General + Public License can be found in `/usr/share/common-licenses/GPL-1'. diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/info/util-linux.conffiles b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/info/util-linux.conffiles new file mode 100644 index 0000000000000000000000000000000000000000..173ae853c60734352d81ebbd36e705b4ddee150a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/info/util-linux.conffiles @@ -0,0 +1,6 @@ +/etc/default/hwclock +/etc/init.d/hwclock.sh +/etc/pam.d/runuser +/etc/pam.d/runuser-l +/etc/pam.d/su +/etc/pam.d/su-l \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/info/zlib1g.md5sums b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/info/zlib1g.md5sums new file mode 100644 index 0000000000000000000000000000000000000000..70a9410cf3f19bb9c64bab0820ea3546c0db41e8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/info/zlib1g.md5sums @@ -0,0 +1,4 @@ +55f905631797551d4d936a34c7e73474 lib/x86_64-linux-gnu/libz.so.1.2.11 +cede84bda30d2380217f97753c8ccf3a usr/share/doc/zlib1g/changelog.Debian.gz +f3c9dafa6da7992c47328b4464f6d122 usr/share/doc/zlib1g/changelog.gz +a4fae96070439a5209a62ae5b8017ab2 usr/share/doc/zlib1g/copyright \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/empty b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/empty new file mode 100644 index 0000000000000000000000000000000000000000..3a74c4a01cc10b34d04ce27c5d35f45e700116c0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/empty @@ -0,0 +1 @@ +Package: \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/installed-size-4KB b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/installed-size-4KB new file mode 100644 index 0000000000000000000000000000000000000000..5a7cbd19a8818bed694e34e94b6fc2cba03c83d4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/installed-size-4KB @@ -0,0 +1,31 @@ +Package: apt +Status: install ok installed +Priority: required +Section: admin +Installed-Size: 4KB +Maintainer: APT Development Team +Architecture: amd64 +Version: 1.8.2 +Source: apt-dev +Replaces: apt-transport-https (<< 1.5~alpha4~), apt-utils (<< 1.3~exp2~) +Provides: apt-transport-https (= 1.8.2) +Depends: adduser, gpgv | gpgv2 | gpgv1, debian-archive-keyring, libapt-pkg5.0 (>= 1.7.0~alpha3~), libc6 (>= 2.15), libgcc1 (>= 1:3.0), libgnutls30 (>= 3.6.6), libseccomp2 (>= 1.0.1), libstdc++6 (>= 5.2) +Recommends: ca-certificates +Suggests: apt-doc, aptitude | synaptic | wajig, dpkg-dev (>= 1.17.2), gnupg | gnupg2 | gnupg1, powermgmt-base +Breaks: apt-transport-https (<< 1.5~alpha4~), apt-utils (<< 1.3~exp2~), aptitude (<< 0.8.10) +Conffiles: +Description: commandline package manager + This package provides commandline tools for searching and + managing as well as querying information about packages + as a low-level access to all features of the libapt-pkg library. + . + These include: + * apt-get for retrieval of packages and information about them + from authenticated sources and for installation, upgrade and + removal of packages together with their dependencies + * apt-cache for querying available information about installed + as well as installable packages + * apt-cdrom to use removable media as a source for packages + * apt-config as an interface to the configuration settings + * apt-key as an interface to manage authentication keys + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/multiple b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/multiple new file mode 100644 index 0000000000000000000000000000000000000000..956a1af3ef2eb2c7ef90a73106c15c9be5e8fede --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/multiple @@ -0,0 +1,56 @@ +Package: + +Package: no-version + +Package: tzdata +Status: install ok installed +Priority: required +Source: tzdata-dev +Section: localization +Installed-Size: 3036 +Maintainer: GNU Libc Maintainers +Architecture: all +Multi-Arch: foreign +Version: 2020a-0+deb10u1 +Replaces: libc0.1, libc0.3, libc6, libc6.1 +Provides: tzdata-buster +Depends: debconf (>= 0.5) | debconf-2.0 +Description: time zone and daylight-saving time data + This package contains data required for the implementation of + standard local time for many representative locations around the + globe. It is updated periodically to reflect changes made by + political bodies to time zone boundaries, UTC offsets, and + daylight-saving rules. +Homepage: https://www.iana.org/time-zones + +Package: util-linux +Essential: yes +Status: install ok installed +Priority: required +Section: utils +Installed-Size: 4327 +Maintainer: LaMont Jones +Architecture: amd64 +Multi-Arch: foreign +Version: 2.33.1-0.1 +Replaces: bash-completion (<< 1:2.8), initscripts (<< 2.88dsf-59.2~), login (<< 1:4.5-1.1~), mount (<< 2.29.2-3~), s390-tools (<< 2.2.0-1~), setpriv (<< 2.32.1-0.2~), sysvinit-utils (<< 2.88dsf-59.1~) +Depends: fdisk, login (>= 1:4.5-1.1~) +Pre-Depends: libaudit1 (>= 1:2.2.1), libblkid1 (>= 2.31.1), libc6 (>= 2.25), libcap-ng0 (>= 0.7.9), libmount1 (>= 2.25), libpam0g (>= 0.99.7.1), libselinux1 (>= 2.6-3~), libsmartcols1 (>= 2.33), libsystemd0, libtinfo6 (>= 6), libudev1 (>= 183), libuuid1 (>= 2.16), zlib1g (>= 1:1.1.4) +Suggests: dosfstools, kbd | console-tools, util-linux-locales +Breaks: bash-completion (<< 1:2.8), grml-debootstrap (<< 0.68), mount (<< 2.29.2-3~), s390-tools (<< 2.2.0-1~), setpriv (<< 2.32.1-0.2~), sysvinit-utils (<< 2.88dsf-59.4~) +Conffiles: + /etc/default/hwclock 3916544450533eca69131f894db0ca12 + /etc/init.d/hwclock.sh 1ca5c0743fa797ffa364db95bb8d8d8e + /etc/pam.d/runuser b8b44b045259525e0fae9e38fdb2aeeb + /etc/pam.d/runuser-l 2106ea05877e8913f34b2c77fa02be45 + /etc/pam.d/su ce6dcfda3b190a27a455bb38a45ff34a + /etc/pam.d/su-l 756fef5687fecc0d986e5951427b0c4f +Description: miscellaneous system utilities + This package contains a number of important utilities, most of which + are oriented towards maintenance of your system. Some of the more + important utilities included in this package allow you to view kernel + messages, create new filesystems, view block device information, + interface with real time clock, etc. + + + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/single b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/single new file mode 100644 index 0000000000000000000000000000000000000000..da9beca38c096cabca92bbabbcac6d333f3ffa90 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/deb/test-fixtures/status/single @@ -0,0 +1,35 @@ +Package: apt +Status: install ok installed +Priority: required +Section: admin +Installed-Size: 4064 +Maintainer: APT Development Team +Architecture: amd64 +Version: 1.8.2 +Source: apt-dev +Replaces: apt-transport-https (<< 1.5~alpha4~), apt-utils (<< 1.3~exp2~) +Provides: apt-transport-https (= 1.8.2) +Depends: adduser, gpgv | gpgv2 | gpgv1, debian-archive-keyring, libapt-pkg5.0 (>= 1.7.0~alpha3~), libc6 (>= 2.15), libgcc1 (>= 1:3.0), libgnutls30 (>= 3.6.6), libseccomp2 (>= 1.0.1), libstdc++6 (>= 5.2) +Recommends: ca-certificates +Suggests: apt-doc, aptitude | synaptic | wajig, dpkg-dev (>= 1.17.2), gnupg | gnupg2 | gnupg1, powermgmt-base +Breaks: apt-transport-https (<< 1.5~alpha4~), apt-utils (<< 1.3~exp2~), aptitude (<< 0.8.10) +Conffiles: + /etc/apt/apt.conf.d/01autoremove 76120d358bc9037bb6358e737b3050b5 + /etc/cron.daily/apt-compat 49e9b2cfa17849700d4db735d04244f3 + /etc/kernel/postinst.d/apt-auto-removal 4ad976a68f045517cf4696cec7b8aa3a + /etc/logrotate.d/apt 179f2ed4f85cbaca12fa3d69c2a4a1c3 +Description: commandline package manager + This package provides commandline tools for searching and + managing as well as querying information about packages + as a low-level access to all features of the libapt-pkg library. + . + These include: + * apt-get for retrieval of packages and information about them + from authenticated sources and for installation, upgrade and + removal of packages together with their dependencies + * apt-cache for querying available information about installed + as well as installable packages + * apt-cdrom to use removable media as a source for packages + * apt-config as an interface to the configuration settings + * apt-key as an interface to manage authentication keys + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..e5907e9ec4254668adce42ac99c4a23463fb86ee --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/cataloger.go @@ -0,0 +1,14 @@ +package dotnet + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewDotnetDepsCataloger returns a new Dotnet cataloger object base on deps json files. +func NewDotnetDepsCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/*.deps.json": parseDotnetDeps, + } + + return common.NewGenericCataloger(nil, globParsers, "dotnet-deps-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/parse_dotnet_deps.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/parse_dotnet_deps.go new file mode 100644 index 0000000000000000000000000000000000000000..c6128197592001775b6c1a8883ca92cbcca5ee96 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/parse_dotnet_deps.go @@ -0,0 +1,72 @@ +package dotnet + +import ( + "encoding/json" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseDotnetDeps + +type dotnetDeps struct { + Libraries map[string]dotnetDepsLibrary `json:"libraries"` +} + +type dotnetDepsLibrary struct { + Type string `json:"type"` + Path string `json:"path"` + Sha512 string `json:"sha512"` + HashPath string `json:"hashPath"` +} + +func parseDotnetDeps(path string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + var packages []*pkg.Package + + dec := json.NewDecoder(reader) + + var p dotnetDeps + if err := dec.Decode(&p); err != nil { + return nil, nil, fmt.Errorf("failed to parse deps.json file: %w", err) + } + + for nameVersion, lib := range p.Libraries { + dotnetPkg := newDotnetDepsPackage(nameVersion, lib) + + if dotnetPkg != nil { + packages = append(packages, dotnetPkg) + } + } + + return packages, nil, nil +} + +func newDotnetDepsPackage(nameVersion string, lib dotnetDepsLibrary) *pkg.Package { + if lib.Type != "package" { + return nil + } + + splitted := strings.Split(nameVersion, "/") + name := splitted[0] + version := splitted[1] + + return &pkg.Package{ + Name: name, + Version: version, + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: &pkg.DotnetDepsMetadata{ + Name: name, + Version: version, + Path: lib.Path, + Sha512: lib.Sha512, + HashPath: lib.HashPath, + }, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/parse_dotnet_deps_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/parse_dotnet_deps_test.go new file mode 100644 index 0000000000000000000000000000000000000000..2907c362891b9b96c22b68cfa2f4d261bc98f02e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/parse_dotnet_deps_test.go @@ -0,0 +1,199 @@ +package dotnet + +import ( + "os" + "testing" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/pkg" +) + +func assertPackagesEqual(t *testing.T, actual []*pkg.Package, expected map[string]*pkg.Package) { + assert.Len(t, actual, len(expected)) +} + +func TestParseDotnetDeps(t *testing.T) { + expected := map[string]*pkg.Package{ + "AWSSDK.Core": { + Name: "AWSSDK.Core", + Version: "3.7.10.6", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "AWSSDK.Core", + Version: "3.7.10.6", + Sha512: "sha512-kHBB+QmosVaG6DpngXQ8OlLVVNMzltNITfsRr68Z90qO7dSqJ2EHNd8dtBU1u3AQQLqqFHOY0lfmbpexeH6Pew==", + Path: "awssdk.core/3.7.10.6", + HashPath: "awssdk.core.3.7.10.6.nupkg.sha512", + }, + }, + "Microsoft.Extensions.DependencyInjection": { + Name: "Microsoft.Extensions.DependencyInjection", + Version: "6.0.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Microsoft.Extensions.DependencyInjection", + Version: "6.0.0", + Sha512: "sha512-k6PWQMuoBDGGHOQTtyois2u4AwyVcIwL2LaSLlTZQm2CYcJ1pxbt6jfAnpWmzENA/wfrYRI/X9DTLoUkE4AsLw==", + Path: "microsoft.extensions.dependencyinjection/6.0.0", + HashPath: "microsoft.extensions.dependencyinjection.6.0.0.nupkg.sha512", + }, + }, + "Microsoft.Extensions.DependencyInjection.Abstractions": { + Name: "Microsoft.Extensions.DependencyInjection.Abstractions", + Version: "6.0.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Microsoft.Extensions.DependencyInjection", + Version: "6.0.0", + Sha512: "sha512-xlzi2IYREJH3/m6+lUrQlujzX8wDitm4QGnUu6kUXTQAWPuZY8i+ticFJbzfqaetLA6KR/rO6Ew/HuYD+bxifg==", + Path: "microsoft.extensions.dependencyinjection.abstractions/6.0.0", + HashPath: "microsoft.extensions.dependencyinjection.abstractions.6.0.0.nupkg.sha512", + }, + }, + "Microsoft.Extensions.Logging": { + Name: "Microsoft.Extensions.Logging", + Version: "6.0.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Microsoft.Extensions.Logging", + Version: "6.0.0", + Sha512: "sha512-eIbyj40QDg1NDz0HBW0S5f3wrLVnKWnDJ/JtZ+yJDFnDj90VoPuoPmFkeaXrtu+0cKm5GRAwoDf+dBWXK0TUdg==", + Path: "microsoft.extensions.logging/6.0.0", + HashPath: "microsoft.extensions.logging.6.0.0.nupkg.sha512", + }, + }, + "Microsoft.Extensions.Logging.Abstractions": { + Name: "Microsoft.Extensions.Logging.Abstractions", + Version: "6.0.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Microsoft.Extensions.Logging", + Version: "6.0.0", + Sha512: "sha512-/HggWBbTwy8TgebGSX5DBZ24ndhzi93sHUBDvP1IxbZD7FDokYzdAr6+vbWGjw2XAfR2EJ1sfKUotpjHnFWPxA==", + Path: "microsoft.extensions.logging.abstractions/6.0.0", + HashPath: "microsoft.extensions.logging.abstractions.6.0.0.nupkg.sha512", + }, + }, + "Microsoft.Extensions.Options": { + Name: "Microsoft.Extensions.Options", + Version: "6.0.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Microsoft.Extensions.Options", + Version: "6.0.0", + Sha512: "sha512-dzXN0+V1AyjOe2xcJ86Qbo233KHuLEY0njf/P2Kw8SfJU+d45HNS2ctJdnEnrWbM9Ye2eFgaC5Mj9otRMU6IsQ==", + Path: "microsoft.extensions.options/6.0.0", + HashPath: "microsoft.extensions.options.6.0.0.nupkg.sha512", + }, + }, + "Microsoft.Extensions.Primitives": { + Name: "Microsoft.Extensions.Primitives", + Version: "6.0.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Microsoft.Extensions.Primitives", + Version: "6.0.0", + Sha512: "sha512-9+PnzmQFfEFNR9J2aDTfJGGupShHjOuGw4VUv+JB044biSHrnmCIMD+mJHmb2H7YryrfBEXDurxQ47gJZdCKNQ==", + Path: "microsoft.extensions.primitives/6.0.0", + HashPath: "microsoft.extensions.primitives.6.0.0.nupkg.sha512", + }, + }, + "Newtonsoft.Json": { + Name: "Newtonsoft.Json", + Version: "13.0.1", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Newtonsoft.Json", + Version: "13.0.1", + Sha512: "sha512-ppPFpBcvxdsfUonNcvITKqLl3bqxWbDCZIzDWHzjpdAHRFfZe0Dw9HmA0+za13IdyrgJwpkDTDA9fHaxOrt20A==", + Path: "newtonsoft.json/13.0.1", + HashPath: "newtonsoft.json.13.0.1.nupkg.sha512", + }, + }, + "Serilog": { + Name: "Serilog", + Version: "2.10.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Serilog", + Version: "2.10.0", + Sha512: "sha512-+QX0hmf37a0/OZLxM3wL7V6/ADvC1XihXN4Kq/p6d8lCPfgkRdiuhbWlMaFjR9Av0dy5F0+MBeDmDdRZN/YwQA==", + Path: "serilog/2.10.0", + HashPath: "serilog.2.10.0.nupkg.sha512", + }, + }, + "Serilog.Sinks.Console": { + Name: "Serilog.Sinks.Console", + Version: "4.0.1", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "Serilog.Sinks.Console", + Version: "4.0.1", + Sha512: "sha512-apLOvSJQLlIbKlbx+Y2UDHSP05kJsV7mou+fvJoRGs/iR+jC22r8cuFVMjjfVxz/AD4B2UCltFhE1naRLXwKNw==", + Path: "serilog.sinks.console/4.0.1", + HashPath: "serilog.sinks.console.4.0.1.nupkg.sha512", + }, + }, + "System.Diagnostics.DiagnosticSource": { + Name: "System.Diagnostics.DiagnosticSource", + Version: "6.0.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "System.Diagnostics.DiagnosticSource", + Version: "6.0.0", + Sha512: "sha512-frQDfv0rl209cKm1lnwTgFPzNigy2EKk1BS3uAvHvlBVKe5cymGyHO+Sj+NLv5VF/AhHsqPIUUwya5oV4CHMUw==", + Path: "system.diagnostics.diagnosticsource/6.0.0", + HashPath: "system.diagnostics.diagnosticsource.6.0.0.nupkg.sha512", + }, + }, + "System.Runtime.CompilerServices.Unsafe": { + Name: "System.Runtime.CompilerServices.Unsafe", + Version: "6.0.0", + Language: pkg.Dotnet, + Type: pkg.DotnetPkg, + MetadataType: pkg.DotnetDepsMetadataType, + Metadata: pkg.DotnetDepsMetadata{ + Name: "System.Runtime.CompilerServices.Unsafe", + Version: "6.0.0", + Sha512: "sha512-/iUeP3tq1S0XdNNoMz5C9twLSrM/TH+qElHkXWaPvuNOt+99G75NrV0OS2EqHx5wMN7popYjpc8oTjC1y16DLg==", + Path: "system.runtime.compilerservices.unsafe/6.0.0", + HashPath: "system.runtime.compilerservices.unsafe.6.0.0.nupkg.sha512", + }, + }, + } + + fixture, err := os.Open("test-fixtures/TestLibrary.deps.json") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, _, err := parseDotnetDeps(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse deps.json: %+v", err) + } + + assertPackagesEqual(t, actual, expected) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/test-fixtures/TestLibrary.deps.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/test-fixtures/TestLibrary.deps.json new file mode 100644 index 0000000000000000000000000000000000000000..a429ec4094da8fd4192edf75028340ac0ca98447 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/dotnet/test-fixtures/TestLibrary.deps.json @@ -0,0 +1,235 @@ +{ + "runtimeTarget": { + "name": ".NETCoreApp,Version=v6.0", + "signature": "" + }, + "compilationOptions": {}, + "targets": { + ".NETCoreApp,Version=v6.0": { + "TestLibrary/1.0.0": { + "dependencies": { + "Microsoft.Extensions.DependencyInjection": "6.0.0", + "Microsoft.Extensions.Logging": "6.0.0", + "Newtonsoft.Json": "13.0.1", + "Serilog": "2.10.0", + "Serilog.Sinks.Console": "4.0.1", + "TestCommon": "1.0.0" + }, + "runtime": { + "TestLibrary.dll": {} + } + }, + "AWSSDK.Core/3.7.10.6": { + "runtime": { + "lib/netcoreapp3.1/AWSSDK.Core.dll": { + "assemblyVersion": "3.3.0.0", + "fileVersion": "3.7.10.6" + } + } + }, + "Microsoft.Extensions.DependencyInjection/6.0.0": { + "dependencies": { + "Microsoft.Extensions.DependencyInjection.Abstractions": "6.0.0", + "System.Runtime.CompilerServices.Unsafe": "6.0.0" + }, + "runtime": { + "lib/net6.0/Microsoft.Extensions.DependencyInjection.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.DependencyInjection.Abstractions/6.0.0": { + "runtime": { + "lib/net6.0/Microsoft.Extensions.DependencyInjection.Abstractions.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.Logging/6.0.0": { + "dependencies": { + "Microsoft.Extensions.DependencyInjection": "6.0.0", + "Microsoft.Extensions.DependencyInjection.Abstractions": "6.0.0", + "Microsoft.Extensions.Logging.Abstractions": "6.0.0", + "Microsoft.Extensions.Options": "6.0.0", + "System.Diagnostics.DiagnosticSource": "6.0.0" + }, + "runtime": { + "lib/netstandard2.1/Microsoft.Extensions.Logging.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.Logging.Abstractions/6.0.0": { + "runtime": { + "lib/net6.0/Microsoft.Extensions.Logging.Abstractions.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.Options/6.0.0": { + "dependencies": { + "Microsoft.Extensions.DependencyInjection.Abstractions": "6.0.0", + "Microsoft.Extensions.Primitives": "6.0.0" + }, + "runtime": { + "lib/netstandard2.1/Microsoft.Extensions.Options.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.Primitives/6.0.0": { + "dependencies": { + "System.Runtime.CompilerServices.Unsafe": "6.0.0" + }, + "runtime": { + "lib/net6.0/Microsoft.Extensions.Primitives.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Newtonsoft.Json/13.0.1": { + "runtime": { + "lib/netstandard2.0/Newtonsoft.Json.dll": { + "assemblyVersion": "13.0.0.0", + "fileVersion": "13.0.1.25517" + } + } + }, + "Serilog/2.10.0": { + "runtime": { + "lib/netstandard2.1/Serilog.dll": { + "assemblyVersion": "2.0.0.0", + "fileVersion": "2.10.0.0" + } + } + }, + "Serilog.Sinks.Console/4.0.1": { + "dependencies": { + "Serilog": "2.10.0" + }, + "runtime": { + "lib/net5.0/Serilog.Sinks.Console.dll": { + "assemblyVersion": "4.0.1.0", + "fileVersion": "4.0.1.0" + } + } + }, + "System.Diagnostics.DiagnosticSource/6.0.0": { + "dependencies": { + "System.Runtime.CompilerServices.Unsafe": "6.0.0" + } + }, + "System.Runtime.CompilerServices.Unsafe/6.0.0": {}, + "TestCommon/1.0.0": { + "dependencies": { + "AWSSDK.Core": "3.7.10.6" + }, + "runtime": { + "TestCommon.dll": {} + } + } + } + }, + "libraries": { + "TestLibrary/1.0.0": { + "type": "project", + "serviceable": false, + "sha512": "" + }, + "AWSSDK.Core/3.7.10.6": { + "type": "package", + "serviceable": true, + "sha512": "sha512-kHBB+QmosVaG6DpngXQ8OlLVVNMzltNITfsRr68Z90qO7dSqJ2EHNd8dtBU1u3AQQLqqFHOY0lfmbpexeH6Pew==", + "path": "awssdk.core/3.7.10.6", + "hashPath": "awssdk.core.3.7.10.6.nupkg.sha512" + }, + "Microsoft.Extensions.DependencyInjection/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-k6PWQMuoBDGGHOQTtyois2u4AwyVcIwL2LaSLlTZQm2CYcJ1pxbt6jfAnpWmzENA/wfrYRI/X9DTLoUkE4AsLw==", + "path": "microsoft.extensions.dependencyinjection/6.0.0", + "hashPath": "microsoft.extensions.dependencyinjection.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.DependencyInjection.Abstractions/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-xlzi2IYREJH3/m6+lUrQlujzX8wDitm4QGnUu6kUXTQAWPuZY8i+ticFJbzfqaetLA6KR/rO6Ew/HuYD+bxifg==", + "path": "microsoft.extensions.dependencyinjection.abstractions/6.0.0", + "hashPath": "microsoft.extensions.dependencyinjection.abstractions.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.Logging/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-eIbyj40QDg1NDz0HBW0S5f3wrLVnKWnDJ/JtZ+yJDFnDj90VoPuoPmFkeaXrtu+0cKm5GRAwoDf+dBWXK0TUdg==", + "path": "microsoft.extensions.logging/6.0.0", + "hashPath": "microsoft.extensions.logging.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.Logging.Abstractions/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-/HggWBbTwy8TgebGSX5DBZ24ndhzi93sHUBDvP1IxbZD7FDokYzdAr6+vbWGjw2XAfR2EJ1sfKUotpjHnFWPxA==", + "path": "microsoft.extensions.logging.abstractions/6.0.0", + "hashPath": "microsoft.extensions.logging.abstractions.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.Options/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-dzXN0+V1AyjOe2xcJ86Qbo233KHuLEY0njf/P2Kw8SfJU+d45HNS2ctJdnEnrWbM9Ye2eFgaC5Mj9otRMU6IsQ==", + "path": "microsoft.extensions.options/6.0.0", + "hashPath": "microsoft.extensions.options.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.Primitives/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-9+PnzmQFfEFNR9J2aDTfJGGupShHjOuGw4VUv+JB044biSHrnmCIMD+mJHmb2H7YryrfBEXDurxQ47gJZdCKNQ==", + "path": "microsoft.extensions.primitives/6.0.0", + "hashPath": "microsoft.extensions.primitives.6.0.0.nupkg.sha512" + }, + "Newtonsoft.Json/13.0.1": { + "type": "package", + "serviceable": true, + "sha512": "sha512-ppPFpBcvxdsfUonNcvITKqLl3bqxWbDCZIzDWHzjpdAHRFfZe0Dw9HmA0+za13IdyrgJwpkDTDA9fHaxOrt20A==", + "path": "newtonsoft.json/13.0.1", + "hashPath": "newtonsoft.json.13.0.1.nupkg.sha512" + }, + "Serilog/2.10.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-+QX0hmf37a0/OZLxM3wL7V6/ADvC1XihXN4Kq/p6d8lCPfgkRdiuhbWlMaFjR9Av0dy5F0+MBeDmDdRZN/YwQA==", + "path": "serilog/2.10.0", + "hashPath": "serilog.2.10.0.nupkg.sha512" + }, + "Serilog.Sinks.Console/4.0.1": { + "type": "package", + "serviceable": true, + "sha512": "sha512-apLOvSJQLlIbKlbx+Y2UDHSP05kJsV7mou+fvJoRGs/iR+jC22r8cuFVMjjfVxz/AD4B2UCltFhE1naRLXwKNw==", + "path": "serilog.sinks.console/4.0.1", + "hashPath": "serilog.sinks.console.4.0.1.nupkg.sha512" + }, + "System.Diagnostics.DiagnosticSource/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-frQDfv0rl209cKm1lnwTgFPzNigy2EKk1BS3uAvHvlBVKe5cymGyHO+Sj+NLv5VF/AhHsqPIUUwya5oV4CHMUw==", + "path": "system.diagnostics.diagnosticsource/6.0.0", + "hashPath": "system.diagnostics.diagnosticsource.6.0.0.nupkg.sha512" + }, + "System.Runtime.CompilerServices.Unsafe/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-/iUeP3tq1S0XdNNoMz5C9twLSrM/TH+qElHkXWaPvuNOt+99G75NrV0OS2EqHx5wMN7popYjpc8oTjC1y16DLg==", + "path": "system.runtime.compilerservices.unsafe/6.0.0", + "hashPath": "system.runtime.compilerservices.unsafe.6.0.0.nupkg.sha512" + }, + "TestCommon/1.0.0": { + "type": "project", + "serviceable": false, + "sha512": "" + } + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/binary_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/binary_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..494c7da86c232a970cbef1a5bdd440d743347ef4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/binary_cataloger.go @@ -0,0 +1,61 @@ +/* +Package golang provides a concrete Cataloger implementation for go.mod files. +*/ +package golang + +import ( + "fmt" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/internal/unionreader" + "github.com/anchore/syft/syft/source" +) + +const catalogerName = "go-module-binary-cataloger" + +type Cataloger struct{} + +// NewGoModuleBinaryCataloger returns a new Golang cataloger object. +func NewGoModuleBinaryCataloger() *Cataloger { + return &Cataloger{} +} + +// Name returns a string that uniquely describes a cataloger +func (c *Cataloger) Name() string { + return catalogerName +} + +// Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing rpm db installation. +func (c *Cataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + var pkgs []pkg.Package + + fileMatches, err := resolver.FilesByMIMEType(internal.ExecutableMIMETypeSet.List()...) + if err != nil { + return pkgs, nil, fmt.Errorf("failed to find bin by mime types: %w", err) + } + + for _, location := range fileMatches { + readerCloser, err := resolver.FileContentsByLocation(location) + if err != nil { + log.Warnf("golang cataloger: opening file: %v", err) + continue + } + + reader, err := unionreader.GetUnionReader(readerCloser) + if err != nil { + return nil, nil, err + } + + mods, archs := scanFile(reader, location.RealPath) + internal.CloseAndLogError(readerCloser, location.RealPath) + + for i, mod := range mods { + pkgs = append(pkgs, buildGoPkgInfo(location, mod, archs[i])...) + } + } + + return pkgs, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/README.md b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/README.md new file mode 100644 index 0000000000000000000000000000000000000000..58cdf17cec2816c820e101b55fc2b9e3a2ac6c1f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/README.md @@ -0,0 +1,4 @@ +xcoff +----- + +The code in this package comes from: https://github.com/golang/go/tree/master/src/internal/xcoff -- it was copied over to add support for [xcoff](https://en.wikipedia.org/wiki/XCOFF) binaries. Golang keeps this package as internal, forbidding its external use. diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/file.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/file.go new file mode 100644 index 0000000000000000000000000000000000000000..76a39a34f741b7cb5d8dd059ec555d0da1913854 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/file.go @@ -0,0 +1,688 @@ +// Copyright 2018 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +// Package xcoff implements access to XCOFF (Extended Common Object File Format) files. + +//nolint //this is an internal golang lib +package xcoff + +import ( + "encoding/binary" + "fmt" + "io" + "os" + "strings" +) + +// SectionHeader holds information about an XCOFF section header. +type SectionHeader struct { + Name string + VirtualAddress uint64 + Size uint64 + Type uint32 + Relptr uint64 + Nreloc uint32 +} + +type Section struct { + SectionHeader + Relocs []Reloc + io.ReaderAt + sr *io.SectionReader +} + +// AuxiliaryCSect holds information about an XCOFF symbol in an AUX_CSECT entry. +type AuxiliaryCSect struct { + Length int64 + StorageMappingClass int + SymbolType int +} + +// AuxiliaryFcn holds information about an XCOFF symbol in an AUX_FCN entry. +type AuxiliaryFcn struct { + Size int64 +} + +type Symbol struct { + Name string + Value uint64 + SectionNumber int + StorageClass int + AuxFcn AuxiliaryFcn + AuxCSect AuxiliaryCSect +} + +type Reloc struct { + VirtualAddress uint64 + Symbol *Symbol + Signed bool + InstructionFixed bool + Length uint8 + Type uint8 +} + +// ImportedSymbol holds information about an imported XCOFF symbol. +type ImportedSymbol struct { + Name string + Library string +} + +// FileHeader holds information about an XCOFF file header. +type FileHeader struct { + TargetMachine uint16 +} + +// A File represents an open XCOFF file. +type File struct { + FileHeader + Sections []*Section + Symbols []*Symbol + StringTable []byte + LibraryPaths []string + + closer io.Closer +} + +// Open opens the named file using os.Open and prepares it for use as an XCOFF binary. +func Open(name string) (*File, error) { + f, err := os.Open(name) + if err != nil { + return nil, err + } + ff, err := NewFile(f) + if err != nil { + f.Close() + return nil, err + } + ff.closer = f + return ff, nil +} + +// Close closes the File. +// If the File was created using NewFile directly instead of Open, +// Close has no effect. +func (f *File) Close() error { + var err error + if f.closer != nil { + err = f.closer.Close() + f.closer = nil + } + return err +} + +// Section returns the first section with the given name, or nil if no such +// section exists. +// Xcoff have section's name limited to 8 bytes. Some sections like .gosymtab +// can be trunked but this method will still find them. +func (f *File) Section(name string) *Section { + for _, s := range f.Sections { + if s.Name == name || (len(name) > 8 && s.Name == name[:8]) { + return s + } + } + return nil +} + +// SectionByType returns the first section in f with the +// given type, or nil if there is no such section. +func (f *File) SectionByType(typ uint32) *Section { + for _, s := range f.Sections { + if s.Type == typ { + return s + } + } + return nil +} + +// cstring converts ASCII byte sequence b to string. +// It stops once it finds 0 or reaches end of b. +func cstring(b []byte) string { + var i int + for i = 0; i < len(b) && b[i] != 0; i++ { + } + return string(b[:i]) +} + +// getString extracts a string from an XCOFF string table. +func getString(st []byte, offset uint32) (string, bool) { + if offset < 4 || int(offset) >= len(st) { + return "", false + } + return cstring(st[offset:]), true +} + +// NewFile creates a new File for accessing an XCOFF binary in an underlying reader. +func NewFile(r io.ReaderAt) (*File, error) { + sr := io.NewSectionReader(r, 0, 1<<63-1) + // Read XCOFF target machine + var magic uint16 + if err := binary.Read(sr, binary.BigEndian, &magic); err != nil { + return nil, err + } + if magic != U802TOCMAGIC && magic != U64_TOCMAGIC { + return nil, fmt.Errorf("unrecognised XCOFF magic: 0x%x", magic) + } + + f := new(File) + f.TargetMachine = magic + + // Read XCOFF file header + if _, err := sr.Seek(0, os.SEEK_SET); err != nil { + return nil, err + } + var nscns uint16 + var symptr uint64 + var nsyms int32 + var opthdr uint16 + var hdrsz int + switch f.TargetMachine { + case U802TOCMAGIC: + fhdr := new(FileHeader32) + if err := binary.Read(sr, binary.BigEndian, fhdr); err != nil { + return nil, err + } + nscns = fhdr.Fnscns + symptr = uint64(fhdr.Fsymptr) + nsyms = fhdr.Fnsyms + opthdr = fhdr.Fopthdr + hdrsz = FILHSZ_32 + case U64_TOCMAGIC: + fhdr := new(FileHeader64) + if err := binary.Read(sr, binary.BigEndian, fhdr); err != nil { + return nil, err + } + nscns = fhdr.Fnscns + symptr = fhdr.Fsymptr + nsyms = fhdr.Fnsyms + opthdr = fhdr.Fopthdr + hdrsz = FILHSZ_64 + } + + if symptr == 0 || nsyms <= 0 { + return nil, fmt.Errorf("no symbol table") + } + + // Read string table (located right after symbol table). + offset := symptr + uint64(nsyms)*SYMESZ + if _, err := sr.Seek(int64(offset), os.SEEK_SET); err != nil { + return nil, err + } + // The first 4 bytes contain the length (in bytes). + var l uint32 + if err := binary.Read(sr, binary.BigEndian, &l); err != nil { + return nil, err + } + if l > 4 { + if _, err := sr.Seek(int64(offset), os.SEEK_SET); err != nil { + return nil, err + } + f.StringTable = make([]byte, l) + if _, err := io.ReadFull(sr, f.StringTable); err != nil { + return nil, err + } + } + + // Read section headers + if _, err := sr.Seek(int64(hdrsz)+int64(opthdr), os.SEEK_SET); err != nil { + return nil, err + } + f.Sections = make([]*Section, nscns) + for i := 0; i < int(nscns); i++ { + var scnptr uint64 + s := new(Section) + switch f.TargetMachine { + case U802TOCMAGIC: + shdr := new(SectionHeader32) + if err := binary.Read(sr, binary.BigEndian, shdr); err != nil { + return nil, err + } + s.Name = cstring(shdr.Sname[:]) + s.VirtualAddress = uint64(shdr.Svaddr) + s.Size = uint64(shdr.Ssize) + scnptr = uint64(shdr.Sscnptr) + s.Type = shdr.Sflags + s.Relptr = uint64(shdr.Srelptr) + s.Nreloc = uint32(shdr.Snreloc) + case U64_TOCMAGIC: + shdr := new(SectionHeader64) + if err := binary.Read(sr, binary.BigEndian, shdr); err != nil { + return nil, err + } + s.Name = cstring(shdr.Sname[:]) + s.VirtualAddress = shdr.Svaddr + s.Size = shdr.Ssize + scnptr = shdr.Sscnptr + s.Type = shdr.Sflags + s.Relptr = shdr.Srelptr + s.Nreloc = shdr.Snreloc + } + r2 := r + if scnptr == 0 { // .bss must have all 0s + r2 = zeroReaderAt{} + } + s.sr = io.NewSectionReader(r2, int64(scnptr), int64(s.Size)) + s.ReaderAt = s.sr + f.Sections[i] = s + } + + // Symbol map needed by relocation + var idxToSym = make(map[int]*Symbol) + + // Read symbol table + if _, err := sr.Seek(int64(symptr), os.SEEK_SET); err != nil { + return nil, err + } + f.Symbols = make([]*Symbol, 0) + for i := 0; i < int(nsyms); i++ { + var numaux int + var ok, needAuxFcn bool + sym := new(Symbol) + switch f.TargetMachine { + case U802TOCMAGIC: + se := new(SymEnt32) + if err := binary.Read(sr, binary.BigEndian, se); err != nil { + return nil, err + } + numaux = int(se.Nnumaux) + sym.SectionNumber = int(se.Nscnum) + sym.StorageClass = int(se.Nsclass) + sym.Value = uint64(se.Nvalue) + needAuxFcn = se.Ntype&SYM_TYPE_FUNC != 0 && numaux > 1 + zeroes := binary.BigEndian.Uint32(se.Nname[:4]) + if zeroes != 0 { + sym.Name = cstring(se.Nname[:]) + } else { + offset := binary.BigEndian.Uint32(se.Nname[4:]) + sym.Name, ok = getString(f.StringTable, offset) + if !ok { + goto skip + } + } + case U64_TOCMAGIC: + se := new(SymEnt64) + if err := binary.Read(sr, binary.BigEndian, se); err != nil { + return nil, err + } + numaux = int(se.Nnumaux) + sym.SectionNumber = int(se.Nscnum) + sym.StorageClass = int(se.Nsclass) + sym.Value = se.Nvalue + needAuxFcn = se.Ntype&SYM_TYPE_FUNC != 0 && numaux > 1 + sym.Name, ok = getString(f.StringTable, se.Noffset) + if !ok { + goto skip + } + } + if sym.StorageClass != C_EXT && sym.StorageClass != C_WEAKEXT && sym.StorageClass != C_HIDEXT { + goto skip + } + // Must have at least one csect auxiliary entry. + if numaux < 1 || i+numaux >= int(nsyms) { + goto skip + } + + if sym.SectionNumber > int(nscns) { + goto skip + } + if sym.SectionNumber == 0 { + sym.Value = 0 + } else { + sym.Value -= f.Sections[sym.SectionNumber-1].VirtualAddress + } + + idxToSym[i] = sym + + // If this symbol is a function, it must retrieve its size from + // its AUX_FCN entry. + // It can happen that a function symbol doesn't have any AUX_FCN. + // In this case, needAuxFcn is false and their size will be set to 0. + if needAuxFcn { + switch f.TargetMachine { + case U802TOCMAGIC: + aux := new(AuxFcn32) + if err := binary.Read(sr, binary.BigEndian, aux); err != nil { + return nil, err + } + sym.AuxFcn.Size = int64(aux.Xfsize) + case U64_TOCMAGIC: + aux := new(AuxFcn64) + if err := binary.Read(sr, binary.BigEndian, aux); err != nil { + return nil, err + } + sym.AuxFcn.Size = int64(aux.Xfsize) + } + } + + // Read csect auxiliary entry (by convention, it is the last). + if !needAuxFcn { + if _, err := sr.Seek(int64(numaux-1)*SYMESZ, os.SEEK_CUR); err != nil { + return nil, err + } + } + i += numaux + numaux = 0 + switch f.TargetMachine { + case U802TOCMAGIC: + aux := new(AuxCSect32) + if err := binary.Read(sr, binary.BigEndian, aux); err != nil { + return nil, err + } + sym.AuxCSect.SymbolType = int(aux.Xsmtyp & 0x7) + sym.AuxCSect.StorageMappingClass = int(aux.Xsmclas) + sym.AuxCSect.Length = int64(aux.Xscnlen) + case U64_TOCMAGIC: + aux := new(AuxCSect64) + if err := binary.Read(sr, binary.BigEndian, aux); err != nil { + return nil, err + } + sym.AuxCSect.SymbolType = int(aux.Xsmtyp & 0x7) + sym.AuxCSect.StorageMappingClass = int(aux.Xsmclas) + sym.AuxCSect.Length = int64(aux.Xscnlenhi)<<32 | int64(aux.Xscnlenlo) + } + f.Symbols = append(f.Symbols, sym) + skip: + i += numaux // Skip auxiliary entries + if _, err := sr.Seek(int64(numaux)*SYMESZ, os.SEEK_CUR); err != nil { + return nil, err + } + } + + // Read relocations + // Only for .data or .text section + for _, sect := range f.Sections { + if sect.Type != STYP_TEXT && sect.Type != STYP_DATA { + continue + } + sect.Relocs = make([]Reloc, sect.Nreloc) + if sect.Relptr == 0 { + continue + } + if _, err := sr.Seek(int64(sect.Relptr), os.SEEK_SET); err != nil { + return nil, err + } + for i := uint32(0); i < sect.Nreloc; i++ { + switch f.TargetMachine { + case U802TOCMAGIC: + rel := new(Reloc32) + if err := binary.Read(sr, binary.BigEndian, rel); err != nil { + return nil, err + } + sect.Relocs[i].VirtualAddress = uint64(rel.Rvaddr) + sect.Relocs[i].Symbol = idxToSym[int(rel.Rsymndx)] + sect.Relocs[i].Type = rel.Rtype + sect.Relocs[i].Length = rel.Rsize&0x3F + 1 + + if rel.Rsize&0x80 != 0 { + sect.Relocs[i].Signed = true + } + if rel.Rsize&0x40 != 0 { + sect.Relocs[i].InstructionFixed = true + } + + case U64_TOCMAGIC: + rel := new(Reloc64) + if err := binary.Read(sr, binary.BigEndian, rel); err != nil { + return nil, err + } + sect.Relocs[i].VirtualAddress = rel.Rvaddr + sect.Relocs[i].Symbol = idxToSym[int(rel.Rsymndx)] + sect.Relocs[i].Type = rel.Rtype + sect.Relocs[i].Length = rel.Rsize&0x3F + 1 + if rel.Rsize&0x80 != 0 { + sect.Relocs[i].Signed = true + } + if rel.Rsize&0x40 != 0 { + sect.Relocs[i].InstructionFixed = true + } + } + } + } + + return f, nil +} + +// zeroReaderAt is ReaderAt that reads 0s. +type zeroReaderAt struct{} + +// ReadAt writes len(p) 0s into p. +func (w zeroReaderAt) ReadAt(p []byte, off int64) (n int, err error) { + for i := range p { + p[i] = 0 + } + return len(p), nil +} + +// Data reads and returns the contents of the XCOFF section s. +func (s *Section) Data() ([]byte, error) { + dat := make([]byte, s.sr.Size()) + n, err := s.sr.ReadAt(dat, 0) + if n == len(dat) { + err = nil + } + return dat[:n], err +} + +// CSect reads and returns the contents of a csect. +// func (f *File) CSect(name string) []byte { +// for _, sym := range f.Symbols { +// if sym.Name == name && sym.AuxCSect.SymbolType == XTY_SD { +// if i := sym.SectionNumber - 1; 0 <= i && i < len(f.Sections) { +// s := f.Sections[i] +// if sym.Value+uint64(sym.AuxCSect.Length) <= s.Size { +// dat := make([]byte, sym.AuxCSect.Length) +// _, err := s.sr.ReadAt(dat, int64(sym.Value)) +// if err != nil { +// return nil +// } +// return dat +// } +// } +// break +// } +// } +// return nil +// } + +// func (f *File) DWARF() (*dwarf.Data, error) { +// // There are many other DWARF sections, but these +// // are the ones the debug/dwarf package uses. +// // Don't bother loading others. +// var subtypes = [...]uint32{SSUBTYP_DWABREV, SSUBTYP_DWINFO, SSUBTYP_DWLINE, SSUBTYP_DWRNGES, SSUBTYP_DWSTR} +// var dat [len(subtypes)][]byte +// for i, subtype := range subtypes { +// s := f.SectionByType(STYP_DWARF | subtype) +// if s != nil { +// b, err := s.Data() +// if err != nil && uint64(len(b)) < s.Size { +// return nil, err +// } +// dat[i] = b +// } +// } + +// abbrev, info, line, ranges, str := dat[0], dat[1], dat[2], dat[3], dat[4] +// return dwarf.New(abbrev, nil, nil, info, line, nil, ranges, str) +// } + +// readImportID returns the import file IDs stored inside the .loader section. +// Library name pattern is either path/base/member or base/member +func (f *File) readImportIDs(s *Section) ([]string, error) { + // Read loader header + if _, err := s.sr.Seek(0, os.SEEK_SET); err != nil { + return nil, err + } + var istlen uint32 + var nimpid int32 + var impoff uint64 + switch f.TargetMachine { + case U802TOCMAGIC: + lhdr := new(LoaderHeader32) + if err := binary.Read(s.sr, binary.BigEndian, lhdr); err != nil { + return nil, err + } + istlen = lhdr.Listlen + nimpid = lhdr.Lnimpid + impoff = uint64(lhdr.Limpoff) + case U64_TOCMAGIC: + lhdr := new(LoaderHeader64) + if err := binary.Read(s.sr, binary.BigEndian, lhdr); err != nil { + return nil, err + } + istlen = lhdr.Listlen + nimpid = lhdr.Lnimpid + impoff = lhdr.Limpoff + } + + // Read loader import file ID table + if _, err := s.sr.Seek(int64(impoff), os.SEEK_SET); err != nil { + return nil, err + } + table := make([]byte, istlen) + if _, err := io.ReadFull(s.sr, table); err != nil { + return nil, err + } + + offset := 0 + // First import file ID is the default LIBPATH value + libpath := cstring(table[offset:]) + f.LibraryPaths = strings.Split(libpath, ":") + offset += len(libpath) + 3 // 3 null bytes + all := make([]string, 0) + for i := 1; i < int(nimpid); i++ { + impidpath := cstring(table[offset:]) + offset += len(impidpath) + 1 + impidbase := cstring(table[offset:]) + offset += len(impidbase) + 1 + impidmem := cstring(table[offset:]) + offset += len(impidmem) + 1 + var path string + if len(impidpath) > 0 { + path = impidpath + "/" + impidbase + "/" + impidmem + } else { + path = impidbase + "/" + impidmem + } + all = append(all, path) + } + + return all, nil +} + +// ImportedSymbols returns the names of all symbols +// referred to by the binary f that are expected to be +// satisfied by other libraries at dynamic load time. +// It does not return weak symbols. +func (f *File) ImportedSymbols() ([]ImportedSymbol, error) { + s := f.SectionByType(STYP_LOADER) + if s == nil { + return nil, nil + } + // Read loader header + if _, err := s.sr.Seek(0, os.SEEK_SET); err != nil { + return nil, err + } + var stlen uint32 + var stoff uint64 + var nsyms int32 + var symoff uint64 + switch f.TargetMachine { + case U802TOCMAGIC: + lhdr := new(LoaderHeader32) + if err := binary.Read(s.sr, binary.BigEndian, lhdr); err != nil { + return nil, err + } + stlen = lhdr.Lstlen + stoff = uint64(lhdr.Lstoff) + nsyms = lhdr.Lnsyms + symoff = LDHDRSZ_32 + case U64_TOCMAGIC: + lhdr := new(LoaderHeader64) + if err := binary.Read(s.sr, binary.BigEndian, lhdr); err != nil { + return nil, err + } + stlen = lhdr.Lstlen + stoff = lhdr.Lstoff + nsyms = lhdr.Lnsyms + symoff = lhdr.Lsymoff + } + + // Read loader section string table + if _, err := s.sr.Seek(int64(stoff), os.SEEK_SET); err != nil { + return nil, err + } + st := make([]byte, stlen) + if _, err := io.ReadFull(s.sr, st); err != nil { + return nil, err + } + + // Read imported libraries + libs, err := f.readImportIDs(s) + if err != nil { + return nil, err + } + + // Read loader symbol table + if _, err := s.sr.Seek(int64(symoff), os.SEEK_SET); err != nil { + return nil, err + } + all := make([]ImportedSymbol, 0) + for i := 0; i < int(nsyms); i++ { + var name string + var ifile int32 + var ok bool + switch f.TargetMachine { + case U802TOCMAGIC: + ldsym := new(LoaderSymbol32) + if err := binary.Read(s.sr, binary.BigEndian, ldsym); err != nil { + return nil, err + } + if ldsym.Lsmtype&0x40 == 0 { + continue // Imported symbols only + } + zeroes := binary.BigEndian.Uint32(ldsym.Lname[:4]) + if zeroes != 0 { + name = cstring(ldsym.Lname[:]) + } else { + offset := binary.BigEndian.Uint32(ldsym.Lname[4:]) + name, ok = getString(st, offset) + if !ok { + continue + } + } + ifile = ldsym.Lifile + case U64_TOCMAGIC: + ldsym := new(LoaderSymbol64) + if err := binary.Read(s.sr, binary.BigEndian, ldsym); err != nil { + return nil, err + } + if ldsym.Lsmtype&0x40 == 0 { + continue // Imported symbols only + } + name, ok = getString(st, ldsym.Loffset) + if !ok { + continue + } + ifile = ldsym.Lifile + } + var sym ImportedSymbol + sym.Name = name + if ifile >= 1 && int(ifile) <= len(libs) { + sym.Library = libs[ifile-1] + } + all = append(all, sym) + } + + return all, nil +} + +// ImportedLibraries returns the names of all libraries +// referred to by the binary f that are expected to be +// linked with the binary at dynamic link time. +func (f *File) ImportedLibraries() ([]string, error) { + s := f.SectionByType(STYP_LOADER) + if s == nil { + return nil, nil + } + all, err := f.readImportIDs(s) + return all, err +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/file_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/file_test.go new file mode 100644 index 0000000000000000000000000000000000000000..a6722e9453f2ff39fbe97c5d032ade939e3e5765 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/file_test.go @@ -0,0 +1,102 @@ +// Copyright 2018 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package xcoff + +import ( + "reflect" + "testing" +) + +type fileTest struct { + file string + hdr FileHeader + sections []*SectionHeader + needed []string +} + +var fileTests = []fileTest{ + { + "testdata/gcc-ppc32-aix-dwarf2-exec", + FileHeader{U802TOCMAGIC}, + []*SectionHeader{ + {".text", 0x10000290, 0x00000bbd, STYP_TEXT, 0x7ae6, 0x36}, + {".data", 0x20000e4d, 0x00000437, STYP_DATA, 0x7d02, 0x2b}, + {".bss", 0x20001284, 0x0000021c, STYP_BSS, 0, 0}, + {".loader", 0x00000000, 0x000004b3, STYP_LOADER, 0, 0}, + {".dwline", 0x00000000, 0x000000df, STYP_DWARF | SSUBTYP_DWLINE, 0x7eb0, 0x7}, + {".dwinfo", 0x00000000, 0x00000314, STYP_DWARF | SSUBTYP_DWINFO, 0x7ef6, 0xa}, + {".dwabrev", 0x00000000, 0x000000d6, STYP_DWARF | SSUBTYP_DWABREV, 0, 0}, + {".dwarnge", 0x00000000, 0x00000020, STYP_DWARF | SSUBTYP_DWARNGE, 0x7f5a, 0x2}, + {".dwloc", 0x00000000, 0x00000074, STYP_DWARF | SSUBTYP_DWLOC, 0, 0}, + {".debug", 0x00000000, 0x00005e4f, STYP_DEBUG, 0, 0}, + }, + []string{"libc.a/shr.o"}, + }, + { + "testdata/gcc-ppc64-aix-dwarf2-exec", + FileHeader{U64_TOCMAGIC}, + []*SectionHeader{ + {".text", 0x10000480, 0x00000afd, STYP_TEXT, 0x8322, 0x34}, + {".data", 0x20000f7d, 0x000002f3, STYP_DATA, 0x85fa, 0x25}, + {".bss", 0x20001270, 0x00000428, STYP_BSS, 0, 0}, + {".loader", 0x00000000, 0x00000535, STYP_LOADER, 0, 0}, + {".dwline", 0x00000000, 0x000000b4, STYP_DWARF | SSUBTYP_DWLINE, 0x8800, 0x4}, + {".dwinfo", 0x00000000, 0x0000036a, STYP_DWARF | SSUBTYP_DWINFO, 0x8838, 0x7}, + {".dwabrev", 0x00000000, 0x000000b5, STYP_DWARF | SSUBTYP_DWABREV, 0, 0}, + {".dwarnge", 0x00000000, 0x00000040, STYP_DWARF | SSUBTYP_DWARNGE, 0x889a, 0x2}, + {".dwloc", 0x00000000, 0x00000062, STYP_DWARF | SSUBTYP_DWLOC, 0, 0}, + {".debug", 0x00000000, 0x00006605, STYP_DEBUG, 0, 0}, + }, + []string{"libc.a/shr_64.o"}, + }, +} + +func TestOpen(t *testing.T) { + for i := range fileTests { + tt := &fileTests[i] + + f, err := Open(tt.file) + if err != nil { + t.Error(err) + continue + } + if !reflect.DeepEqual(f.FileHeader, tt.hdr) { + t.Errorf("open %s:\n\thave %#v\n\twant %#v\n", tt.file, f.FileHeader, tt.hdr) + continue + } + + for i, sh := range f.Sections { + if i >= len(tt.sections) { + break + } + have := &sh.SectionHeader + want := tt.sections[i] + if !reflect.DeepEqual(have, want) { + t.Errorf("open %s, section %d:\n\thave %#v\n\twant %#v\n", tt.file, i, have, want) + } + } + tn := len(tt.sections) + fn := len(f.Sections) + if tn != fn { + t.Errorf("open %s: len(Sections) = %d, want %d", tt.file, fn, tn) + } + tl := tt.needed + fl, err := f.ImportedLibraries() + if err != nil { + t.Error(err) + } + if !reflect.DeepEqual(tl, fl) { + t.Errorf("open %s: loader import = %v, want %v", tt.file, tl, fl) + } + } +} + +func TestOpenFailure(t *testing.T) { + filename := "file.go" // not an XCOFF object file + _, err := Open(filename) // don't crash + if err == nil { + t.Errorf("open %s: succeeded unexpectedly", filename) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/testdata/gcc-ppc32-aix-dwarf2-exec b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/testdata/gcc-ppc32-aix-dwarf2-exec new file mode 100644 index 0000000000000000000000000000000000000000..810e21a0dfc78b29f2dfc5afe2bc588763177ea6 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/testdata/gcc-ppc32-aix-dwarf2-exec differ diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/testdata/gcc-ppc64-aix-dwarf2-exec b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/testdata/gcc-ppc64-aix-dwarf2-exec new file mode 100644 index 0000000000000000000000000000000000000000..707d01ebd43487081a620250a213dcdba7a80379 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/testdata/gcc-ppc64-aix-dwarf2-exec differ diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/xcoff.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/xcoff.go new file mode 100644 index 0000000000000000000000000000000000000000..96cf01d25b6cfbb0dce54e09dbf3850ba992f75d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/internal/xcoff/xcoff.go @@ -0,0 +1,373 @@ +// The code in this package comes from: +// https://github.com/golang/go/tree/master/src/internal/xcoff +// it was copied over to add support for xcoff binaries. +// Golang keeps this package as internal, forbidding its external use. + +// Copyright 2018 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +//nolint // this is an internal golang lib +package xcoff + +// File Header. +type FileHeader32 struct { + Fmagic uint16 // Target machine + Fnscns uint16 // Number of sections + Ftimedat int32 // Time and date of file creation + Fsymptr uint32 // Byte offset to symbol table start + Fnsyms int32 // Number of entries in symbol table + Fopthdr uint16 // Number of bytes in optional header + Fflags uint16 // Flags +} + +type FileHeader64 struct { + Fmagic uint16 // Target machine + Fnscns uint16 // Number of sections + Ftimedat int32 // Time and date of file creation + Fsymptr uint64 // Byte offset to symbol table start + Fopthdr uint16 // Number of bytes in optional header + Fflags uint16 // Flags + Fnsyms int32 // Number of entries in symbol table +} + +const ( + FILHSZ_32 = 20 + FILHSZ_64 = 24 +) +const ( + U802TOCMAGIC = 0737 // AIX 32-bit XCOFF + U64_TOCMAGIC = 0767 // AIX 64-bit XCOFF +) + +// Flags that describe the type of the object file. +const ( + F_RELFLG = 0x0001 + F_EXEC = 0x0002 + F_LNNO = 0x0004 + F_FDPR_PROF = 0x0010 + F_FDPR_OPTI = 0x0020 + F_DSA = 0x0040 + F_VARPG = 0x0100 + F_DYNLOAD = 0x1000 + F_SHROBJ = 0x2000 + F_LOADONLY = 0x4000 +) + +// Section Header. +type SectionHeader32 struct { + Sname [8]byte // Section name + Spaddr uint32 // Physical address + Svaddr uint32 // Virtual address + Ssize uint32 // Section size + Sscnptr uint32 // Offset in file to raw data for section + Srelptr uint32 // Offset in file to relocation entries for section + Slnnoptr uint32 // Offset in file to line number entries for section + Snreloc uint16 // Number of relocation entries + Snlnno uint16 // Number of line number entries + Sflags uint32 // Flags to define the section type +} + +type SectionHeader64 struct { + Sname [8]byte // Section name + Spaddr uint64 // Physical address + Svaddr uint64 // Virtual address + Ssize uint64 // Section size + Sscnptr uint64 // Offset in file to raw data for section + Srelptr uint64 // Offset in file to relocation entries for section + Slnnoptr uint64 // Offset in file to line number entries for section + Snreloc uint32 // Number of relocation entries + Snlnno uint32 // Number of line number entries + Sflags uint32 // Flags to define the section type + Spad uint32 // Needs to be 72 bytes long +} + +// Flags defining the section type. +const ( + STYP_DWARF = 0x0010 + STYP_TEXT = 0x0020 + STYP_DATA = 0x0040 + STYP_BSS = 0x0080 + STYP_EXCEPT = 0x0100 + STYP_INFO = 0x0200 + STYP_TDATA = 0x0400 + STYP_TBSS = 0x0800 + STYP_LOADER = 0x1000 + STYP_DEBUG = 0x2000 + STYP_TYPCHK = 0x4000 + STYP_OVRFLO = 0x8000 +) +const ( + SSUBTYP_DWINFO = 0x10000 // DWARF info section + SSUBTYP_DWLINE = 0x20000 // DWARF line-number section + SSUBTYP_DWPBNMS = 0x30000 // DWARF public names section + SSUBTYP_DWPBTYP = 0x40000 // DWARF public types section + SSUBTYP_DWARNGE = 0x50000 // DWARF aranges section + SSUBTYP_DWABREV = 0x60000 // DWARF abbreviation section + SSUBTYP_DWSTR = 0x70000 // DWARF strings section + SSUBTYP_DWRNGES = 0x80000 // DWARF ranges section + SSUBTYP_DWLOC = 0x90000 // DWARF location lists section + SSUBTYP_DWFRAME = 0xA0000 // DWARF frames section + SSUBTYP_DWMAC = 0xB0000 // DWARF macros section +) + +// Symbol Table Entry. +type SymEnt32 struct { + Nname [8]byte // Symbol name + Nvalue uint32 // Symbol value + Nscnum int16 // Section number of symbol + Ntype uint16 // Basic and derived type specification + Nsclass int8 // Storage class of symbol + Nnumaux int8 // Number of auxiliary entries +} + +type SymEnt64 struct { + Nvalue uint64 // Symbol value + Noffset uint32 // Offset of the name in string table or .debug section + Nscnum int16 // Section number of symbol + Ntype uint16 // Basic and derived type specification + Nsclass int8 // Storage class of symbol + Nnumaux int8 // Number of auxiliary entries +} + +const SYMESZ = 18 + +const ( + // Nscnum + N_DEBUG = -2 + N_ABS = -1 + N_UNDEF = 0 + + //Ntype + SYM_V_INTERNAL = 0x1000 + SYM_V_HIDDEN = 0x2000 + SYM_V_PROTECTED = 0x3000 + SYM_V_EXPORTED = 0x4000 + SYM_TYPE_FUNC = 0x0020 // is function +) + +// Storage Class. +const ( + C_NULL = 0 // Symbol table entry marked for deletion + C_EXT = 2 // External symbol + C_STAT = 3 // Static symbol + C_BLOCK = 100 // Beginning or end of inner block + C_FCN = 101 // Beginning or end of function + C_FILE = 103 // Source file name and compiler information + C_HIDEXT = 107 // Unnamed external symbol + C_BINCL = 108 // Beginning of include file + C_EINCL = 109 // End of include file + C_WEAKEXT = 111 // Weak external symbol + C_DWARF = 112 // DWARF symbol + C_GSYM = 128 // Global variable + C_LSYM = 129 // Automatic variable allocated on stack + C_PSYM = 130 // Argument to subroutine allocated on stack + C_RSYM = 131 // Register variable + C_RPSYM = 132 // Argument to function or procedure stored in register + C_STSYM = 133 // Statically allocated symbol + C_BCOMM = 135 // Beginning of common block + C_ECOML = 136 // Local member of common block + C_ECOMM = 137 // End of common block + C_DECL = 140 // Declaration of object + C_ENTRY = 141 // Alternate entry + C_FUN = 142 // Function or procedure + C_BSTAT = 143 // Beginning of static block + C_ESTAT = 144 // End of static block + C_GTLS = 145 // Global thread-local variable + C_STTLS = 146 // Static thread-local variable +) + +// File Auxiliary Entry +type AuxFile64 struct { + Xfname [8]byte // Name or offset inside string table + Xftype uint8 // Source file string type + Xauxtype uint8 // Type of auxiliary entry +} + +// Function Auxiliary Entry +type AuxFcn32 struct { + Xexptr uint32 // File offset to exception table entry + Xfsize uint32 // Size of function in bytes + Xlnnoptr uint32 // File pointer to line number + Xendndx uint32 // Symbol table index of next entry + Xpad uint16 // Unused +} +type AuxFcn64 struct { + Xlnnoptr uint64 // File pointer to line number + Xfsize uint32 // Size of function in bytes + Xendndx uint32 // Symbol table index of next entry + Xpad uint8 // Unused + Xauxtype uint8 // Type of auxiliary entry +} + +type AuxSect64 struct { + Xscnlen uint64 // section length + Xnreloc uint64 // Num RLDs + pad uint8 + Xauxtype uint8 // Type of auxiliary entry +} + +// csect Auxiliary Entry. +type AuxCSect32 struct { + Xscnlen int32 // Length or symbol table index + Xparmhash uint32 // Offset of parameter type-check string + Xsnhash uint16 // .typchk section number + Xsmtyp uint8 // Symbol alignment and type + Xsmclas uint8 // Storage-mapping class + Xstab uint32 // Reserved + Xsnstab uint16 // Reserved +} + +type AuxCSect64 struct { + Xscnlenlo uint32 // Lower 4 bytes of length or symbol table index + Xparmhash uint32 // Offset of parameter type-check string + Xsnhash uint16 // .typchk section number + Xsmtyp uint8 // Symbol alignment and type + Xsmclas uint8 // Storage-mapping class + Xscnlenhi int32 // Upper 4 bytes of length or symbol table index + Xpad uint8 // Unused + Xauxtype uint8 // Type of auxiliary entry +} + +// Auxiliary type +// const ( +// _AUX_EXCEPT = 255 +// _AUX_FCN = 254 +// _AUX_SYM = 253 +// _AUX_FILE = 252 +// _AUX_CSECT = 251 +// _AUX_SECT = 250 +// ) + +// Symbol type field. +const ( + XTY_ER = 0 // External reference + XTY_SD = 1 // Section definition + XTY_LD = 2 // Label definition + XTY_CM = 3 // Common csect definition +) + +// Defines for File auxiliary definitions: x_ftype field of x_file +const ( + XFT_FN = 0 // Source File Name + XFT_CT = 1 // Compile Time Stamp + XFT_CV = 2 // Compiler Version Number + XFT_CD = 128 // Compiler Defined Information +) + +// Storage-mapping class. +const ( + XMC_PR = 0 // Program code + XMC_RO = 1 // Read-only constant + XMC_DB = 2 // Debug dictionary table + XMC_TC = 3 // TOC entry + XMC_UA = 4 // Unclassified + XMC_RW = 5 // Read/Write data + XMC_GL = 6 // Global linkage + XMC_XO = 7 // Extended operation + XMC_SV = 8 // 32-bit supervisor call descriptor + XMC_BS = 9 // BSS class + XMC_DS = 10 // Function descriptor + XMC_UC = 11 // Unnamed FORTRAN common + XMC_TC0 = 15 // TOC anchor + XMC_TD = 16 // Scalar data entry in the TOC + XMC_SV64 = 17 // 64-bit supervisor call descriptor + XMC_SV3264 = 18 // Supervisor call descriptor for both 32-bit and 64-bit + XMC_TL = 20 // Read/Write thread-local data + XMC_UL = 21 // Read/Write thread-local data (.tbss) + XMC_TE = 22 // TOC entry +) + +// Loader Header. +type LoaderHeader32 struct { + Lversion int32 // Loader section version number + Lnsyms int32 // Number of symbol table entries + Lnreloc int32 // Number of relocation table entries + Listlen uint32 // Length of import file ID string table + Lnimpid int32 // Number of import file IDs + Limpoff uint32 // Offset to start of import file IDs + Lstlen uint32 // Length of string table + Lstoff uint32 // Offset to start of string table +} + +type LoaderHeader64 struct { + Lversion int32 // Loader section version number + Lnsyms int32 // Number of symbol table entries + Lnreloc int32 // Number of relocation table entries + Listlen uint32 // Length of import file ID string table + Lnimpid int32 // Number of import file IDs + Lstlen uint32 // Length of string table + Limpoff uint64 // Offset to start of import file IDs + Lstoff uint64 // Offset to start of string table + Lsymoff uint64 // Offset to start of symbol table + Lrldoff uint64 // Offset to start of relocation entries +} + +const ( + LDHDRSZ_32 = 32 + LDHDRSZ_64 = 56 +) + +// Loader Symbol. +type LoaderSymbol32 struct { + Lname [8]byte // Symbol name or byte offset into string table + Lvalue uint32 // Address field + Lscnum int16 // Section number containing symbol + Lsmtype int8 // Symbol type, export, import flags + Lsmclas int8 // Symbol storage class + Lifile int32 // Import file ID; ordinal of import file IDs + Lparm uint32 // Parameter type-check field +} + +type LoaderSymbol64 struct { + Lvalue uint64 // Address field + Loffset uint32 // Byte offset into string table of symbol name + Lscnum int16 // Section number containing symbol + Lsmtype int8 // Symbol type, export, import flags + Lsmclas int8 // Symbol storage class + Lifile int32 // Import file ID; ordinal of import file IDs + Lparm uint32 // Parameter type-check field +} + +type Reloc32 struct { + Rvaddr uint32 // (virtual) address of reference + Rsymndx uint32 // Index into symbol table + Rsize uint8 // Sign and reloc bit len + Rtype uint8 // Toc relocation type +} + +type Reloc64 struct { + Rvaddr uint64 // (virtual) address of reference + Rsymndx uint32 // Index into symbol table + Rsize uint8 // Sign and reloc bit len + Rtype uint8 // Toc relocation type +} + +const ( + R_POS = 0x00 // A(sym) Positive Relocation + R_NEG = 0x01 // -A(sym) Negative Relocation + R_REL = 0x02 // A(sym-*) Relative to self + R_TOC = 0x03 // A(sym-TOC) Relative to TOC + R_TRL = 0x12 // A(sym-TOC) TOC Relative indirect load. + + R_TRLA = 0x13 // A(sym-TOC) TOC Rel load address. modifiable inst + R_GL = 0x05 // A(external TOC of sym) Global Linkage + R_TCL = 0x06 // A(local TOC of sym) Local object TOC address + R_RL = 0x0C // A(sym) Pos indirect load. modifiable instruction + R_RLA = 0x0D // A(sym) Pos Load Address. modifiable instruction + R_REF = 0x0F // AL0(sym) Non relocating ref. No garbage collect + R_BA = 0x08 // A(sym) Branch absolute. Cannot modify instruction + R_RBA = 0x18 // A(sym) Branch absolute. modifiable instruction + R_BR = 0x0A // A(sym-*) Branch rel to self. non modifiable + R_RBR = 0x1A // A(sym-*) Branch rel to self. modifiable instr + + R_TLS = 0x20 // General-dynamic reference to TLS symbol + R_TLS_IE = 0x21 // Initial-exec reference to TLS symbol + R_TLS_LD = 0x22 // Local-dynamic reference to TLS symbol + R_TLS_LE = 0x23 // Local-exec reference to TLS symbol + R_TLSM = 0x24 // Module reference to TLS symbol + R_TLSML = 0x25 // Module reference to local (own) module + + R_TOCU = 0x30 // Relative to TOC - high order bits + R_TOCL = 0x31 // Relative to TOC - low order bits +) diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/mod_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/mod_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..50ce25923715e1db0b0f2724d98975af2f4dcfcb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/mod_cataloger.go @@ -0,0 +1,17 @@ +/* +Package golang provides a concrete Cataloger implementation for go.mod files. +*/ +package golang + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewGoModFileCataloger returns a new Go module cataloger object. +func NewGoModFileCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/go.mod": parseGoMod, + } + + return common.NewGenericCataloger(nil, globParsers, "go-mod-file-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_bin.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_bin.go new file mode 100644 index 0000000000000000000000000000000000000000..5dd726783a6794d54bd30a393b77ee43f9cbbe60 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_bin.go @@ -0,0 +1,211 @@ +package golang + +import ( + "bytes" + "debug/elf" + "debug/macho" + "debug/pe" + "errors" + "fmt" + "io" + "runtime/debug" + "strings" + "time" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/golang/internal/xcoff" + "github.com/anchore/syft/syft/source" + "golang.org/x/mod/module" +) + +const GOARCH = "GOARCH" + +var ( + // errUnrecognizedFormat is returned when a given executable file doesn't + // appear to be in a known format, or it breaks the rules of that format, + // or when there are I/O errors reading the file. + errUnrecognizedFormat = errors.New("unrecognized file format") + // devel is used to recognize the current default version when a golang main distribution is built + // https://github.com/golang/go/issues/29228 this issue has more details on the progress of being able to + // inject the correct version into the main module of the build process +) + +const devel = "(devel)" + +func makeGoMainPackage(mod *debug.BuildInfo, arch string, location source.Location) pkg.Package { + gbs := getBuildSettings(mod.Settings) + main := newGoBinaryPackage(&mod.Main, mod.Main.Path, mod.GoVersion, arch, location, gbs) + if main.Version == devel { + if version, ok := gbs["vcs.revision"]; ok { + if timestamp, ok := gbs["vcs.time"]; ok { + //NOTE: err is ignored, because if parsing fails + // we still use the empty Time{} struct to generate an empty date, like 00010101000000 + // for consistency with the pseudo-version format: https://go.dev/ref/mod#pseudo-versions + ts, _ := time.Parse(time.RFC3339, timestamp) + if len(version) >= 12 { + version = version[:12] + } + version = module.PseudoVersion("", "", ts, version) + } + main.Version = version + } + } + + return main +} + +func newGoBinaryPackage(dep *debug.Module, mainModule, goVersion, architecture string, location source.Location, buildSettings map[string]string) pkg.Package { + if dep.Replace != nil { + dep = dep.Replace + } + + p := pkg.Package{ + FoundBy: catalogerName, + Name: dep.Path, + Version: dep.Version, + Language: pkg.Go, + Type: pkg.GoModulePkg, + Locations: source.NewLocationSet(location), + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{ + GoCompiledVersion: goVersion, + H1Digest: dep.Sum, + Architecture: architecture, + BuildSettings: buildSettings, + MainModule: mainModule, + }, + } + + p.SetID() + + return p +} + +// getArchs finds a binary architecture by two ways: +// 1) reading build info from binaries compiled by go1.18+ +// 2) reading file headers from binaries compiled by < go1.18 +func getArchs(readers []io.ReaderAt, builds []*debug.BuildInfo) []string { + if len(readers) != len(builds) { + log.Warnf("golang cataloger: bin parsing: number of builds and readers doesn't match") + return nil + } + + if len(readers) == 0 || len(builds) == 0 { + log.Warnf("golang cataloger: bin parsing: %d readers and %d build info items", len(readers), len(builds)) + return nil + } + + archs := make([]string, len(builds)) + for i, build := range builds { + archs[i] = getGOARCH(build.Settings) + } + + // if architecture was found via build settings return + if archs[0] != "" { + return archs + } + + for i, r := range readers { + a, err := getGOARCHFromBin(r) + if err != nil { + log.Warnf("golang cataloger: bin parsing: getting arch from binary: %v", err) + continue + } + + archs[i] = a + } + return archs +} + +func getGOARCH(settings []debug.BuildSetting) string { + for _, s := range settings { + if s.Key == GOARCH { + return s.Value + } + } + + return "" +} + +func getGOARCHFromBin(r io.ReaderAt) (string, error) { + // Read the first bytes of the file to identify the format, then delegate to + // a format-specific function to load segment and section headers. + ident := make([]byte, 16) + if n, err := r.ReadAt(ident, 0); n < len(ident) || err != nil { + return "", fmt.Errorf("unrecognized file format: %w", err) + } + + var arch string + switch { + case bytes.HasPrefix(ident, []byte("\x7FELF")): + f, err := elf.NewFile(r) + if err != nil { + return "", fmt.Errorf("unrecognized file format: %w", err) + } + arch = f.Machine.String() + case bytes.HasPrefix(ident, []byte("MZ")): + f, err := pe.NewFile(r) + if err != nil { + return "", fmt.Errorf("unrecognized file format: %w", err) + } + arch = fmt.Sprintf("%d", f.Machine) + case bytes.HasPrefix(ident, []byte("\xFE\xED\xFA")) || bytes.HasPrefix(ident[1:], []byte("\xFA\xED\xFE")): + f, err := macho.NewFile(r) + if err != nil { + return "", fmt.Errorf("unrecognized file format: %w", err) + } + arch = f.Cpu.String() + case bytes.HasPrefix(ident, []byte{0x01, 0xDF}) || bytes.HasPrefix(ident, []byte{0x01, 0xF7}): + f, err := xcoff.NewFile(r) + if err != nil { + return "", fmt.Errorf("unrecognized file format: %w", err) + } + arch = fmt.Sprintf("%d", f.FileHeader.TargetMachine) + default: + return "", errUnrecognizedFormat + } + + arch = strings.Replace(arch, "EM_", "", 1) + arch = strings.Replace(arch, "Cpu", "", 1) + arch = strings.ToLower(arch) + + return arch, nil +} + +func getBuildSettings(settings []debug.BuildSetting) map[string]string { + m := make(map[string]string) + for _, s := range settings { + m[s.Key] = s.Value + } + return m +} + +func buildGoPkgInfo(location source.Location, mod *debug.BuildInfo, arch string) []pkg.Package { + var pkgs []pkg.Package + if mod == nil { + return pkgs + } + + for _, dep := range mod.Deps { + if dep == nil { + continue + } + p := newGoBinaryPackage(dep, mod.Main.Path, mod.GoVersion, arch, location, nil) + if pkg.IsValid(&p) { + pkgs = append(pkgs, p) + } + } + + // NOTE(jonasagx): this use happened originally while creating unit tests. It might never + // happen in the wild, but I kept it as a safeguard against empty modules. + var empty debug.Module + if mod.Main == empty { + return pkgs + } + + main := makeGoMainPackage(mod, arch, location) + pkgs = append(pkgs, main) + + return pkgs +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_bin_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_bin_test.go new file mode 100644 index 0000000000000000000000000000000000000000..2c2a383aea95b81450e56beab6ff0a7068cb84a9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_bin_test.go @@ -0,0 +1,424 @@ +package golang + +import ( + "bufio" + "io" + "os" + "os/exec" + "path/filepath" + "runtime/debug" + "strconv" + "syscall" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +// make will run the default make target for the given test fixture path +func runMakeTarget(t *testing.T, fixtureName string) { + cwd, err := os.Getwd() + require.NoError(t, err) + fixtureDir := filepath.Join(cwd, "test-fixtures/", fixtureName) + + t.Logf("Generating Fixture in %q", fixtureDir) + + cmd := exec.Command("make") + cmd.Dir = fixtureDir + + stderr, err := cmd.StderrPipe() + require.NoError(t, err) + + stdout, err := cmd.StdoutPipe() + require.NoError(t, err) + + err = cmd.Start() + require.NoError(t, err) + + show := func(label string, reader io.ReadCloser) { + scanner := bufio.NewScanner(reader) + scanner.Split(bufio.ScanLines) + for scanner.Scan() { + t.Logf("%s: %s", label, scanner.Text()) + } + } + go show("out", stdout) + go show("err", stderr) + + if err := cmd.Wait(); err != nil { + if exiterr, ok := err.(*exec.ExitError); ok { + // The program has exited with an exit code != 0 + + // This works on both Unix and Windows. Although package + // syscall is generally platform dependent, WaitStatus is + // defined for both Unix and Windows and in both cases has + // an ExitStatus() method with the same signature. + if status, ok := exiterr.Sys().(syscall.WaitStatus); ok { + if status.ExitStatus() != 0 { + t.Fatalf("failed to generate fixture: rc=%d", status.ExitStatus()) + } + } + } else { + t.Fatalf("unable to get generate fixture result: %+v", err) + } + } +} + +func Test_getGOARCHFromBin(t *testing.T) { + runMakeTarget(t, "archs") + + tests := []struct { + name string + filepath string + expected string + }{ + { + name: "pe", + filepath: "test-fixtures/archs/binaries/hello-win-amd64", + // see: https://docs.microsoft.com/en-us/windows/win32/debug/pe-format#machine-types + expected: strconv.Itoa(0x8664), + }, + { + name: "elf-ppc64", + filepath: "test-fixtures/archs/binaries/hello-linux-ppc64le", + expected: "ppc64", + }, + { + name: "mach-o-arm64", + filepath: "test-fixtures/archs/binaries/hello-mach-o-arm64", + expected: "arm64", + }, + { + name: "linux-arm", + filepath: "test-fixtures/archs/binaries/hello-linux-arm", + expected: "arm", + }, + { + name: "xcoff-32bit", + filepath: "internal/xcoff/testdata/gcc-ppc32-aix-dwarf2-exec", + expected: strconv.Itoa(0x1DF), + }, + { + name: "xcoff-64bit", + filepath: "internal/xcoff/testdata/gcc-ppc64-aix-dwarf2-exec", + expected: strconv.Itoa(0x1F7), + }, + } + + for _, tt := range tests { + f, err := os.Open(tt.filepath) + require.NoError(t, err) + arch, err := getGOARCHFromBin(f) + require.NoError(t, err, "test name: %s", tt.name) + assert.Equal(t, tt.expected, arch) + } + +} + +func TestBuildGoPkgInfo(t *testing.T) { + const ( + goCompiledVersion = "1.18" + archDetails = "amd64" + ) + buildSettings := map[string]string{ + "GOARCH": "amd64", + "GOOS": "darwin", + "GOAMD64": "v1", + } + + expectedMain := pkg.Package{ + Name: "github.com/anchore/syft", + FoundBy: catalogerName, + Language: pkg.Go, + Type: pkg.GoModulePkg, + Version: "(devel)", + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a-path", + FileSystemID: "layer-id", + }, + }, + ), + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{ + GoCompiledVersion: goCompiledVersion, + Architecture: archDetails, + BuildSettings: buildSettings, + MainModule: "github.com/anchore/syft", + }, + } + + tests := []struct { + name string + mod *debug.BuildInfo + arch string + expected []pkg.Package + }{ + { + name: "buildGoPkgInfo parses a nil mod", + mod: nil, + expected: []pkg.Package(nil), + }, + { + name: "package without name", + mod: &debug.BuildInfo{ + Deps: []*debug.Module{ + { + Path: "github.com/adrg/xdg", + }, + { + Path: "", + Version: "v0.2.1", + }, + }, + }, + expected: []pkg.Package{ + { + Name: "github.com/adrg/xdg", + FoundBy: catalogerName, + Language: pkg.Go, + Type: pkg.GoModulePkg, + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a-path", + FileSystemID: "layer-id", + }, + }, + ), + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{}, + }, + }, + }, + { + name: "buildGoPkgInfo parses a blank mod and returns no packages", + mod: &debug.BuildInfo{}, + expected: []pkg.Package(nil), + }, + { + name: "buildGoPkgInfo parses a mod without main module", + arch: archDetails, + mod: &debug.BuildInfo{ + GoVersion: goCompiledVersion, + Settings: []debug.BuildSetting{ + {Key: "GOARCH", Value: archDetails}, + {Key: "GOOS", Value: "darwin"}, + {Key: "GOAMD64", Value: "v1"}, + }, + Deps: []*debug.Module{ + { + Path: "github.com/adrg/xdg", + Version: "v0.2.1", + Sum: "h1:VSVdnH7cQ7V+B33qSJHTCRlNgra1607Q8PzEmnvb2Ic=", + }, + }, + }, + expected: []pkg.Package{ + { + Name: "github.com/adrg/xdg", + FoundBy: catalogerName, + Version: "v0.2.1", + Language: pkg.Go, + Type: pkg.GoModulePkg, + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a-path", + FileSystemID: "layer-id", + }, + }, + ), + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{ + GoCompiledVersion: goCompiledVersion, + Architecture: archDetails, + H1Digest: "h1:VSVdnH7cQ7V+B33qSJHTCRlNgra1607Q8PzEmnvb2Ic=", + }, + }, + }, + }, + { + name: "buildGoPkgInfo parses a mod without packages", + arch: archDetails, + mod: &debug.BuildInfo{ + GoVersion: goCompiledVersion, + Main: debug.Module{Path: "github.com/anchore/syft", Version: "(devel)"}, + Settings: []debug.BuildSetting{ + {Key: "GOARCH", Value: archDetails}, + {Key: "GOOS", Value: "darwin"}, + {Key: "GOAMD64", Value: "v1"}, + }, + }, + expected: []pkg.Package{expectedMain}, + }, + { + name: "buildGoPkgInfo parses a populated mod string and returns packages but no source info", + arch: archDetails, + mod: &debug.BuildInfo{ + GoVersion: goCompiledVersion, + Main: debug.Module{Path: "github.com/anchore/syft", Version: "(devel)"}, + Settings: []debug.BuildSetting{ + {Key: "GOARCH", Value: archDetails}, + {Key: "GOOS", Value: "darwin"}, + {Key: "GOAMD64", Value: "v1"}, + }, + Deps: []*debug.Module{ + { + Path: "github.com/adrg/xdg", + Version: "v0.2.1", + Sum: "h1:VSVdnH7cQ7V+B33qSJHTCRlNgra1607Q8PzEmnvb2Ic=", + }, + { + Path: "github.com/anchore/client-go", + Version: "v0.0.0-20210222170800-9c70f9b80bcf", + Sum: "h1:DYssiUV1pBmKqzKsm4mqXx8artqC0Q8HgZsVI3lMsAg=", + }, + }, + }, + expected: []pkg.Package{ + { + Name: "github.com/adrg/xdg", + FoundBy: catalogerName, + Version: "v0.2.1", + Language: pkg.Go, + Type: pkg.GoModulePkg, + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a-path", + FileSystemID: "layer-id", + }, + }, + ), + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{ + GoCompiledVersion: goCompiledVersion, + Architecture: archDetails, + H1Digest: "h1:VSVdnH7cQ7V+B33qSJHTCRlNgra1607Q8PzEmnvb2Ic=", + MainModule: "github.com/anchore/syft", + }, + }, + { + Name: "github.com/anchore/client-go", + FoundBy: catalogerName, + Version: "v0.0.0-20210222170800-9c70f9b80bcf", + Language: pkg.Go, + Type: pkg.GoModulePkg, + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a-path", + FileSystemID: "layer-id", + }, + }, + ), + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{ + GoCompiledVersion: goCompiledVersion, + Architecture: archDetails, + H1Digest: "h1:DYssiUV1pBmKqzKsm4mqXx8artqC0Q8HgZsVI3lMsAg=", + MainModule: "github.com/anchore/syft", + }, + }, + expectedMain, + }, + }, + { + name: "buildGoPkgInfo parses a populated mod string and returns packages when a replace directive exists", + arch: archDetails, + mod: &debug.BuildInfo{ + GoVersion: goCompiledVersion, + Main: debug.Module{Path: "github.com/anchore/syft", Version: "(devel)"}, + Settings: []debug.BuildSetting{ + {Key: "GOARCH", Value: archDetails}, + {Key: "GOOS", Value: "darwin"}, + {Key: "GOAMD64", Value: "v1"}, + }, + Deps: []*debug.Module{ + { + Path: "golang.org/x/sys", + Version: "v0.0.0-20211006194710-c8a6f5223071", + Sum: "h1:PjhxBct4MZii8FFR8+oeS7QOvxKOTZXgk63EU2XpfJE=", + }, + { + Path: "golang.org/x/term", + Version: "v0.0.0-20210927222741-03fcf44c2211", + Sum: "h1:PjhxBct4MZii8FFR8+oeS7QOvxKOTZXgk63EU2XpfJE=", + Replace: &debug.Module{ + Path: "golang.org/x/term", + Version: "v0.0.0-20210916214954-140adaaadfaf", + Sum: "h1:Ihq/mm/suC88gF8WFcVwk+OV6Tq+wyA1O0E5UEvDglI=", + }, + }, + }, + }, + expected: []pkg.Package{ + { + Name: "golang.org/x/sys", + FoundBy: catalogerName, + Version: "v0.0.0-20211006194710-c8a6f5223071", + Language: pkg.Go, + Type: pkg.GoModulePkg, + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a-path", + FileSystemID: "layer-id", + }, + }, + ), + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{ + GoCompiledVersion: goCompiledVersion, + Architecture: archDetails, + H1Digest: "h1:PjhxBct4MZii8FFR8+oeS7QOvxKOTZXgk63EU2XpfJE=", + MainModule: "github.com/anchore/syft", + }}, + { + Name: "golang.org/x/term", + FoundBy: catalogerName, + Version: "v0.0.0-20210916214954-140adaaadfaf", + Language: pkg.Go, + Type: pkg.GoModulePkg, + Locations: source.NewLocationSet( + source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a-path", + FileSystemID: "layer-id", + }, + }, + ), + MetadataType: pkg.GolangBinMetadataType, + Metadata: pkg.GolangBinMetadata{ + GoCompiledVersion: goCompiledVersion, + Architecture: archDetails, + H1Digest: "h1:Ihq/mm/suC88gF8WFcVwk+OV6Tq+wyA1O0E5UEvDglI=", + MainModule: "github.com/anchore/syft", + }, + }, + expectedMain, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + for i := range test.expected { + p := &test.expected[i] + p.SetID() + } + location := source.Location{ + Coordinates: source.Coordinates{ + RealPath: "/a-path", + FileSystemID: "layer-id", + }, + } + pkgs := buildGoPkgInfo(location, test.mod, test.arch) + assert.Equal(t, test.expected, pkgs) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_mod.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_mod.go new file mode 100644 index 0000000000000000000000000000000000000000..61c52c93e7f4b88cfd917b49111b4cf3bc9a2b38 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_mod.go @@ -0,0 +1,63 @@ +package golang + +import ( + "fmt" + "io" + "sort" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "golang.org/x/mod/modfile" +) + +// parseGoMod takes a go.mod and lists all packages discovered. +func parseGoMod(path string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + packages := make(map[string]*pkg.Package) + + contents, err := io.ReadAll(reader) + if err != nil { + return nil, nil, fmt.Errorf("failed to read go module: %w", err) + } + + file, err := modfile.Parse(path, contents, nil) + if err != nil { + return nil, nil, fmt.Errorf("failed to parse go module: %w", err) + } + + for _, m := range file.Require { + packages[m.Mod.Path] = &pkg.Package{ + Name: m.Mod.Path, + Version: m.Mod.Version, + Language: pkg.Go, + Type: pkg.GoModulePkg, + } + } + + // remove any old packages and replace with new ones... + for _, m := range file.Replace { + packages[m.New.Path] = &pkg.Package{ + Name: m.New.Path, + Version: m.New.Version, + Language: pkg.Go, + Type: pkg.GoModulePkg, + } + } + + // remove any packages from the exclude fields + for _, m := range file.Exclude { + delete(packages, m.Mod.Path) + } + + pkgsSlice := make([]*pkg.Package, len(packages)) + idx := 0 + for _, p := range packages { + pkgsSlice[idx] = p + idx++ + } + + sort.SliceStable(pkgsSlice, func(i, j int) bool { + return pkgsSlice[i].Name < pkgsSlice[j].Name + }) + + return pkgsSlice, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_mod_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_mod_test.go new file mode 100644 index 0000000000000000000000000000000000000000..f685024b9921622a1ebfe31a2bb3ec75daeda0b7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/parse_go_mod_test.go @@ -0,0 +1,107 @@ +package golang + +import ( + "os" + "testing" + + "github.com/go-test/deep" + + "github.com/anchore/syft/syft/pkg" +) + +func TestParseGoMod(t *testing.T) { + tests := []struct { + fixture string + expected map[string]pkg.Package + }{ + { + fixture: "test-fixtures/one-package", + expected: map[string]pkg.Package{ + "github.com/bmatcuk/doublestar": { + Name: "github.com/bmatcuk/doublestar", + Version: "v1.3.1", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + }, + }, + { + + fixture: "test-fixtures/many-packages", + expected: map[string]pkg.Package{ + "github.com/anchore/go-testutils": { + Name: "github.com/anchore/go-testutils", + Version: "v0.0.0-20200624184116-66aa578126db", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + "github.com/anchore/go-version": { + Name: "github.com/anchore/go-version", + Version: "v1.2.2-0.20200701162849-18adb9c92b9b", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + "github.com/anchore/stereoscope": { + Name: "github.com/anchore/stereoscope", + Version: "v0.0.0-20200706164556-7cf39d7f4639", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + "github.com/bmatcuk/doublestar": { + Name: "github.com/bmatcuk/doublestar", + Version: "v8.8.8", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + "github.com/go-test/deep": { + Name: "github.com/go-test/deep", + Version: "v1.0.6", + Language: pkg.Go, + Type: pkg.GoModulePkg, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + f, err := os.Open(test.fixture) + if err != nil { + t.Fatalf(err.Error()) + } + + // TODO: no relationships are under test yet + actual, _, err := parseGoMod(test.fixture, f) + if err != nil { + t.Fatalf(err.Error()) + } + + if len(actual) != len(test.expected) { + t.Fatalf("unexpected length: %d", len(actual)) + } + + for _, a := range actual { + e, ok := test.expected[a.Name] + if !ok { + t.Errorf("extra package: %s", a.Name) + continue + } + + diffs := deep.Equal(a, &e) + if len(diffs) > 0 { + t.Errorf("diffs found for %q", a.Name) + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + } + } + + if t.Failed() { + for _, a := range actual { + t.Logf("Found: %+v", a) + } + } + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/scan_bin.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/scan_bin.go new file mode 100644 index 0000000000000000000000000000000000000000..58ad1a3d48960a924bafd83304a5c758f71455ea --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/scan_bin.go @@ -0,0 +1,48 @@ +package golang + +import ( + "debug/buildinfo" + "runtime/debug" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg/cataloger/internal/unionreader" +) + +// scanFile scans file to try to report the Go and module versions. +func scanFile(reader unionreader.UnionReader, filename string) ([]*debug.BuildInfo, []string) { + // NOTE: multiple readers are returned to cover universal binaries, which are files + // with more than one binary + readers, err := unionreader.GetReaders(reader) + if err != nil { + log.Warnf("golang cataloger: failed to open a binary: %v", err) + return nil, nil + } + + var builds []*debug.BuildInfo + for _, r := range readers { + bi, err := buildinfo.Read(r) + + // note: the stdlib does not export the error we need to check for + if err != nil { + if err.Error() == "not a Go executable" { + // since the cataloger can only select executables and not distinguish if they are a go-compiled + // binary, we should not show warnings/logs in this case. + return nil, nil + } + // in this case we could not read the or parse the file, but not explicitly because it is not a + // go-compiled binary (though it still might be). + // TODO: We should change this back to "warn" eventually. + // But right now it's catching too many cases where the reader IS NOT a Go binary at all. + // It'd be great to see how we can get those cases to be detected and handled above before we get to + // this point in execution. + log.Infof("golang cataloger: unable to read buildinfo (file=%q): %v", filename, err) + return nil, nil + } + + builds = append(builds, bi) + } + + archs := getArchs(readers, builds) + + return builds, archs +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/.gitignore b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..3155ad3e011291a635d0eb65ff3cdeecaec20147 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/.gitignore @@ -0,0 +1 @@ +binaries/ \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/Makefile b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..60eee7ff96ab2850f91183616fabf71489aaa6e8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/Makefile @@ -0,0 +1,29 @@ +DESTINATION=binaries + +all: $(DESTINATION)/hello-mach-o-arm64 $(DESTINATION)/hello-linux-arm $(DESTINATION)/hello-linux-ppc64le $(DESTINATION)/hello-win-amd64 + +$(DESTINATION)/hello-mach-o-arm64: + mkdir -p $(DESTINATION) + GOARCH=arm64 GOOS=darwin ./src/build.sh $(DESTINATION)/hello-mach-o-arm64 + +$(DESTINATION)/hello-linux-arm: + mkdir -p $(DESTINATION) + GOARCH=arm GOOS=linux ./src/build.sh $(DESTINATION)/hello-linux-arm + +$(DESTINATION)/hello-linux-ppc64le: + mkdir -p $(DESTINATION) + GOARCH=ppc64le GOOS=linux ./src/build.sh $(DESTINATION)/hello-linux-ppc64le + +$(DESTINATION)/hello-win-amd64: + mkdir -p $(DESTINATION) + GOARCH=amd64 GOOS=windows ./src/build.sh $(DESTINATION)/hello-win-amd64 + +# we need a way to determine if CI should bust the test cache based on the source material +$(DESTINATION).fingerprint: clean + mkdir -p $(DESTINATION) + find src -type f -exec sha256sum {} \; | sort | tee /dev/stderr | tee $(DESTINATION).fingerprint + sha256sum $(DESTINATION).fingerprint + +.PHONY: clean +clean: + rm -f $(DESTINATION)/* diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/build.sh b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/build.sh new file mode 100755 index 0000000000000000000000000000000000000000..8a3919470b39a8360eba120ed686195affeac5aa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/build.sh @@ -0,0 +1,20 @@ +#!/usr/bin/env bash +set -uxe + +# note: this can be easily done in a 1-liner, however circle CI does NOT allow volume mounts from the host in docker executors (since they are on remote hosts, where the host files are inaccessible) +# note: gocache override is so we can run docker build not as root in a container without permission issues + +BINARY=$1 +CTRID=$(docker create -e GOOS="${GOOS}" -e GOARCH="${GOARCH}" -u "$(id -u):$(id -g)" -e GOCACHE=/tmp -w /src golang:1.17 go build -o main main.go) + +function cleanup() { + docker rm "${CTRID}" +} + +trap cleanup EXIT +set +e + +# note: pwd = parent directory (archs) +docker cp "$(pwd)/src" "${CTRID}:/" +docker start -a "${CTRID}" +docker cp "${CTRID}:/src/main" "$BINARY" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/go.mod b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/go.mod new file mode 100644 index 0000000000000000000000000000000000000000..d49c920e3bde0fe9240ccb83ed5e99dc51da7546 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/go.mod @@ -0,0 +1,3 @@ +module arch/v1 + +go 1.17 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/main.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/main.go new file mode 100644 index 0000000000000000000000000000000000000000..d592354fb0450fa3e7b9c813db3b40f3812df861 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/archs/src/main.go @@ -0,0 +1,5 @@ +package main + +func main() { + println("свобода!") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/many-packages b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/many-packages new file mode 100644 index 0000000000000000000000000000000000000000..f748cb5745483f1c0a469288647a4030490149c6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/many-packages @@ -0,0 +1,21 @@ +module ( + github.com/anchore/syft +) + +go 1.14 + +// github.com/bogus/package v10.10.10 + +require ( + github.com/adrg/xdg v0.2.1 + github.com/anchore/go-testutils v0.0.0-20200624184116-66aa578126db // github.com/bogus/package v10.10.10 + github.com/anchore/go-version v1.2.2-0.20200701162849-18adb9c92b9b + github.com/anchore/stereoscope v0.0.0-20200706164556-7cf39d7f4639 + //github.com/ignore/this v9.9.9 // indirect + github.com/bmatcuk/doublestar v1.3.1 // indirect + github.com/go-test/deep v1.0.6 // a comment +) + +replace github.com/bmatcuk/doublestar => github.com/bmatcuk/doublestar v8.8.8 + +exclude github.com/adrg/xdg v0.2.1 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/one-package b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/one-package new file mode 100644 index 0000000000000000000000000000000000000000..4edcf7e8b29f88c15eeefb0ac46e226c0d3f5221 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/golang/test-fixtures/one-package @@ -0,0 +1,7 @@ +module github.com/anchore/syft + +go 1.14 + +require ( + github.com/bmatcuk/doublestar v1.3.1 +) diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..2841792080c827bf063a596825fe37dac16c4883 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/cataloger.go @@ -0,0 +1,15 @@ +package haskell + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewHackageCataloger returns a new Haskell cataloger object. +func NewHackageCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/stack.yaml": parseStackYaml, + "**/stack.yaml.lock": parseStackLock, + "**/cabal.project.freeze": parseCabalFreeze, + } + return common.NewGenericCataloger(nil, globParsers, "hackage-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_cabal_freeze.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_cabal_freeze.go new file mode 100644 index 0000000000000000000000000000000000000000..e09a1a7e9278a2486eea9eef725613e86349f356 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_cabal_freeze.go @@ -0,0 +1,53 @@ +package haskell + +import ( + "bufio" + "errors" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseCabalFreeze + +// parseCabalFreeze is a parser function for cabal.project.freeze contents, returning all packages discovered. +func parseCabalFreeze(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + r := bufio.NewReader(reader) + pkgs := []*pkg.Package{} + for { + line, err := r.ReadString('\n') + switch { + case errors.Is(io.EOF, err): + return pkgs, nil, nil + case err != nil: + return nil, nil, fmt.Errorf("failed to parse cabal.project.freeze file: %w", err) + } + + if !strings.Contains(line, "any.") { + continue + } + + line = strings.TrimSpace(line) + startPkgEncoding, endPkgEncoding := strings.Index(line, "any.")+4, strings.Index(line, ",") + line = line[startPkgEncoding:endPkgEncoding] + splits := strings.Split(line, " ==") + + pkgName, pkgVersion := splits[0], splits[1] + pkgs = append(pkgs, &pkg.Package{ + Name: pkgName, + Version: pkgVersion, + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: pkgName, + Version: pkgVersion, + }, + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_cabal_freeze_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_cabal_freeze_test.go new file mode 100644 index 0000000000000000000000000000000000000000..162d0d8cb4bcbd4dd1c268039cebb6ca95d0fc6d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_cabal_freeze_test.go @@ -0,0 +1,151 @@ +package haskell + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseCabalFreeze(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "Cabal", + Version: "3.2.1.0", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "Cabal", + Version: "3.2.1.0", + }, + }, + { + Name: "Diff", + Version: "0.4.1", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "Diff", + Version: "0.4.1", + }, + }, + { + Name: "HTTP", + Version: "4000.3.16", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "HTTP", + Version: "4000.3.16", + }, + }, + { + Name: "HUnit", + Version: "1.6.2.0", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "HUnit", + Version: "1.6.2.0", + }, + }, + { + Name: "OneTuple", + Version: "0.3.1", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "OneTuple", + Version: "0.3.1", + }, + }, + { + Name: "Only", + Version: "0.1", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "Only", + Version: "0.1", + }, + }, + { + Name: "PyF", + Version: "0.10.2.0", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "PyF", + Version: "0.10.2.0", + }, + }, + { + Name: "QuickCheck", + Version: "2.14.2", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "QuickCheck", + Version: "2.14.2", + }, + }, + { + Name: "RSA", + Version: "2.4.1", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "RSA", + Version: "2.4.1", + }, + }, + { + Name: "SHA", + Version: "1.6.4.4", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "SHA", + Version: "1.6.4.4", + }, + }, + { + Name: "Spock", + Version: "0.14.0.0", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "Spock", + Version: "0.14.0.0", + }, + }, + } + + fixture, err := os.Open("test-fixtures/cabal.project.freeze") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseCabalFreeze(fixture.Name(), fixture) + if err != nil { + t.Error(err) + } + + differences := deep.Equal(expected, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..0d08c25ffa6405892d0b4c3261f87ce66766f7b8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_lock.go @@ -0,0 +1,90 @@ +package haskell + +import ( + "fmt" + "io" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "gopkg.in/yaml.v3" +) + +// integrity check +var _ common.ParserFn = parseStackLock + +type stackLock struct { + Packages []stackPackage `yaml:"packages"` + Snapshots []stackSnapshot `yaml:"snapshots"` +} + +type stackPackage struct { + Completed completedPackage `yaml:"completed"` +} + +type completedPackage struct { + Hackage string `yaml:"hackage"` +} + +type stackSnapshot struct { + Completed completedSnapshot `yaml:"completed"` +} + +type completedSnapshot struct { + URL string `yaml:"url"` + Sha string `yaml:"sha256"` +} + +func parseStackPackageEncoding(pkgEncoding string) (name, version, hash string) { + lastDashIdx := strings.LastIndex(pkgEncoding, "-") + name = pkgEncoding[:lastDashIdx] + remainingEncoding := pkgEncoding[lastDashIdx+1:] + encodingSplits := strings.Split(remainingEncoding, "@") + version = encodingSplits[0] + startHash, endHash := strings.Index(encodingSplits[1], ":")+1, strings.Index(encodingSplits[1], ",") + hash = encodingSplits[1][startHash:endHash] + return +} + +// parseStackLock is a parser function for stack.yaml.lock contents, returning all packages discovered. +func parseStackLock(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + bytes, err := io.ReadAll(reader) + if err != nil { + return nil, nil, fmt.Errorf("failed to load stack.yaml.lock file: %w", err) + } + + var lockFile stackLock + + if err := yaml.Unmarshal(bytes, &lockFile); err != nil { + return nil, nil, fmt.Errorf("failed to parse stack.yaml.lock file: %w", err) + } + + var ( + pkgs []*pkg.Package + snapshotURL string + ) + + for _, snap := range lockFile.Snapshots { + snapshotURL = snap.Completed.URL + } + + for _, pack := range lockFile.Packages { + pkgName, pkgVersion, pkgHash := parseStackPackageEncoding(pack.Completed.Hackage) + pkgs = append(pkgs, &pkg.Package{ + Name: pkgName, + Version: pkgVersion, + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: pkgName, + Version: pkgVersion, + PkgHash: &pkgHash, + SnapshotURL: &snapshotURL, + }, + }) + } + + return pkgs, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..3ad296b2c9b7c489c54b63c4918c044ea4908310 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_lock_test.go @@ -0,0 +1,152 @@ +package haskell + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func fixtureP(str string) *string { + return &str +} + +func TestParseStackLock(t *testing.T) { + url := "https://raw.githubusercontent.com/commercialhaskell/stackage-snapshots/master/lts/19/14.yaml" + expected := []*pkg.Package{ + { + Name: "HTTP", + Version: "4000.3.16", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "HTTP", + Version: "4000.3.16", + PkgHash: fixtureP("6042643c15a0b43e522a6693f1e322f05000d519543a84149cb80aeffee34f71"), + SnapshotURL: &url, + }, + }, + { + Name: "configurator-pg", + Version: "0.2.6", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "configurator-pg", + Version: "0.2.6", + PkgHash: fixtureP("cd9b06a458428e493a4d6def725af7ab1ab0fef678fbd871f9586fc7f9aa70be"), + SnapshotURL: &url, + }, + }, + { + Name: "hasql-dynamic-statements", + Version: "0.3.1.1", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "hasql-dynamic-statements", + Version: "0.3.1.1", + PkgHash: fixtureP("2cfe6e75990e690f595a87cbe553f2e90fcd738610f6c66749c81cc4396b2cc4"), + SnapshotURL: &url, + }, + }, + { + Name: "hasql-implicits", + Version: "0.1.0.4", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "hasql-implicits", + Version: "0.1.0.4", + PkgHash: fixtureP("0848d3cbc9d94e1e539948fa0be4d0326b26335034161bf8076785293444ca6f"), + SnapshotURL: &url, + }, + }, + { + Name: "hasql-pool", + Version: "0.5.2.2", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "hasql-pool", + Version: "0.5.2.2", + PkgHash: fixtureP("b56d4dea112d97a2ef4b2749508c0ca646828cb2d77b827e8dc433d249bb2062"), + SnapshotURL: &url, + }, + }, + { + Name: "lens-aeson", + Version: "1.1.3", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "lens-aeson", + Version: "1.1.3", + PkgHash: fixtureP("52c8eaecd2d1c2a969c0762277c4a8ee72c339a686727d5785932e72ef9c3050"), + SnapshotURL: &url, + }, + }, + { + Name: "optparse-applicative", + Version: "0.16.1.0", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "optparse-applicative", + Version: "0.16.1.0", + PkgHash: fixtureP("418c22ed6a19124d457d96bc66bd22c93ac22fad0c7100fe4972bbb4ac989731"), + SnapshotURL: &url, + }, + }, + { + Name: "protolude", + Version: "0.3.2", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "protolude", + Version: "0.3.2", + PkgHash: fixtureP("2a38b3dad40d238ab644e234b692c8911423f9d3ed0e36b62287c4a698d92cd1"), + SnapshotURL: &url, + }, + }, + { + Name: "ptr", + Version: "0.16.8.2", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "ptr", + Version: "0.16.8.2", + PkgHash: fixtureP("708ebb95117f2872d2c5a554eb6804cf1126e86abe793b2673f913f14e5eb1ac"), + SnapshotURL: &url, + }, + }, + } + + fixture, err := os.Open("test-fixtures/stack.yaml.lock") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseStackLock(fixture.Name(), fixture) + if err != nil { + t.Error(err) + } + + differences := deep.Equal(expected, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_yaml.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_yaml.go new file mode 100644 index 0000000000000000000000000000000000000000..eb71f51ca2108c05fdf27eff7b8eb831f38b8ff3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_yaml.go @@ -0,0 +1,54 @@ +package haskell + +import ( + "fmt" + "io" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "gopkg.in/yaml.v3" +) + +// integrity check +var _ common.ParserFn = parseStackYaml + +type stackYaml struct { + ExtraDeps []string `yaml:"extra-deps"` +} + +// parseStackYaml is a parser function for stack.yaml contents, returning all packages discovered. +func parseStackYaml(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + bytes, err := io.ReadAll(reader) + if err != nil { + return nil, nil, fmt.Errorf("failed to load stack.yaml file: %w", err) + } + + var stackFile stackYaml + + if err := yaml.Unmarshal(bytes, &stackFile); err != nil { + return nil, nil, fmt.Errorf("failed to parse stack.yaml file: %w", err) + } + + var ( + pkgs []*pkg.Package + ) + + for _, dep := range stackFile.ExtraDeps { + pkgName, pkgVersion, pkgHash := parseStackPackageEncoding(dep) + pkgs = append(pkgs, &pkg.Package{ + Name: pkgName, + Version: pkgVersion, + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: pkgName, + Version: pkgVersion, + PkgHash: &pkgHash, + }, + }) + } + + return pkgs, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_yaml_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_yaml_test.go new file mode 100644 index 0000000000000000000000000000000000000000..351630b715785da43a6bded971bce39c28b9eb36 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/parse_stack_yaml_test.go @@ -0,0 +1,126 @@ +package haskell + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseStackYaml(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "ShellCheck", + Version: "0.8.0", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "ShellCheck", + Version: "0.8.0", + PkgHash: fixtureP("353c9322847b661e4c6f7c83c2acf8e5c08b682fbe516c7d46c29605937543df"), + }, + }, + { + Name: "colourista", + Version: "0.1.0.1", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "colourista", + Version: "0.1.0.1", + PkgHash: fixtureP("98353ee0e2f5d97d2148513f084c1cd37dfda03e48aa9dd7a017c9d9c0ba710e"), + }, + }, + { + Name: "language-docker", + Version: "11.0.0", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "language-docker", + Version: "11.0.0", + PkgHash: fixtureP("3406ff0c1d592490f53ead8cf2cd22bdf3d79fd125ccaf3add683f6d71c24d55"), + }, + }, + { + Name: "spdx", + Version: "1.0.0.2", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "spdx", + Version: "1.0.0.2", + PkgHash: fixtureP("7dfac9b454ff2da0abb7560f0ffbe00ae442dd5cb76e8be469f77e6988a70fed"), + }, + }, + { + Name: "hspec", + Version: "2.9.4", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "hspec", + Version: "2.9.4", + PkgHash: fixtureP("658a6a74d5a70c040edd6df2a12228c6d9e63082adaad1ed4d0438ad082a0ef3"), + }, + }, + { + Name: "hspec-core", + Version: "2.9.4", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "hspec-core", + Version: "2.9.4", + PkgHash: fixtureP("a126e9087409fef8dcafcd2f8656456527ac7bb163ed4d9cb3a57589042a5fe8"), + }, + }, + { + Name: "hspec-discover", + Version: "2.9.4", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "hspec-discover", + Version: "2.9.4", + PkgHash: fixtureP("fbcf49ecfc3d4da53e797fd0275264cba776ffa324ee223e2a3f4ec2d2c9c4a6"), + }, + }, + { + Name: "stm", + Version: "2.5.0.2", + Language: pkg.Haskell, + Type: pkg.HackagePkg, + MetadataType: pkg.HackageMetadataType, + Metadata: pkg.HackageMetadata{ + Name: "stm", + Version: "2.5.0.2", + PkgHash: fixtureP("e4dc6473faaa75fbd7eccab4e3ee1d651d75bb0e49946ef0b8b751ccde771a55"), + }, + }, + } + + fixture, err := os.Open("test-fixtures/stack.yaml") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseStackYaml(fixture.Name(), fixture) + if err != nil { + t.Error(err) + } + + differences := deep.Equal(expected, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/cabal.project.freeze b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/cabal.project.freeze new file mode 100644 index 0000000000000000000000000000000000000000..5c2cb9ac9bddbfa9bb6683451577feecb20f016c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/cabal.project.freeze @@ -0,0 +1,17 @@ +active-repositories: hackage.haskell.org:merge +constraints: any.Cabal ==3.2.1.0, + any.Diff ==0.4.1, + any.HTTP ==4000.3.16, + any.HUnit ==1.6.2.0, + any.OneTuple ==0.3.1, + tls +compat -hans +network, + any.Only ==0.1, + any.PyF ==0.10.2.0, + any.QuickCheck ==2.14.2, + semigroups +binary +bytestring -bytestring-builder +containers +deepseq +hashable +tagged +template-haskell +text +transformers +unordered-containers, + any.RSA ==2.4.1, + any.SHA ==1.6.4.4, + void -safe, + any.Spock ==0.14.0.0, + +index-state: hackage.haskell.org 2022-07-07T01:01:53Z diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/stack.yaml b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/stack.yaml new file mode 100644 index 0000000000000000000000000000000000000000..8c05906e1b01d759f87186336e32023409fd3a3a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/stack.yaml @@ -0,0 +1,16 @@ +flags: {} +extra-package-dbs: [] +packages: + - . +resolver: lts-18.28 +extra-deps: + - ShellCheck-0.8.0@sha256:353c9322847b661e4c6f7c83c2acf8e5c08b682fbe516c7d46c29605937543df,3297 + - colourista-0.1.0.1@sha256:98353ee0e2f5d97d2148513f084c1cd37dfda03e48aa9dd7a017c9d9c0ba710e,3307 + - language-docker-11.0.0@sha256:3406ff0c1d592490f53ead8cf2cd22bdf3d79fd125ccaf3add683f6d71c24d55,3883 + - spdx-1.0.0.2@sha256:7dfac9b454ff2da0abb7560f0ffbe00ae442dd5cb76e8be469f77e6988a70fed,2008 + - hspec-2.9.4@sha256:658a6a74d5a70c040edd6df2a12228c6d9e63082adaad1ed4d0438ad082a0ef3,1709 + - hspec-core-2.9.4@sha256:a126e9087409fef8dcafcd2f8656456527ac7bb163ed4d9cb3a57589042a5fe8,6498 + - hspec-discover-2.9.4@sha256:fbcf49ecfc3d4da53e797fd0275264cba776ffa324ee223e2a3f4ec2d2c9c4a6,2165 + - stm-2.5.0.2@sha256:e4dc6473faaa75fbd7eccab4e3ee1d651d75bb0e49946ef0b8b751ccde771a55,2314 +ghc-options: + "$everything": -haddock diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/stack.yaml.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/stack.yaml.lock new file mode 100644 index 0000000000000000000000000000000000000000..a185422556e28502cef265f7ed4e7aa435b48cbb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/haskell/test-fixtures/stack.yaml.lock @@ -0,0 +1,75 @@ +# This file was autogenerated by Stack. +# You should not edit this file by hand. +# For more information, please see the documentation at: +# https://docs.haskellstack.org/en/stable/lock_files + +packages: +- completed: + hackage: HTTP-4000.3.16@sha256:6042643c15a0b43e522a6693f1e322f05000d519543a84149cb80aeffee34f71,5947 + pantry-tree: + size: 1428 + sha256: b73a7f6d21cf20bbf819e19039409c9010efb5000d2b72cdd8fd67a9027c14e8 + original: + hackage: HTTP-4000.3.16@sha256:6042643c15a0b43e522a6693f1e322f05000d519543a84149cb80aeffee34f71,5947 +- completed: + hackage: configurator-pg-0.2.6@sha256:cd9b06a458428e493a4d6def725af7ab1ab0fef678fbd871f9586fc7f9aa70be,2849 + pantry-tree: + size: 2463 + sha256: 97efe7a22afc93033bda5adcffdabc0f1c30dc32b2c3ba02114ce7cd74c942fd + original: + hackage: configurator-pg-0.2.6@sha256:cd9b06a458428e493a4d6def725af7ab1ab0fef678fbd871f9586fc7f9aa70be,2849 +- completed: + hackage: hasql-dynamic-statements-0.3.1.1@sha256:2cfe6e75990e690f595a87cbe553f2e90fcd738610f6c66749c81cc4396b2cc4,2675 + pantry-tree: + size: 595 + sha256: b84ae10a5c776f88f546df73bc957a35e61056400b7e805dad0b254612907e97 + original: + hackage: hasql-dynamic-statements-0.3.1.1@sha256:2cfe6e75990e690f595a87cbe553f2e90fcd738610f6c66749c81cc4396b2cc4,2675 +- completed: + hackage: hasql-implicits-0.1.0.4@sha256:0848d3cbc9d94e1e539948fa0be4d0326b26335034161bf8076785293444ca6f,1361 + pantry-tree: + size: 264 + sha256: d49af8f8749ab7039fa668af4b78f997f7fa2928b4aded6798f573a3d08e76a0 + original: + hackage: hasql-implicits-0.1.0.4@sha256:0848d3cbc9d94e1e539948fa0be4d0326b26335034161bf8076785293444ca6f,1361 +- completed: + hackage: hasql-pool-0.5.2.2@sha256:b56d4dea112d97a2ef4b2749508c0ca646828cb2d77b827e8dc433d249bb2062,2438 + pantry-tree: + size: 412 + sha256: 2741a33f947d28b4076c798c20c1f646beecd21f5eaf522c8256cbeb34d4d6d0 + original: + hackage: hasql-pool-0.5.2.2@sha256:b56d4dea112d97a2ef4b2749508c0ca646828cb2d77b827e8dc433d249bb2062,2438 +- completed: + hackage: lens-aeson-1.1.3@sha256:52c8eaecd2d1c2a969c0762277c4a8ee72c339a686727d5785932e72ef9c3050,1764 + pantry-tree: + size: 541 + sha256: b31392b78f2a03111c805f4400007778eb93b49f998ab41dfbebaaf9b5526bad + original: + hackage: lens-aeson-1.1.3@sha256:52c8eaecd2d1c2a969c0762277c4a8ee72c339a686727d5785932e72ef9c3050,1764 +- completed: + hackage: optparse-applicative-0.16.1.0@sha256:418c22ed6a19124d457d96bc66bd22c93ac22fad0c7100fe4972bbb4ac989731,4982 + pantry-tree: + size: 2979 + sha256: dd092d843091c08691485d68a1908517079b1bc6f3d73928f37635a19dc27fc1 + original: + hackage: optparse-applicative-0.16.1.0@sha256:418c22ed6a19124d457d96bc66bd22c93ac22fad0c7100fe4972bbb4ac989731,4982 +- completed: + hackage: protolude-0.3.2@sha256:2a38b3dad40d238ab644e234b692c8911423f9d3ed0e36b62287c4a698d92cd1,2240 + pantry-tree: + size: 1594 + sha256: a36d2912ac552d950ba4476de7d950b56b82dd28e48b9f4d0efee938f10bc525 + original: + hackage: protolude-0.3.2@sha256:2a38b3dad40d238ab644e234b692c8911423f9d3ed0e36b62287c4a698d92cd1,2240 +- completed: + hackage: ptr-0.16.8.2@sha256:708ebb95117f2872d2c5a554eb6804cf1126e86abe793b2673f913f14e5eb1ac,3959 + pantry-tree: + size: 1303 + sha256: 557c438345de19f82bf01d676100da2a191ef06f624e7a4b90b09ac17cbb52a5 + original: + hackage: ptr-0.16.8.2@sha256:708ebb95117f2872d2c5a554eb6804cf1126e86abe793b2673f913f14e5eb1ac,3959 +snapshots: +- completed: + size: 618951 + url: https://raw.githubusercontent.com/commercialhaskell/stackage-snapshots/master/lts/19/14.yaml + sha256: 4c31d4ef975b0211078862566aedf3b82b6cea569fc2cde4c72a51e5a8d236ce + original: lts-19.14 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/internal/unionreader/union_reader.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/internal/unionreader/union_reader.go new file mode 100644 index 0000000000000000000000000000000000000000..2e75463044a1a9617c35580edc67f2cff4029608 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/internal/unionreader/union_reader.go @@ -0,0 +1,65 @@ +package unionreader + +import ( + "bytes" + "fmt" + "io" + + macho "github.com/anchore/go-macholibre" + "github.com/anchore/syft/internal/log" +) + +// unionReader is a single interface with all reading functions needed by multi-arch binary catalogers +// cataloger. +type UnionReader interface { + io.Reader + io.ReaderAt + io.Seeker + io.Closer +} + +// getReaders extracts one or more io.ReaderAt objects representing binaries that can be processed (multiple binaries in the case for multi-architecture binaries). +func GetReaders(f UnionReader) ([]io.ReaderAt, error) { + if macho.IsUniversalMachoBinary(f) { + machoReaders, err := macho.ExtractReaders(f) + if err != nil { + log.Debugf("extracting readers: %v", err) + return nil, err + } + + var readers []io.ReaderAt + for _, e := range machoReaders { + readers = append(readers, e.Reader) + } + + return readers, nil + } + + return []io.ReaderAt{f}, nil +} + +func GetUnionReader(readerCloser io.ReadCloser) (UnionReader, error) { + reader, ok := readerCloser.(UnionReader) + if ok { + return reader, nil + } + + b, err := io.ReadAll(readerCloser) + if err != nil { + return nil, fmt.Errorf("unable to read contents from binary: %w", err) + } + + bytesReader := bytes.NewReader(b) + + reader = struct { + io.ReadCloser + io.ReaderAt + io.Seeker + }{ + ReadCloser: io.NopCloser(bytesReader), + ReaderAt: bytesReader, + Seeker: bytesReader, + } + + return reader, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/internal/unionreader/union_reader_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/internal/unionreader/union_reader_test.go new file mode 100644 index 0000000000000000000000000000000000000000..15c67459aa1ddfcc3c9a06d66a267415c4720dce --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/internal/unionreader/union_reader_test.go @@ -0,0 +1,30 @@ +package unionreader + +import ( + "io" + "strings" + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func Test_getUnionReader_notUnionReader(t *testing.T) { + expectedContents := "this is a test" + reader := io.NopCloser(strings.NewReader(expectedContents)) + + // make certain that the test fixture does not implement the union reader + _, ok := reader.(UnionReader) + require.False(t, ok) + + actual, err := GetUnionReader(reader) + require.NoError(t, err) + + _, ok = actual.(UnionReader) + require.True(t, ok) + + b, err := io.ReadAll(actual) + require.NoError(t, err) + + assert.Equal(t, expectedContents, string(b)) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_filename.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_filename.go new file mode 100644 index 0000000000000000000000000000000000000000..cb4d14216290510b3552dde322c4aa972a62948a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_filename.go @@ -0,0 +1,119 @@ +package java + +import ( + "path/filepath" + "regexp" + "strings" + + "github.com/anchore/syft/internal/log" + + "github.com/anchore/syft/syft/pkg" +) + +// nameAndVersionPattern finds the package name and version (as named capture +// groups) in a string. The pattern's strategy is to start at the beginning of +// the string, and for every next dash-delimited group, consider the group to be +// a continuation of the package name, unless the group begins with a number or +// matches any of a specified set of "version-indicating" patterns. When a given +// group meets this criterion, consider the group and the remainder of the +// string to be the package version. +// +// Regex components of note: +// +// (?Ui) ... Sets the "U" and the "i" options for this Regex —— (ungreedy, +// and case-insensitive, respectively). "Ungreedy" is important so that the '*' that trails the package name +// component doesn't consume the rest of the string. +// +// [[:alpha:]][[:word:].]* ... Matches any word, and the word can include "word" characters ( +// which includes numbers and underscores), and periods, but the first character of the word MUST be a letter. +// +// (?:\.[[:alpha:]][[:word:].]*)* ... This looks redundant, but it's not. It +// extends the previous pattern such that the net effect of both components is +// that words can also include a period and more words (thus, when combined, not +// only is "something" matched, but so is "com.prefix.thing" +// +// (?:\d.*|(?:build\d*.*)|(?:rc?\d+(?:^[[:alpha:]].*)?)) ... +// This match group covers the "version-indicating" patterns mentioned in the above description. Given the pipes ( +// '|'), this functions as a series of 'OR'-joined conditions: +// +// \d.* ... "If it starts with a numeric digit, this is a version, no matter what follows." +// build\d*.* ... "If it starts with "build" and then a numeric digit immediately after, this is a version." +// rc?\d+(?:^[[:alpha:]].*)? ... "If it starts with "r" or "rc" and then one or more numeric digits immediately +// after, but no alpha characters right after that (in the same word), this is a version." +// +// Match examples: +// +// some-package-4.0.1 --> name="some-package", version="4.0.1" +// prefix.thing-4 --> name="prefix.thing", version="4" +// my-http2-server-5 --> name="my-http2-server", version="5" +// jetpack-build235-rc5 --> name="jetpack", version="build2.0-rc5" +// ironman-r4-2009 --> name="ironman", version="r4-2009" +var nameAndVersionPattern = regexp.MustCompile(`(?Ui)^(?P(?:[[:alpha:]][[:word:].]*(?:\.[[:alpha:]][[:word:].]*)*-?)+)(?:-(?P(\d.*|(build\d*.*)|(rc?\d+(?:^[[:alpha:]].*)?))))?$`) +var secondaryVersionPattern = regexp.MustCompile(`(?:[._-](?P(\d.*|(build\d*.*)|(rc?\d+(?:^[[:alpha:]].*)?))))?$`) + +type archiveFilename struct { + raw string + name string + version string +} + +func getSubexp(matches []string, subexpName string, re *regexp.Regexp, raw string) string { + if len(matches) < 1 { + log.Warnf("unexpectedly empty matches for archive '%s'", raw) + return "" + } + + index := re.SubexpIndex(subexpName) + if index < 1 { + log.Warnf("unexpected index of '%s' capture group for Java archive '%s'", subexpName, raw) + return "" + } + + // Prevent out-of-range panic + if len(matches) < index+1 { + log.Warnf("no match found for '%s' in '%s'", subexpName, matches[0]) + return "" + } + + return matches[index] +} + +func newJavaArchiveFilename(raw string) archiveFilename { + // trim the file extension and remove any path prefixes + cleanedFileName := strings.TrimSuffix(filepath.Base(raw), filepath.Ext(raw)) + + matches := nameAndVersionPattern.FindStringSubmatch(cleanedFileName) + + name := getSubexp(matches, "name", nameAndVersionPattern, raw) + version := getSubexp(matches, "version", nameAndVersionPattern, raw) + + // some jars get named with different conventions, like `_` or `.` + if version == "" { + matches = secondaryVersionPattern.FindStringSubmatch(name) + version = getSubexp(matches, "version", secondaryVersionPattern, raw) + if version != "" { + name = name[0 : len(name)-len(version)-1] + } + } + + return archiveFilename{ + raw: raw, + name: name, + version: version, + } +} + +func (a archiveFilename) extension() string { + return strings.TrimPrefix(filepath.Ext(a.raw), ".") +} + +func (a archiveFilename) pkgType() pkg.Type { + switch strings.ToLower(a.extension()) { + case "jar", "war", "ear", "lpkg", "par", "sar": + return pkg.JavaPkg + case "jpi", "hpi": + return pkg.JenkinsPluginPkg + default: + return pkg.UnknownPkg + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_filename_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_filename_test.go new file mode 100644 index 0000000000000000000000000000000000000000..da3c959074b136047cbf6f6aeb457fd147efa136 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_filename_test.go @@ -0,0 +1,201 @@ +package java + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/sergi/go-diff/diffmatchpatch" +) + +func TestExtractInfoFromJavaArchiveFilename(t *testing.T) { + tests := []struct { + filename string + version string + extension string + name string + ty pkg.Type + }{ + { + filename: "pkg-maven-4.3.2.blerg", + version: "4.3.2", + extension: "blerg", + name: "pkg-maven", + ty: pkg.UnknownPkg, + }, + { + filename: "pkg-maven.4.3.2.blerg", + version: "4.3.2", + extension: "blerg", + name: "pkg-maven", + ty: pkg.UnknownPkg, + }, + { + filename: "pkg-maven_4.3.2.blerg", + version: "4.3.2", + extension: "blerg", + name: "pkg-maven", + ty: pkg.UnknownPkg, + }, + { + filename: "pkg-maven-4.3.2.jar", + version: "4.3.2", + extension: "jar", + name: "pkg-maven", + ty: pkg.JavaPkg, + }, + { + filename: "pkg-extra-field-maven-4.3.2.war", + version: "4.3.2", + extension: "war", + name: "pkg-extra-field-maven", + ty: pkg.JavaPkg, + }, + { + filename: "liferay-package.lpkg", + version: "", + extension: "lpkg", + name: "liferay-package", + ty: pkg.JavaPkg, + }, + { + filename: "pkg-extra-field-maven-4.3.2-rc1.ear", + version: "4.3.2-rc1", + extension: "ear", + name: "pkg-extra-field-maven", + ty: pkg.JavaPkg, + }, + { + filename: "pkg-extra-field-maven-4.3.2-rc1.par", + version: "4.3.2-rc1", + extension: "par", + name: "pkg-extra-field-maven", + ty: pkg.JavaPkg, + }, + { + filename: "pkg-extra-field-maven-4.3.2-rc1.sar", + version: "4.3.2-rc1", + extension: "sar", + name: "pkg-extra-field-maven", + ty: pkg.JavaPkg, + }, + { + filename: "/some/path/pkg-extra-field-maven-4.3.2-rc1.jpi", + version: "4.3.2-rc1", + extension: "jpi", + name: "pkg-extra-field-maven", + ty: pkg.JenkinsPluginPkg, + }, + { + filename: "/some/path-with-version-5.4.3/pkg-extra-field-maven-4.3.2-rc1.hpi", + version: "4.3.2-rc1", + extension: "hpi", + name: "pkg-extra-field-maven", + ty: pkg.JenkinsPluginPkg, + }, + { + filename: "/some/path-with-version-5.4.3/wagon-webdav-1.0.2-beta-2.2.3a-hudson.jar", + version: "1.0.2-beta-2.2.3a-hudson", + extension: "jar", + name: "wagon-webdav", + ty: pkg.JavaPkg, + }, + { + filename: "/some/path-with-version-5.4.3/wagon-webdav-1.0.2-beta-2.2.3-hudson.jar", + version: "1.0.2-beta-2.2.3-hudson", + extension: "jar", + name: "wagon-webdav", + ty: pkg.JavaPkg, + }, + { + filename: "/some/path-with-version-5.4.3/windows-remote-command-1.0.jar", + version: "1.0", + extension: "jar", + name: "windows-remote-command", + ty: pkg.JavaPkg, + }, + { + filename: "/some/path-with-version-5.4.3/wagon-http-lightweight-1.0.5-beta-2.jar", + version: "1.0.5-beta-2", + extension: "jar", + name: "wagon-http-lightweight", + ty: pkg.JavaPkg, + }, + { + filename: "/hudson.war:WEB-INF/lib/commons-jelly-1.1-hudson-20100305.jar", + version: "1.1-hudson-20100305", + extension: "jar", + name: "commons-jelly", + ty: pkg.JavaPkg, + }, + { + filename: "/hudson.war:WEB-INF/lib/jtidy-4aug2000r7-dev-hudson-1.jar", + version: "4aug2000r7-dev-hudson-1", + extension: "jar", + name: "jtidy", + ty: pkg.JavaPkg, + }, + { + filename: "/hudson.war:WEB-INF/lib/trilead-ssh2-build212-hudson-5.jar", + version: "build212-hudson-5", + extension: "jar", + name: "trilead-ssh2", + ty: pkg.JavaPkg, + }, + { + filename: "/hudson.war:WEB-INF/lib/guava-r06.jar", + version: "r06", + extension: "jar", + name: "guava", + ty: pkg.JavaPkg, + }, + { + // regression: https://github.com/anchore/syft/issues/255 + filename: "BOOT-INF/lib/spring-data-r2dbc-1.1.0.RELEASE.jar", + version: "1.1.0.RELEASE", + extension: "jar", + name: "spring-data-r2dbc", + ty: pkg.JavaPkg, + }, + { + // regression for artifact of the same name within jboss/keycloak:13.0.1 docker image + // which covers package name components with periods in them + filename: "jboss-saaj-api_1.4_spec-1.0.2.Final.jar", + version: "1.0.2.Final", + extension: "jar", + name: "jboss-saaj-api_1.4_spec", + ty: pkg.JavaPkg, + }, + } + + for _, test := range tests { + t.Run(test.filename, func(t *testing.T) { + obj := newJavaArchiveFilename(test.filename) + + ty := obj.pkgType() + if ty != test.ty { + t.Errorf("mismatched type: %+v != %v", ty, test.ty) + } + + version := obj.version + if version != test.version { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.version, version, true) + t.Errorf("mismatched version:\n%s", dmp.DiffPrettyText(diffs)) + } + + extension := obj.extension() + if extension != test.extension { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.extension, extension, true) + t.Errorf("mismatched extension:\n%s", dmp.DiffPrettyText(diffs)) + } + + name := obj.name + if name != test.name { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.name, name, true) + t.Errorf("mismatched name:\n%s", dmp.DiffPrettyText(diffs)) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_parser.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_parser.go new file mode 100644 index 0000000000000000000000000000000000000000..b87cf55266a60e5559ab9a33b2fff3260077e277 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_parser.go @@ -0,0 +1,450 @@ +package java + +import ( + "crypto" + "fmt" + "io" + "os" + "path" + "strings" + + "github.com/anchore/syft/internal/file" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + syftFile "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseJavaArchive + +var archiveFormatGlobs = []string{ + "**/*.jar", + "**/*.war", + "**/*.ear", + "**/*.par", + "**/*.sar", + "**/*.jpi", + "**/*.hpi", + "**/*.lpkg", // Zip-compressed package used to deploy applications + // (aka plugins) to Liferay Portal server. Those files contains .JAR(s) and a .PROPERTIES file, the latter + // has information about the application and installation requirements. + // NOTE(jonasagx): If you would like to test it with lpkg file, + // use: https://web.liferay.com/marketplace/-/mp/download/25019275/7403 + // LifeRay makes it pretty cumbersome to make a such plugins; their docs are + // out of date, and they charge for their IDE. If you find an example + // project that we can build in CI feel free to include it +} + +// javaArchiveHashes are all the current hash algorithms used to calculate archive digests +var javaArchiveHashes = []crypto.Hash{ + crypto.SHA1, +} + +type archiveParser struct { + fileManifest file.ZipFileManifest + virtualPath string + archivePath string + contentPath string + fileInfo archiveFilename + detectNested bool +} + +// parseJavaArchive is a parser function for java archive contents, returning all Java libraries and nested archives. +func parseJavaArchive(virtualPath string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + parser, cleanupFn, err := newJavaArchiveParser(virtualPath, reader, true) + // note: even on error, we should always run cleanup functions + defer cleanupFn() + if err != nil { + return nil, nil, err + } + return parser.parse() +} + +// uniquePkgKey creates a unique string to identify the given package. +func uniquePkgKey(p *pkg.Package) string { + if p == nil { + return "" + } + return fmt.Sprintf("%s|%s", p.Name, p.Version) +} + +// newJavaArchiveParser returns a new java archive parser object for the given archive. Can be configured to discover +// and parse nested archives or ignore them. +func newJavaArchiveParser(virtualPath string, reader io.Reader, detectNested bool) (*archiveParser, func(), error) { + // fetch the last element of the virtual path + virtualElements := strings.Split(virtualPath, ":") + currentFilepath := virtualElements[len(virtualElements)-1] + + contentPath, archivePath, cleanupFn, err := saveArchiveToTmp(currentFilepath, reader) + if err != nil { + return nil, cleanupFn, fmt.Errorf("unable to process java archive: %w", err) + } + + fileManifest, err := file.NewZipFileManifest(archivePath) + if err != nil { + return nil, cleanupFn, fmt.Errorf("unable to read files from java archive: %w", err) + } + + return &archiveParser{ + fileManifest: fileManifest, + virtualPath: virtualPath, + archivePath: archivePath, + contentPath: contentPath, + fileInfo: newJavaArchiveFilename(currentFilepath), + detectNested: detectNested, + }, cleanupFn, nil +} + +// parse the loaded archive and return all packages found. +func (j *archiveParser) parse() ([]*pkg.Package, []artifact.Relationship, error) { + var pkgs []*pkg.Package + var relationships []artifact.Relationship + + // find the parent package from the java manifest + parentPkg, err := j.discoverMainPackage() + if err != nil { + return nil, nil, fmt.Errorf("could not generate package from %s: %w", j.virtualPath, err) + } + + // find aux packages from pom.properties/pom.xml and potentially modify the existing parentPkg + // NOTE: we cannot generate sha1 digests from packages discovered via pom.properties/pom.xml + auxPkgs, err := j.discoverPkgsFromAllMavenFiles(parentPkg) + if err != nil { + return nil, nil, err + } + pkgs = append(pkgs, auxPkgs...) + + if j.detectNested { + // find nested java archive packages + nestedPkgs, nestedRelationships, err := j.discoverPkgsFromNestedArchives(parentPkg) + if err != nil { + return nil, nil, err + } + pkgs = append(pkgs, nestedPkgs...) + relationships = append(relationships, nestedRelationships...) + } + + // lastly, add the parent package to the list (assuming the parent exists) + if parentPkg != nil { + pkgs = append([]*pkg.Package{parentPkg}, pkgs...) + } + + // add pURLs to all packages found + // note: since package information may change after initial creation when parsing multiple locations within the + // jar, we wait until the conclusion of the parsing process before synthesizing pURLs. + for _, p := range pkgs { + addPURL(p) + } + + return pkgs, relationships, nil +} + +// discoverMainPackage parses the root Java manifest used as the parent package to all discovered nested packages. +func (j *archiveParser) discoverMainPackage() (*pkg.Package, error) { + // search and parse java manifest files + // TODO: do we want to prefer or check for pom files over manifest here? + manifestMatches := j.fileManifest.GlobMatch(manifestGlob) + if len(manifestMatches) > 1 { + return nil, fmt.Errorf("found multiple manifests in the jar: %+v", manifestMatches) + } else if len(manifestMatches) == 0 { + // we did not find any manifests, but that may not be a problem (there may be other information to generate packages for) + return nil, nil + } + + // fetch the manifest file + contents, err := file.ContentsFromZip(j.archivePath, manifestMatches...) + if err != nil { + return nil, fmt.Errorf("unable to extract java manifests (%s): %w", j.virtualPath, err) + } + + // parse the manifest file into a rich object + manifestContents := contents[manifestMatches[0]] + manifest, err := parseJavaManifest(j.archivePath, strings.NewReader(manifestContents)) + if err != nil { + log.Warnf("failed to parse java manifest (%s): %+v", j.virtualPath, err) + return nil, nil + } + + archiveCloser, err := os.Open(j.archivePath) + if err != nil { + return nil, fmt.Errorf("unable to open archive path (%s): %w", j.archivePath, err) + } + defer archiveCloser.Close() + + // grab and assign digest for the entire archive + digests, err := syftFile.DigestsFromFile(archiveCloser, javaArchiveHashes) + if err != nil { + log.Warnf("failed to create digest for file=%q: %+v", j.archivePath, err) + } + + return &pkg.Package{ + Name: selectName(manifest, j.fileInfo), + Version: selectVersion(manifest, j.fileInfo), + Language: pkg.Java, + Type: j.fileInfo.pkgType(), + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: j.virtualPath, + Manifest: manifest, + ArchiveDigests: digests, + }, + }, nil +} + +// discoverPkgsFromAllMavenFiles parses Maven POM properties/xml for a given +// parent package, returning all listed Java packages found for each pom +// properties discovered and potentially updating the given parentPkg with new +// data. +func (j *archiveParser) discoverPkgsFromAllMavenFiles(parentPkg *pkg.Package) ([]*pkg.Package, error) { + if parentPkg == nil { + return nil, nil + } + + var pkgs []*pkg.Package + + // pom.properties + properties, err := pomPropertiesByParentPath(j.archivePath, j.virtualPath, j.fileManifest.GlobMatch(pomPropertiesGlob)) + if err != nil { + return nil, err + } + + // pom.xml + projects, err := pomProjectByParentPath(j.archivePath, j.virtualPath, j.fileManifest.GlobMatch(pomXMLGlob)) + if err != nil { + return nil, err + } + + for parentPath, propertiesObj := range properties { + var pomProject *pkg.PomProject + if proj, exists := projects[parentPath]; exists { + pomProject = &proj + } + + pkgFromPom := newPackageFromMavenData(propertiesObj, pomProject, parentPkg, j.virtualPath) + if pkgFromPom != nil { + pkgs = append(pkgs, pkgFromPom) + } + } + + return pkgs, nil +} + +func (j *archiveParser) discoverPkgsFromNestedArchives(parentPkg *pkg.Package) ([]*pkg.Package, []artifact.Relationship, error) { + // we know that all java archives are zip formatted files, so we can use the shared zip helper + return discoverPkgsFromZip(j.virtualPath, j.archivePath, j.contentPath, j.fileManifest, parentPkg) +} + +// discoverPkgsFromZip finds Java archives within Java archives, returning all listed Java packages found and +// associating each discovered package to the given parent package. +func discoverPkgsFromZip(virtualPath, archivePath, contentPath string, fileManifest file.ZipFileManifest, parentPkg *pkg.Package) ([]*pkg.Package, []artifact.Relationship, error) { + // search and parse pom.properties files & fetch the contents + openers, err := file.ExtractFromZipToUniqueTempFile(archivePath, contentPath, fileManifest.GlobMatch(archiveFormatGlobs...)...) + if err != nil { + return nil, nil, fmt.Errorf("unable to extract files from zip: %w", err) + } + + return discoverPkgsFromOpeners(virtualPath, openers, parentPkg) +} + +// discoverPkgsFromOpeners finds Java archives within the given files and associates them with the given parent package. +func discoverPkgsFromOpeners(virtualPath string, openers map[string]file.Opener, parentPkg *pkg.Package) ([]*pkg.Package, []artifact.Relationship, error) { + var pkgs []*pkg.Package + var relationships []artifact.Relationship + + for pathWithinArchive, archiveOpener := range openers { + nestedPkgs, nestedRelationships, err := discoverPkgsFromOpener(virtualPath, pathWithinArchive, archiveOpener) + if err != nil { + log.Warnf("unable to discover java packages from opener (%s): %+v", virtualPath, err) + continue + } + + // attach the parent package to all discovered packages that are not already associated with a java archive + for _, p := range nestedPkgs { + if metadata, ok := p.Metadata.(pkg.JavaMetadata); ok { + if metadata.Parent == nil { + metadata.Parent = parentPkg + } + p.Metadata = metadata + } + pkgs = append(pkgs, p) + } + + relationships = append(relationships, nestedRelationships...) + } + + return pkgs, relationships, nil +} + +// discoverPkgsFromOpener finds Java archives within the given file. +func discoverPkgsFromOpener(virtualPath, pathWithinArchive string, archiveOpener file.Opener) ([]*pkg.Package, []artifact.Relationship, error) { + archiveReadCloser, err := archiveOpener.Open() + if err != nil { + return nil, nil, fmt.Errorf("unable to open archived file from tempdir: %w", err) + } + defer func() { + if closeErr := archiveReadCloser.Close(); closeErr != nil { + log.Warnf("unable to close archived file from tempdir: %+v", closeErr) + } + }() + + nestedPath := fmt.Sprintf("%s:%s", virtualPath, pathWithinArchive) + nestedPkgs, nestedRelationships, err := parseJavaArchive(nestedPath, archiveReadCloser) + if err != nil { + return nil, nil, fmt.Errorf("unable to process nested java archive (%s): %w", pathWithinArchive, err) + } + + return nestedPkgs, nestedRelationships, nil +} + +func pomPropertiesByParentPath(archivePath, virtualPath string, extractPaths []string) (map[string]pkg.PomProperties, error) { + contentsOfMavenPropertiesFiles, err := file.ContentsFromZip(archivePath, extractPaths...) + if err != nil { + return nil, fmt.Errorf("unable to extract maven files: %w", err) + } + + propertiesByParentPath := make(map[string]pkg.PomProperties) + for filePath, fileContents := range contentsOfMavenPropertiesFiles { + pomProperties, err := parsePomProperties(filePath, strings.NewReader(fileContents)) + if err != nil { + log.Warnf("failed to parse pom.properties virtualPath=%q path=%q: %+v", virtualPath, filePath, err) + continue + } + + if pomProperties == nil { + continue + } + + if pomProperties.Version == "" || pomProperties.ArtifactID == "" { + // TODO: if there is no parentPkg (no java manifest) one of these poms could be the parent. We should discover the right parent and attach the correct info accordingly to each discovered package + continue + } + + propertiesByParentPath[path.Dir(filePath)] = *pomProperties + } + + return propertiesByParentPath, nil +} + +func pomProjectByParentPath(archivePath, virtualPath string, extractPaths []string) (map[string]pkg.PomProject, error) { + contentsOfMavenProjectFiles, err := file.ContentsFromZip(archivePath, extractPaths...) + if err != nil { + return nil, fmt.Errorf("unable to extract maven files: %w", err) + } + + projectByParentPath := make(map[string]pkg.PomProject) + for filePath, fileContents := range contentsOfMavenProjectFiles { + pomProject, err := parsePomXMLProject(filePath, strings.NewReader(fileContents)) + if err != nil { + log.Warnf("failed to parse pom.xml virtualPath=%q path=%q: %+v", virtualPath, filePath, err) + continue + } + + if pomProject == nil { + continue + } + + if pomProject.Version == "" || pomProject.ArtifactID == "" { + // TODO: if there is no parentPkg (no java manifest) one of these poms could be the parent. We should discover the right parent and attach the correct info accordingly to each discovered package + continue + } + + projectByParentPath[path.Dir(filePath)] = *pomProject + } + return projectByParentPath, nil +} + +// packagesFromPomProperties processes a single Maven POM properties for a given parent package, returning all listed Java packages found and +// associating each discovered package to the given parent package. Note the pom.xml is optional, the pom.properties is not. +func newPackageFromMavenData(pomProperties pkg.PomProperties, pomProject *pkg.PomProject, parentPkg *pkg.Package, virtualPath string) *pkg.Package { + // keep the artifact name within the virtual path if this package does not match the parent package + vPathSuffix := "" + if !strings.HasPrefix(pomProperties.ArtifactID, parentPkg.Name) { + vPathSuffix += ":" + pomProperties.ArtifactID + } + virtualPath += vPathSuffix + + // discovered props = new package + p := pkg.Package{ + Name: pomProperties.ArtifactID, + Version: pomProperties.Version, + Language: pkg.Java, + Type: pomProperties.PkgTypeIndicated(), + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: virtualPath, + PomProperties: &pomProperties, + PomProject: pomProject, + Parent: parentPkg, + }, + } + + if packageIdentitiesMatch(p, parentPkg) { + updateParentPackage(p, parentPkg) + return nil + } + + return &p +} + +func packageIdentitiesMatch(p pkg.Package, parentPkg *pkg.Package) bool { + // the name/version pair matches... + if uniquePkgKey(&p) == uniquePkgKey(parentPkg) { + return true + } + + metadata := p.Metadata.(pkg.JavaMetadata) + + // the virtual path matches... + if parentPkg.Metadata.(pkg.JavaMetadata).VirtualPath == metadata.VirtualPath { + return true + } + + // the pom artifactId is the parent name + // note: you CANNOT use name-is-subset-of-artifact-id or vice versa --this is too generic. Shaded jars are a good + // example of this: where the package name is "cloudbees-analytics-segment-driver" and a child is "analytics", but + // they do not indicate the same package. + if metadata.PomProperties.ArtifactID != "" && parentPkg.Name == metadata.PomProperties.ArtifactID { + return true + } + + return false +} + +func updateParentPackage(p pkg.Package, parentPkg *pkg.Package) { + // we've run across more information about our parent package, add this info to the parent package metadata + // the pom properties is typically a better source of information for name and version than the manifest + parentPkg.Name = p.Name + parentPkg.Version = p.Version + + // we may have learned more about the type via data in the pom properties + parentPkg.Type = p.Type + + metadata, ok := p.Metadata.(pkg.JavaMetadata) + if !ok { + return + } + pomPropertiesCopy := *metadata.PomProperties + + // keep the pom properties, but don't overwrite existing pom properties + parentMetadata, ok := parentPkg.Metadata.(pkg.JavaMetadata) + if ok && parentMetadata.PomProperties == nil { + parentMetadata.PomProperties = &pomPropertiesCopy + parentPkg.Metadata = parentMetadata + } +} + +func addPURL(p *pkg.Package) { + purl := packageURL(*p) + if purl == "" { + return + } + + metadata, ok := p.Metadata.(pkg.JavaMetadata) + if !ok { + return + } + metadata.PURL = purl + p.Metadata = metadata +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_parser_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_parser_test.go new file mode 100644 index 0000000000000000000000000000000000000000..64d181496976d93ed4a7985cbf876fa97ced4305 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/archive_parser_test.go @@ -0,0 +1,949 @@ +package java + +import ( + "bufio" + "fmt" + "io" + "os" + "os/exec" + "path" + "path/filepath" + "strings" + "syscall" + "testing" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" + "github.com/gookit/color" + "github.com/stretchr/testify/assert" +) + +func generateJavaBuildFixture(t *testing.T, fixturePath string) { + if _, err := os.Stat(fixturePath); !os.IsNotExist(err) { + // fixture already exists... + return + } + + makeTask := strings.TrimPrefix(fixturePath, "test-fixtures/java-builds/") + t.Logf(color.Bold.Sprintf("Generating Fixture from 'make %s'", makeTask)) + + cwd, err := os.Getwd() + if err != nil { + t.Errorf("unable to get cwd: %+v", err) + } + + cmd := exec.Command("make", makeTask) + cmd.Dir = filepath.Join(cwd, "test-fixtures/java-builds/") + + stderr, err := cmd.StderrPipe() + if err != nil { + t.Fatalf("could not get stderr: %+v", err) + } + stdout, err := cmd.StdoutPipe() + if err != nil { + t.Fatalf("could not get stdout: %+v", err) + } + + err = cmd.Start() + if err != nil { + t.Fatalf("failed to start cmd: %+v", err) + } + + show := func(label string, reader io.ReadCloser) { + scanner := bufio.NewScanner(reader) + scanner.Split(bufio.ScanLines) + for scanner.Scan() { + t.Logf("%s: %s", label, scanner.Text()) + } + } + go show("out", stdout) + go show("err", stderr) + + if err := cmd.Wait(); err != nil { + if exiterr, ok := err.(*exec.ExitError); ok { + // The program has exited with an exit code != 0 + + // This works on both Unix and Windows. Although package + // syscall is generally platform dependent, WaitStatus is + // defined for both Unix and Windows and in both cases has + // an ExitStatus() method with the same signature. + if status, ok := exiterr.Sys().(syscall.WaitStatus); ok { + if status.ExitStatus() != 0 { + t.Fatalf("failed to generate fixture: rc=%d", status.ExitStatus()) + } + } + } else { + t.Fatalf("unable to get generate fixture result: %+v", err) + } + } +} + +func TestParseJar(t *testing.T) { + tests := []struct { + fixture string + expected map[string]pkg.Package + ignoreExtras []string + }{ + { + fixture: "test-fixtures/java-builds/packages/example-jenkins-plugin.hpi", + ignoreExtras: []string{ + "Plugin-Version", // has dynamic date + "Built-By", // podman returns the real UID + "Build-Jdk", // can't guarantee the JDK used at build time + }, + expected: map[string]pkg.Package{ + "example-jenkins-plugin": { + Name: "example-jenkins-plugin", + Version: "1.0-SNAPSHOT", + Language: pkg.Java, + Type: pkg.JenkinsPluginPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: "test-fixtures/java-builds/packages/example-jenkins-plugin.hpi", + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + "Specification-Title": "Example Jenkins Plugin", + "Specification-Version": "1.0", + "Implementation-Title": "Example Jenkins Plugin", + "Implementation-Version": "1.0-SNAPSHOT", + // extra fields... + //"Archiver-Version": "Plexus Archiver", + "Plugin-License-Url": "https://opensource.org/licenses/MIT", + "Plugin-License-Name": "MIT License", + "Created-By": "Maven Archiver 3.6.0", + //"Built-By": "?", + //"Build-Jdk": "14.0.1", + "Build-Jdk-Spec": "18", + "Jenkins-Version": "2.204", + //"Minimum-Java-Version": "1.8", + "Plugin-Developers": "", + "Plugin-ScmUrl": "https://github.com/jenkinsci/plugin-pom/example-jenkins-plugin", + //"Extension-Name": "example-jenkins-plugin", + "Short-Name": "example-jenkins-plugin", + "Group-Id": "io.jenkins.plugins", + "Plugin-Dependencies": "structs:1.20", + //"Plugin-Version": "1.0-SNAPSHOT (private-07/09/2020 13:30-?)", + "Hudson-Version": "2.204", + "Long-Name": "Example Jenkins Plugin", + }, + }, + PomProperties: &pkg.PomProperties{ + Path: "META-INF/maven/io.jenkins.plugins/example-jenkins-plugin/pom.properties", + GroupID: "io.jenkins.plugins", + ArtifactID: "example-jenkins-plugin", + Version: "1.0-SNAPSHOT", + Extra: map[string]string{}, + }, + PURL: "pkg:maven/io.jenkins.plugins/example-jenkins-plugin@1.0-SNAPSHOT", + }, + }, + }, + }, + { + fixture: "test-fixtures/java-builds/packages/example-java-app-gradle-0.1.0.jar", + expected: map[string]pkg.Package{ + "example-java-app-gradle": { + Name: "example-java-app-gradle", + Version: "0.1.0", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: "test-fixtures/java-builds/packages/example-java-app-gradle-0.1.0.jar", + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + }, + }, + PURL: "pkg:maven/example-java-app-gradle/example-java-app-gradle@0.1.0", + }, + }, + }, + }, + { + fixture: "test-fixtures/java-builds/packages/example-java-app-maven-0.1.0.jar", + ignoreExtras: []string{ + "Build-Jdk", // can't guarantee the JDK used at build time + "Built-By", // podman returns the real UID + }, + expected: map[string]pkg.Package{ + "example-java-app-maven": { + Name: "example-java-app-maven", + Version: "0.1.0", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: "test-fixtures/java-builds/packages/example-java-app-maven-0.1.0.jar", + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + // extra fields... + "Archiver-Version": "Plexus Archiver", + "Created-By": "Apache Maven 3.8.6", + //"Built-By": "?", + //"Build-Jdk": "14.0.1", + "Main-Class": "hello.HelloWorld", + }, + }, + PomProperties: &pkg.PomProperties{ + Path: "META-INF/maven/org.anchore/example-java-app-maven/pom.properties", + GroupID: "org.anchore", + ArtifactID: "example-java-app-maven", + Version: "0.1.0", + Extra: map[string]string{}, + }, + PURL: "pkg:maven/org.anchore/example-java-app-maven@0.1.0", + }, + }, + "joda-time": { + Name: "joda-time", + Version: "2.9.2", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + // ensure that nested packages with different names than that of the parent are appended as + // a suffix on the virtual path + VirtualPath: "test-fixtures/java-builds/packages/example-java-app-maven-0.1.0.jar:joda-time", + PomProperties: &pkg.PomProperties{ + Path: "META-INF/maven/joda-time/joda-time/pom.properties", + GroupID: "joda-time", + ArtifactID: "joda-time", + Version: "2.9.2", + Extra: map[string]string{}, + }, + PomProject: &pkg.PomProject{ + Path: "META-INF/maven/joda-time/joda-time/pom.xml", + GroupID: "joda-time", + ArtifactID: "joda-time", + Version: "2.9.2", + Name: "Joda-Time", + Description: "Date and time library to replace JDK date handling", + URL: "http://www.joda.org/joda-time/", + }, + PURL: "pkg:maven/joda-time/joda-time@2.9.2", + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(path.Base(test.fixture), func(t *testing.T) { + + generateJavaBuildFixture(t, test.fixture) + + fixture, err := os.Open(test.fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + parser, cleanupFn, err := newJavaArchiveParser(fixture.Name(), fixture, false) + defer cleanupFn() + if err != nil { + t.Fatalf("should not have filed... %+v", err) + } + + actual, _, err := parser.parse() + if err != nil { + t.Fatalf("failed to parse java archive: %+v", err) + } + + if len(actual) != len(test.expected) { + for _, a := range actual { + t.Log(" ", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(test.expected)) + } + + var parent *pkg.Package + for _, a := range actual { + if strings.Contains(a.Name, "example-") { + parent = a + } + } + + if parent == nil { + t.Fatal("could not find the parent pkg") + } + + for _, a := range actual { + e, ok := test.expected[a.Name] + if !ok { + t.Errorf("entry not found: %s", a.Name) + continue + } + + if a.Name != parent.Name && a.Metadata.(pkg.JavaMetadata).Parent != nil && a.Metadata.(pkg.JavaMetadata).Parent.Name != parent.Name { + t.Errorf("mismatched parent: %+v", a.Metadata.(pkg.JavaMetadata).Parent) + } + + // we need to compare the other fields without parent attached + metadata := a.Metadata.(pkg.JavaMetadata) + metadata.Parent = nil + + // redact Digest which is computed differently between CI and local + if len(metadata.ArchiveDigests) > 0 { + metadata.ArchiveDigests = nil + } + + // ignore select fields (only works for the main section) + for _, field := range test.ignoreExtras { + if metadata.Manifest != nil && metadata.Manifest.Main != nil { + delete(metadata.Manifest.Main, field) + } + } + + // write censored data back + a.Metadata = metadata + + diffs := deep.Equal(&e, a) + if len(diffs) > 0 { + t.Errorf("diffs found for %q", a.Name) + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + } + } + }) + } +} + +func TestParseNestedJar(t *testing.T) { + tests := []struct { + fixture string + expected []pkg.Package + ignoreExtras []string + }{ + { + fixture: "test-fixtures/java-builds/packages/spring-boot-0.0.1-SNAPSHOT.jar", + expected: []pkg.Package{ + { + Name: "spring-boot", + Version: "0.0.1-SNAPSHOT", + }, + { + Name: "spring-boot-starter", + Version: "2.2.2.RELEASE", + }, + { + Name: "jul-to-slf4j", + Version: "1.7.29", + }, + { + Name: "tomcat-embed-websocket", + Version: "9.0.29", + }, + { + Name: "spring-boot-starter-validation", + Version: "2.2.2.RELEASE", + }, + { + Name: "hibernate-validator", + Version: "6.0.18.Final", + }, + { + Name: "jboss-logging", + Version: "3.4.1.Final", + }, + { + Name: "spring-expression", + Version: "5.2.2.RELEASE", + }, + { + Name: "jakarta.validation-api", + Version: "2.0.1", + }, + { + Name: "spring-web", + Version: "5.2.2.RELEASE", + }, + { + Name: "spring-boot-starter-actuator", + Version: "2.2.2.RELEASE", + }, + { + Name: "log4j-api", + Version: "2.12.1", + }, + { + Name: "snakeyaml", + Version: "1.25", + }, + { + Name: "jackson-core", + Version: "2.10.1", + }, + { + Name: "jackson-datatype-jsr310", + Version: "2.10.1", + }, + { + Name: "spring-aop", + Version: "5.2.2.RELEASE", + }, + { + Name: "spring-boot-actuator-autoconfigure", + Version: "2.2.2.RELEASE", + }, + { + Name: "spring-jcl", + Version: "5.2.2.RELEASE", + }, + { + Name: "spring-boot", + Version: "2.2.2.RELEASE", + }, + { + Name: "spring-boot-starter-logging", + Version: "2.2.2.RELEASE", + }, + { + Name: "jakarta.annotation-api", + Version: "1.3.5", + }, + { + Name: "spring-webmvc", + Version: "5.2.2.RELEASE", + }, + { + Name: "HdrHistogram", + Version: "2.1.11", + }, + { + Name: "spring-boot-starter-web", + Version: "2.2.2.RELEASE", + }, + { + Name: "logback-classic", + Version: "1.2.3", + }, + { + Name: "log4j-to-slf4j", + Version: "2.12.1", + }, + { + Name: "spring-boot-starter-json", + Version: "2.2.2.RELEASE", + }, + { + Name: "jackson-databind", + Version: "2.10.1", + }, + { + Name: "jackson-module-parameter-names", + Version: "2.10.1", + }, + { + Name: "LatencyUtils", + Version: "2.0.3", + }, + { + Name: "spring-boot-autoconfigure", + Version: "2.2.2.RELEASE", + }, + { + Name: "jackson-datatype-jdk8", + Version: "2.10.1", + }, + { + Name: "tomcat-embed-core", + Version: "9.0.29", + }, + { + Name: "tomcat-embed-el", + Version: "9.0.29", + }, + { + Name: "spring-beans", + Version: "5.2.2.RELEASE", + }, + { + Name: "spring-boot-actuator", + Version: "2.2.2.RELEASE", + }, + { + Name: "slf4j-api", + Version: "1.7.29", + }, + { + Name: "spring-core", + Version: "5.2.2.RELEASE", + }, + { + Name: "logback-core", + Version: "1.2.3", + }, + { + Name: "micrometer-core", + Version: "1.3.1", + }, + { + Name: "pcollections", + Version: "3.1.0", + }, + { + Name: "jackson-annotations", + Version: "2.10.1", + }, + { + Name: "spring-boot-starter-tomcat", + Version: "2.2.2.RELEASE", + }, + { + Name: "classmate", + Version: "1.5.1", + }, + { + Name: "spring-context", + Version: "5.2.2.RELEASE", + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + + generateJavaBuildFixture(t, test.fixture) + + fixture, err := os.Open(test.fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, _, err := parseJavaArchive(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse java archive: %+v", err) + } + + expectedNameVersionPairSet := internal.NewStringSet() + + makeKey := func(p *pkg.Package) string { + if p == nil { + t.Fatal("cannot make key for nil pkg") + } + return fmt.Sprintf("%s|%s", p.Name, p.Version) + } + + for _, e := range test.expected { + expectedNameVersionPairSet.Add(makeKey(&e)) + } + + actualNameVersionPairSet := internal.NewStringSet() + for _, a := range actual { + key := makeKey(a) + actualNameVersionPairSet.Add(key) + if !expectedNameVersionPairSet.Contains(key) { + t.Errorf("extra package: %s", a) + } + } + + for _, key := range expectedNameVersionPairSet.ToSlice() { + if !actualNameVersionPairSet.Contains(key) { + t.Errorf("missing package: %s", key) + } + } + + if len(actual) != len(expectedNameVersionPairSet) { + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(expectedNameVersionPairSet)) + } + + for _, a := range actual { + actualKey := makeKey(a) + + metadata := a.Metadata.(pkg.JavaMetadata) + if actualKey == "spring-boot|0.0.1-SNAPSHOT" { + if metadata.Parent != nil { + t.Errorf("expected no parent for root pkg, got %q", makeKey(metadata.Parent)) + } + } else { + if metadata.Parent == nil { + t.Errorf("unassigned error for pkg=%q", actualKey) + } else if makeKey(metadata.Parent) != "spring-boot|0.0.1-SNAPSHOT" { + // NB: this is a hard-coded condition to simplify the test harness to account for https://github.com/micrometer-metrics/micrometer/issues/1785 + if a.Name == "pcollections" { + if metadata.Parent.Name != "micrometer-core" { + t.Errorf("nested 'pcollections' pkg has wrong parent: %q", metadata.Parent.Name) + } + } else { + t.Errorf("bad parent for pkg=%q parent=%q", actualKey, makeKey(metadata.Parent)) + } + } + } + } + }) + } +} + +func Test_newPackageFromMavenData(t *testing.T) { + virtualPath := "given/virtual/path" + tests := []struct { + name string + props pkg.PomProperties + project *pkg.PomProject + parent *pkg.Package + expectedParent pkg.Package + expectedPackage *pkg.Package + }{ + { + name: "go case: get a single package from pom properties", + props: pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-artifact-id", + Version: "1.0", + }, + parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + // note: the SAME as the original parent values + expectedParent: pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + expectedPackage: &pkg.Package{ + Name: "some-artifact-id", + Version: "1.0", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: virtualPath + ":" + "some-artifact-id", + PomProperties: &pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-artifact-id", + Version: "1.0", + }, + Parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + }, + }, + }, + { + name: "get a single package from pom properties + project", + props: pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-artifact-id", + Version: "1.0", + }, + project: &pkg.PomProject{ + Parent: &pkg.PomParent{ + GroupID: "some-parent-group-id", + ArtifactID: "some-parent-artifact-id", + Version: "1.0-parent", + }, + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-artifact-id", + Version: "1.0", + Description: "desc", + URL: "aweso.me", + }, + parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + // note: the SAME as the original parent values + expectedParent: pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + expectedPackage: &pkg.Package{ + Name: "some-artifact-id", + Version: "1.0", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: virtualPath + ":" + "some-artifact-id", + PomProperties: &pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-artifact-id", + Version: "1.0", + }, + PomProject: &pkg.PomProject{ + Parent: &pkg.PomParent{ + GroupID: "some-parent-group-id", + ArtifactID: "some-parent-artifact-id", + Version: "1.0-parent", + }, + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-artifact-id", + Version: "1.0", + Description: "desc", + URL: "aweso.me", + }, + Parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + }, + }, + }, + { + name: "single package from pom properties that's a Jenkins plugin", + props: pkg.PomProperties{ + Name: "some-name", + GroupID: "com.cloudbees.jenkins.plugins", + ArtifactID: "some-artifact-id", + Version: "1.0", + }, + parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + // note: the SAME as the original parent values + expectedParent: pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + expectedPackage: &pkg.Package{ + Name: "some-artifact-id", + Version: "1.0", + Language: pkg.Java, + Type: pkg.JenkinsPluginPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: virtualPath + ":" + "some-artifact-id", + PomProperties: &pkg.PomProperties{ + Name: "some-name", + GroupID: "com.cloudbees.jenkins.plugins", + ArtifactID: "some-artifact-id", + Version: "1.0", + }, + Parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + }, + }, + }, + { + name: "child matches parent by key", + props: pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-parent-name", // note: matches parent package + Version: "2.0", // note: matches parent package + }, + parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Type: pkg.JavaPkg, + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + // note: the SAME as the original parent values + expectedParent: pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Type: pkg.JavaPkg, + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + // note: we attach the discovered pom properties data + PomProperties: &pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-parent-name", // note: matches parent package + Version: "2.0", // note: matches parent package + }, + Parent: nil, + }, + }, + expectedPackage: nil, + }, + { + name: "child matches parent by key and is Jenkins plugin", + props: pkg.PomProperties{ + Name: "some-name", + GroupID: "com.cloudbees.jenkins.plugins", + ArtifactID: "some-parent-name", // note: matches parent package + Version: "2.0", // note: matches parent package + }, + parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Type: pkg.JavaPkg, + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + expectedParent: pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Type: pkg.JenkinsPluginPkg, + Metadata: pkg.JavaMetadata{ + VirtualPath: "some-parent-virtual-path", + Manifest: nil, + // note: we attach the discovered pom properties data + PomProperties: &pkg.PomProperties{ + Name: "some-name", + GroupID: "com.cloudbees.jenkins.plugins", + ArtifactID: "some-parent-name", // note: matches parent package + Version: "2.0", // note: matches parent package + }, + Parent: nil, + }, + }, + expectedPackage: nil, + }, + { + name: "child matches parent by virtual path -- override name and version", + props: pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-parent-name", // note: DOES NOT match parent package + Version: "3.0", // note: DOES NOT match parent package + }, + parent: &pkg.Package{ + Name: "", // note: empty, so should not be matched on + Version: "", // note: empty, so should not be matched on + Type: pkg.JavaPkg, + Metadata: pkg.JavaMetadata{ + VirtualPath: virtualPath, // note: matching virtual path + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + expectedParent: pkg.Package{ + Name: "some-parent-name", + Version: "3.0", + Type: pkg.JavaPkg, + Metadata: pkg.JavaMetadata{ + VirtualPath: virtualPath, + Manifest: nil, + // note: we attach the discovered pom properties data + PomProperties: &pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-parent-name", + Version: "3.0", + }, + Parent: nil, + }, + }, + expectedPackage: nil, + }, + { + name: "child matches parent by artifact id", + props: pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-parent-name", // note: matches parent package + Version: "NOT_THE_PARENT_VERSION", // note: DOES NOT match parent package + }, + parent: &pkg.Package{ + Name: "some-parent-name", + Version: "2.0", + Type: pkg.JavaPkg, + Metadata: pkg.JavaMetadata{ + VirtualPath: virtualPath + ":NEW_VIRTUAL_PATH", // note: DOES NOT match the existing virtual path + Manifest: nil, + PomProperties: nil, + Parent: nil, + }, + }, + // note: the SAME as the original parent values + expectedParent: pkg.Package{ + Name: "some-parent-name", + Version: "NOT_THE_PARENT_VERSION", // note: the version is updated from pom properties + Type: pkg.JavaPkg, + Metadata: pkg.JavaMetadata{ + VirtualPath: virtualPath + ":NEW_VIRTUAL_PATH", + Manifest: nil, + // note: we attach the discovered pom properties data + PomProperties: &pkg.PomProperties{ + Name: "some-name", + GroupID: "some-group-id", + ArtifactID: "some-parent-name", + Version: "NOT_THE_PARENT_VERSION", + }, + Parent: nil, + }, + }, + expectedPackage: nil, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actualPackage := newPackageFromMavenData(test.props, test.project, test.parent, virtualPath) + assert.Equal(t, test.expectedPackage, actualPackage, "new package doesn't match") + assert.Equal(t, test.expectedParent, *test.parent, "parent doesn't match") + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..5adefd492863115618fe0fdcb7fd1cd8f6262e60 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/cataloger.go @@ -0,0 +1,34 @@ +/* +Package java provides a concrete Cataloger implementation for Java archives (jar, war, ear, par, sar, jpi, hpi formats). +*/ +package java + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewJavaCataloger returns a new Java archive cataloger object. +func NewJavaCataloger(cfg Config) *common.GenericCataloger { + globParsers := make(map[string]common.ParserFn) + + // java archive formats + for _, pattern := range archiveFormatGlobs { + globParsers[pattern] = parseJavaArchive + } + + if cfg.SearchIndexedArchives { + // java archives wrapped within zip files + for _, pattern := range genericZipGlobs { + globParsers[pattern] = parseZipWrappedJavaArchive + } + } + + if cfg.SearchUnindexedArchives { + // java archives wrapped within tar files + for _, pattern := range genericTarGlobs { + globParsers[pattern] = parseTarWrappedJavaArchive + } + } + + return common.NewGenericCataloger(nil, globParsers, "java-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/config.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/config.go new file mode 100644 index 0000000000000000000000000000000000000000..84b940ac1845e4faa478e21c86e6e87754ca659b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/config.go @@ -0,0 +1,6 @@ +package java + +type Config struct { + SearchUnindexedArchives bool + SearchIndexedArchives bool +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/package_url.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/package_url.go new file mode 100644 index 0000000000000000000000000000000000000000..9d5cccd3eb96f066ab23e638fe04a1639d816b5c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/package_url.go @@ -0,0 +1,25 @@ +package java + +import ( + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common/cpe" +) + +// PackageURL returns the PURL for the specific java package (see https://github.com/package-url/purl-spec) +func packageURL(p pkg.Package) string { + var groupID = p.Name + groupIDs := cpe.GroupIDsFromJavaPackage(p) + if len(groupIDs) > 0 { + groupID = groupIDs[0] + } + + pURL := packageurl.NewPackageURL( + packageurl.TypeMaven, // TODO: should we filter down by package types here? + groupID, + p.Name, + p.Version, + nil, // TODO: there are probably several qualifiers that can be specified here + "") + return pURL.ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/package_url_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/package_url_test.go new file mode 100644 index 0000000000000000000000000000000000000000..27cf46ef91ae5006da2449a17532161dbfe98407 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/package_url_test.go @@ -0,0 +1,45 @@ +package java + +import ( + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" + "testing" +) + +func Test_packageURL(t *testing.T) { + tests := []struct { + pkg pkg.Package + expect string + }{ + { + pkg: pkg.Package{ + Name: "example-java-app-maven", + Version: "0.1.0", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + VirtualPath: "test-fixtures/java-builds/packages/example-java-app-maven-0.1.0.jar", + Manifest: &pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + }, + }, + PomProperties: &pkg.PomProperties{ + Path: "META-INF/maven/org.anchore/example-java-app-maven/pom.properties", + GroupID: "org.anchore", + ArtifactID: "example-java-app-maven", + Version: "0.1.0", + Extra: make(map[string]string), + }, + }, + }, + expect: "pkg:maven/org.anchore/example-java-app-maven@0.1.0", + }, + } + for _, tt := range tests { + t.Run(tt.expect, func(t *testing.T) { + assert.Equal(t, tt.expect, packageURL(tt.pkg)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_java_manifest.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_java_manifest.go new file mode 100644 index 0000000000000000000000000000000000000000..688595b030f625178a8674ccfc0c3ea8d79a9a40 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_java_manifest.go @@ -0,0 +1,173 @@ +package java + +import ( + "bufio" + "fmt" + "io" + "strconv" + "strings" + + "github.com/anchore/syft/internal/log" + + "github.com/anchore/syft/syft/pkg" +) + +const manifestGlob = "/META-INF/MANIFEST.MF" + +// parseJavaManifest takes MANIFEST.MF file content and returns sections of parsed key/value pairs. +// For more information: https://docs.oracle.com/en/java/javase/11/docs/specs/jar/jar.html#jar-manifest +// +//nolint:funlen +func parseJavaManifest(path string, reader io.Reader) (*pkg.JavaManifest, error) { + var manifest pkg.JavaManifest + var sections []map[string]string + + currentSection := func() int { + return len(sections) - 1 + } + + var lastKey string + scanner := bufio.NewScanner(reader) + + for scanner.Scan() { + line := scanner.Text() + + // empty lines denote section separators + if strings.TrimSpace(line) == "" { + // we don't want to allocate a new section map that won't necessarily be used, do that once there is + // a non-empty line to process + + // do not process line continuations after this + lastKey = "" + + continue + } + + if line[0] == ' ' { + // this is a continuation + + if lastKey == "" { + log.Warnf("java manifest %q: found continuation with no previous key: %q", path, line) + continue + } + + sections[currentSection()][lastKey] += strings.TrimSpace(line) + + continue + } + + // this is a new key-value pair + idx := strings.Index(line, ":") + if idx == -1 { + log.Warnf("java manifest %q: unable to split java manifest key-value pairs: %q", path, line) + continue + } + + key := strings.TrimSpace(line[0:idx]) + value := strings.TrimSpace(line[idx+1:]) + + if key == "" { + // don't attempt to add new keys or sections unless there is a non-empty key + continue + } + + if lastKey == "" { + // we're entering a new section + sections = append(sections, make(map[string]string)) + } + + sections[currentSection()][key] = value + + // keep track of key for potential future continuations + lastKey = key + } + + if err := scanner.Err(); err != nil { + return nil, fmt.Errorf("unable to read java manifest: %w", err) + } + + if len(sections) > 0 { + manifest.Main = sections[0] + if len(sections) > 1 { + manifest.NamedSections = make(map[string]map[string]string) + for i, s := range sections[1:] { + name, ok := s["Name"] + if !ok { + // per the manifest spec (https://docs.oracle.com/en/java/javase/11/docs/specs/jar/jar.html#jar-manifest) + // this should never happen. If it does, we want to know about it, but not necessarily stop + // cataloging entirely... for this reason we only log. + log.Warnf("java manifest section found without a name: %s", path) + name = strconv.Itoa(i) + } else { + delete(s, "Name") + } + manifest.NamedSections[name] = s + } + } + } + + return &manifest, nil +} + +func selectName(manifest *pkg.JavaManifest, filenameObj archiveFilename) string { + var name string + switch { + case filenameObj.name != "": + name = filenameObj.name + case manifest.Main["Name"] != "": + // Manifest original spec... + name = manifest.Main["Name"] + case manifest.Main["Bundle-Name"] != "": + // BND tooling... + name = manifest.Main["Bundle-Name"] + case manifest.Main["Short-Name"] != "": + // Jenkins... + name = manifest.Main["Short-Name"] + case manifest.Main["Extension-Name"] != "": + // Jenkins... + name = manifest.Main["Extension-Name"] + case manifest.Main["Implementation-Title"] != "": + // last ditch effort... + name = manifest.Main["Implementation-Title"] + } + return name +} + +func selectVersion(manifest *pkg.JavaManifest, filenameObj archiveFilename) string { + if v := filenameObj.version; v != "" { + return v + } + + if manifest == nil { + return "" + } + + fieldNames := []string{ + "Implementation-Version", + "Specification-Version", + "Plugin-Version", + "Bundle-Version", + } + + for _, fieldName := range fieldNames { + if v := fieldValueFromManifest(*manifest, fieldName); v != "" { + return v + } + } + + return "" +} + +func fieldValueFromManifest(manifest pkg.JavaManifest, fieldName string) string { + if value := manifest.Main[fieldName]; value != "" { + return value + } + + for _, section := range manifest.NamedSections { + if value := section[fieldName]; value != "" { + return value + } + } + + return "" +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_java_manifest_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_java_manifest_test.go new file mode 100644 index 0000000000000000000000000000000000000000..0982e35b2a32390dc207d7504b5cb8a7d83b7415 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_java_manifest_test.go @@ -0,0 +1,264 @@ +package java + +import ( + "encoding/json" + "os" + "testing" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseJavaManifest(t *testing.T) { + tests := []struct { + fixture string + expected pkg.JavaManifest + }{ + { + fixture: "test-fixtures/manifest/small", + expected: pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + }, + }, + }, + { + fixture: "test-fixtures/manifest/standard-info", + expected: pkg.JavaManifest{ + Main: map[string]string{ + "Name": "the-best-name", + "Manifest-Version": "1.0", + "Specification-Title": "the-spec-title", + "Specification-Version": "the-spec-version", + "Specification-Vendor": "the-spec-vendor", + "Implementation-Title": "the-impl-title", + "Implementation-Version": "the-impl-version", + "Implementation-Vendor": "the-impl-vendor", + }, + }, + }, + { + fixture: "test-fixtures/manifest/extra-info", + expected: pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + "Archiver-Version": "Plexus Archiver", + "Created-By": "Apache Maven 3.6.3", + }, + NamedSections: map[string]map[string]string{ + "thing-1": { + "Built-By": "?", + }, + "1": { + "Build-Jdk": "14.0.1", + "Main-Class": "hello.HelloWorld", + }, + }, + }, + }, + { + fixture: "test-fixtures/manifest/extra-empty-lines", + expected: pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + "Archiver-Version": "Plexus Archiver", + "Created-By": "Apache Maven 3.6.3", + }, + NamedSections: map[string]map[string]string{ + "thing-1": { + "Built-By": "?", + }, + "thing-2": { + "Built-By": "someone!", + }, + "2": { + "Other": "things", + }, + "3": { + "Last": "item", + }, + }, + }, + }, + { + fixture: "test-fixtures/manifest/continuation", + expected: pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + "Plugin-ScmUrl": "https://github.com/jenkinsci/plugin-pom/example-jenkins-plugin", + }, + }, + }, + { + // regression test, we should always keep the full version + fixture: "test-fixtures/manifest/version-with-date", + expected: pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + "Implementation-Version": "1.3 2244 October 5 2005", + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + fixture, err := os.Open(test.fixture) + if err != nil { + t.Fatalf("could not open fixture: %+v", err) + } + + actual, err := parseJavaManifest(test.fixture, fixture) + if err != nil { + t.Fatalf("failed to parse manifest: %+v", err) + } + + diffs := deep.Equal(actual, &test.expected) + if len(diffs) > 0 { + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + + b, err := json.MarshalIndent(actual, "", " ") + if err != nil { + t.Fatalf("can't show results: %+v", err) + } + + t.Errorf("full result: %s", string(b)) + } + }) + } +} + +func TestSelectName(t *testing.T) { + tests := []struct { + desc string + manifest pkg.JavaManifest + archive archiveFilename + expected string + }{ + { + desc: "Get name from Implementation-Title", + archive: archiveFilename{}, + manifest: pkg.JavaManifest{ + Main: map[string]string{ + "Implementation-Title": "maven-wrapper", + }, + }, + expected: "maven-wrapper", + }, + { + desc: "Implementation-Title does not override name from filename", + manifest: pkg.JavaManifest{ + Main: map[string]string{ + "Name": "foo", + "Implementation-Title": "maven-wrapper", + }, + }, + archive: newJavaArchiveFilename("/something/omg.jar"), + expected: "omg", + }, + } + + for _, test := range tests { + t.Run(test.desc, func(t *testing.T) { + result := selectName(&test.manifest, test.archive) + + if result != test.expected { + t.Errorf("mismatch in names: '%s' != '%s'", result, test.expected) + } + }) + } +} + +func TestSelectVersion(t *testing.T) { + tests := []struct { + name string + manifest pkg.JavaManifest + archive archiveFilename + expected string + }{ + { + name: "Get name from Implementation-Version", + archive: archiveFilename{}, + manifest: pkg.JavaManifest{ + Main: map[string]string{ + "Implementation-Version": "1.8.2", + }, + }, + expected: "1.8.2", + }, + { + name: "Implementation-Version takes precedence over Specification-Version", + manifest: pkg.JavaManifest{ + Main: map[string]string{ + "Implementation-Version": "1.8.2", + "Specification-Version": "1.0", + }, + }, + expected: "1.8.2", + }, + { + name: "Implementation-Version found outside the main section", + manifest: pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + "Ant-Version": "Apache Ant 1.8.2", + "Created-By": "1.5.0_22-b03 (Sun Microsystems Inc.)", + }, + NamedSections: map[string]map[string]string{ + "org/apache/tools/ant/taskdefs/optional/": { + "Implementation-Version": "1.8.2", + }, + }, + }, + expected: "1.8.2", + }, + { + name: "Implementation-Version takes precedence over Specification-Version in subsequent section", + manifest: pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + "Ant-Version": "Apache Ant 1.8.2", + "Created-By": "1.5.0_22-b03 (Sun Microsystems Inc.)", + "Specification-Version": "2.0", + }, + NamedSections: map[string]map[string]string{ + "org/apache/tools/ant/taskdefs/optional/": { + "Specification-Version": "1.8", + }, + "some-other-section": { + "Implementation-Version": "1.8.2", + }, + }, + }, + expected: "1.8.2", + }, + { + name: "Implementation-Version takes precedence over Specification-Version in subsequent section", + manifest: pkg.JavaManifest{ + Main: map[string]string{ + "Manifest-Version": "1.0", + "Ant-Version": "Apache Ant 1.8.2", + "Created-By": "1.5.0_22-b03 (Sun Microsystems Inc.)", + }, + NamedSections: map[string]map[string]string{ + "some-other-section": { + "Bundle-Version": "1.11.28", + }, + }, + }, + expected: "1.11.28", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + result := selectVersion(&test.manifest, test.archive) + + assert.Equal(t, test.expected, result) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_properties.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_properties.go new file mode 100644 index 0000000000000000000000000000000000000000..93ccec636b347942fdf56bc05626dfe2ba56d44d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_properties.go @@ -0,0 +1,53 @@ +package java + +import ( + "bufio" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/syft/pkg" + "github.com/mitchellh/mapstructure" +) + +const pomPropertiesGlob = "*pom.properties" + +func parsePomProperties(path string, reader io.Reader) (*pkg.PomProperties, error) { + var props pkg.PomProperties + propMap := make(map[string]string) + scanner := bufio.NewScanner(reader) + for scanner.Scan() { + line := scanner.Text() + + // ignore empty lines and comments + if strings.TrimSpace(line) == "" || strings.HasPrefix(strings.TrimLeft(line, " "), "#") { + continue + } + + idx := strings.IndexAny(line, "=:") + if idx == -1 { + return nil, fmt.Errorf("unable to split pom.properties key-value pairs: %q", line) + } + + key := strings.TrimSpace(line[0:idx]) + value := strings.TrimSpace(line[idx+1:]) + propMap[key] = value + } + + if err := scanner.Err(); err != nil { + return nil, fmt.Errorf("unable to read pom.properties: %w", err) + } + + if err := mapstructure.Decode(propMap, &props); err != nil { + return nil, fmt.Errorf("unable to parse pom.properties: %w", err) + } + + // don't allow for a nil collection, ensure it is empty + if props.Extra == nil { + props.Extra = make(map[string]string) + } + + props.Path = path + + return &props, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_properties_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_properties_test.go new file mode 100644 index 0000000000000000000000000000000000000000..ab7a3d2b2a420c895144d63ee23953c098123b55 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_properties_test.go @@ -0,0 +1,77 @@ +package java + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func TestParseJavaPomProperties(t *testing.T) { + tests := []struct { + expected pkg.PomProperties + }{ + { + expected: pkg.PomProperties{ + Path: "test-fixtures/pom/small.pom.properties", + GroupID: "org.anchore", + ArtifactID: "example-java-app-maven", + Version: "0.1.0", + Extra: map[string]string{}, + }, + }, + { + expected: pkg.PomProperties{ + Path: "test-fixtures/pom/extra.pom.properties", + GroupID: "org.anchore", + ArtifactID: "example-java-app-maven", + Version: "0.1.0", + Name: "something-here", + Extra: map[string]string{ + "another": "thing", + "sweet": "work", + }, + }, + }, + { + expected: pkg.PomProperties{ + Path: "test-fixtures/pom/colon-delimited.pom.properties", + GroupID: "org.anchore", + ArtifactID: "example-java-app-maven", + Version: "0.1.0", + Extra: map[string]string{}, + }, + }, + { + expected: pkg.PomProperties{ + Path: "test-fixtures/pom/equals-delimited-with-colons.pom.properties", + GroupID: "org.anchore", + ArtifactID: "example-java:app-maven", + Version: "0.1.0:something", + Extra: map[string]string{}, + }, + }, + { + expected: pkg.PomProperties{ + Path: "test-fixtures/pom/colon-delimited-with-equals.pom.properties", + GroupID: "org.anchore", + ArtifactID: "example-java=app-maven", + Version: "0.1.0=something", + Extra: map[string]string{}, + }, + }, + } + + for _, test := range tests { + t.Run(test.expected.Path, func(t *testing.T) { + fixture, err := os.Open(test.expected.Path) + assert.NoError(t, err) + + actual, err := parsePomProperties(fixture.Name(), fixture) + assert.NoError(t, err) + + assert.Equal(t, &test.expected, actual) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_xml.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_xml.go new file mode 100644 index 0000000000000000000000000000000000000000..1f7b932b6b43fdf64a3102af76d81caa4cf8d314 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_xml.go @@ -0,0 +1,110 @@ +package java + +import ( + "encoding/xml" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/vifraa/gopom" + "golang.org/x/net/html/charset" +) + +const pomXMLGlob = "*pom.xml" +const pomXMLDirGlob = "**/pom.xml" + +func parserPomXML(path string, content io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + pom, err := decodePomXML(content) + if err != nil { + return nil, nil, err + } + + var pkgs []*pkg.Package + for _, dep := range pom.Dependencies { + p := newPackageFromPom(dep) + if p.Name == "" { + continue + } + + pkgs = append(pkgs, p) + } + + return pkgs, nil, nil +} + +func parsePomXMLProject(path string, reader io.Reader) (*pkg.PomProject, error) { + project, err := decodePomXML(reader) + if err != nil { + return nil, err + } + return newPomProject(path, project), nil +} + +func newPomProject(path string, p gopom.Project) *pkg.PomProject { + return &pkg.PomProject{ + Path: path, + Parent: pomParent(p.Parent), + GroupID: p.GroupID, + ArtifactID: p.ArtifactID, + Version: p.Version, + Name: p.Name, + Description: cleanDescription(p.Description), + URL: p.URL, + } +} + +func newPackageFromPom(dep gopom.Dependency) *pkg.Package { + p := &pkg.Package{ + Name: dep.ArtifactID, + Version: dep.Version, + Language: pkg.Java, + Type: pkg.JavaPkg, // TODO: should we differentiate between packages from jar/war/zip versus packages from a pom.xml that were not installed yet? + MetadataType: pkg.JavaMetadataType, + FoundBy: javaPomCataloger, + Metadata: pkg.JavaMetadata{ + PomProperties: &pkg.PomProperties{ + GroupID: dep.GroupID, + }, + }, + } + + p.Metadata = pkg.JavaMetadata{PURL: packageURL(*p)} + + return p +} + +func decodePomXML(content io.Reader) (project gopom.Project, err error) { + decoder := xml.NewDecoder(content) + // prevent against warnings for "xml: encoding "iso-8859-1" declared but Decoder.CharsetReader is nil" + decoder.CharsetReader = charset.NewReaderLabel + if err := decoder.Decode(&project); err != nil { + return project, fmt.Errorf("unable to unmarshal pom.xml: %w", err) + } + + return project, nil +} + +func pomParent(parent gopom.Parent) (result *pkg.PomParent) { + if parent.ArtifactID != "" || parent.GroupID != "" || parent.Version != "" { + result = &pkg.PomParent{ + GroupID: parent.GroupID, + ArtifactID: parent.ArtifactID, + Version: parent.Version, + } + } + return result +} + +func cleanDescription(original string) (cleaned string) { + descriptionLines := strings.Split(original, "\n") + for _, line := range descriptionLines { + line = strings.TrimSpace(line) + if len(line) == 0 { + continue + } + cleaned += line + " " + } + return strings.TrimSpace(cleaned) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_xml_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_xml_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e314716f477c389b493f9585bad8405f39981ffe --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/parse_pom_xml_test.go @@ -0,0 +1,170 @@ +package java + +import ( + "os" + "testing" + + "github.com/vifraa/gopom" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" +) + +func Test_parserPomXML(t *testing.T) { + tests := []struct { + input string + expected []*pkg.Package + }{ + { + input: "test-fixtures/pom/pom.xml", + expected: []*pkg.Package{ + { + Name: "joda-time", + Version: "2.9.2", + FoundBy: javaPomCataloger, + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + PURL: "pkg:maven/com.joda/joda-time@2.9.2", + }, + }, + { + Name: "junit", + Version: "4.12", + FoundBy: "java-pom-cataloger", + Language: pkg.Java, + Type: pkg.JavaPkg, + MetadataType: pkg.JavaMetadataType, + Metadata: pkg.JavaMetadata{ + PURL: "pkg:maven/junit/junit@4.12", + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.input, func(t *testing.T) { + fixture, err := os.Open(test.input) + assert.NoError(t, err) + + actual, relationships, err := parserPomXML(fixture.Name(), fixture) + assert.NoError(t, err) + assert.Nil(t, relationships) + assert.Equal(t, test.expected, actual) + }) + } +} + +func Test_parsePomXMLProject(t *testing.T) { + tests := []struct { + expected pkg.PomProject + }{ + { + expected: pkg.PomProject{ + Path: "test-fixtures/pom/commons-codec.pom.xml", + Parent: &pkg.PomParent{ + GroupID: "org.apache.commons", + ArtifactID: "commons-parent", + Version: "42", + }, + GroupID: "commons-codec", + ArtifactID: "commons-codec", + Version: "1.11", + Name: "Apache Commons Codec", + Description: "The Apache Commons Codec package contains simple encoder and decoders for various formats such as Base64 and Hexadecimal. In addition to these widely used encoders and decoders, the codec package also maintains a collection of phonetic encoding utilities.", + URL: "http://commons.apache.org/proper/commons-codec/", + }, + }, + } + + for _, test := range tests { + t.Run(test.expected.Path, func(t *testing.T) { + fixture, err := os.Open(test.expected.Path) + assert.NoError(t, err) + + actual, err := parsePomXMLProject(fixture.Name(), fixture) + assert.NoError(t, err) + + assert.Equal(t, &test.expected, actual) + }) + } +} + +func Test_pomParent(t *testing.T) { + tests := []struct { + name string + input gopom.Parent + expected *pkg.PomParent + }{ + { + name: "only group ID", + input: gopom.Parent{ + GroupID: "org.something", + }, + expected: &pkg.PomParent{ + GroupID: "org.something", + }, + }, + { + name: "only artifact ID", + input: gopom.Parent{ + ArtifactID: "something", + }, + expected: &pkg.PomParent{ + ArtifactID: "something", + }, + }, + { + name: "only Version", + input: gopom.Parent{ + Version: "something", + }, + expected: &pkg.PomParent{ + Version: "something", + }, + }, + { + name: "empty", + input: gopom.Parent{}, + expected: nil, + }, + { + name: "unused field", + input: gopom.Parent{ + RelativePath: "something", + }, + expected: nil, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, pomParent(test.input)) + }) + } +} + +func Test_cleanDescription(t *testing.T) { + tests := []struct { + name string + input string + expected string + }{ + { + name: "indent + multiline", + input: ` The Apache Commons Codec package contains simple encoder and decoders for + various formats such as Base64 and Hexadecimal. In addition to these + widely used encoders and decoders, the codec package also maintains a + collection of phonetic encoding utilities.`, + expected: "The Apache Commons Codec package contains simple encoder and decoders for various formats such as Base64 and Hexadecimal. In addition to these widely used encoders and decoders, the codec package also maintains a collection of phonetic encoding utilities.", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, cleanDescription(test.input)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/pom_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/pom_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..753f5d2c3ecf3e057803455d02333fe5ee770764 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/pom_cataloger.go @@ -0,0 +1,17 @@ +package java + +import "github.com/anchore/syft/syft/pkg/cataloger/common" + +const javaPomCataloger = "java-pom-cataloger" + +// NewJavaPomCataloger returns a cataloger capable of parsing +// dependencies from a pom.xml file. +// Pom files list dependencies that maybe not be locally installed yet. +func NewJavaPomCataloger() *common.GenericCataloger { + globParsers := make(map[string]common.ParserFn) + + // java project files + globParsers[pomXMLDirGlob] = parserPomXML + + return common.NewGenericCataloger(nil, globParsers, javaPomCataloger) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/save_archive_to_tmp.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/save_archive_to_tmp.go new file mode 100644 index 0000000000000000000000000000000000000000..e8a4abe4749921e66eb4d63f57a9f70364a670be --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/save_archive_to_tmp.go @@ -0,0 +1,47 @@ +package java + +import ( + "fmt" + "io" + "io/ioutil" + "os" + "path/filepath" + + "github.com/anchore/syft/internal/log" +) + +func saveArchiveToTmp(archiveVirtualPath string, reader io.Reader) (string, string, func(), error) { + name := filepath.Base(archiveVirtualPath) + tempDir, err := ioutil.TempDir("", "syft-archive-contents-") + if err != nil { + return "", "", func() {}, fmt.Errorf("unable to create tempdir for archive processing: %w", err) + } + + cleanupFn := func() { + err = os.RemoveAll(tempDir) + if err != nil { + log.Errorf("unable to cleanup archive tempdir: %+v", err) + } + } + + archivePath := filepath.Join(tempDir, "archive-"+name) + contentDir := filepath.Join(tempDir, "contents") + + err = os.Mkdir(contentDir, 0755) + if err != nil { + return contentDir, "", cleanupFn, fmt.Errorf("unable to create processing tempdir: %w", err) + } + + archiveFile, err := os.Create(archivePath) + if err != nil { + return contentDir, "", cleanupFn, fmt.Errorf("unable to create archive: %w", err) + } + defer archiveFile.Close() + + _, err = io.Copy(archiveFile, reader) + if err != nil { + return contentDir, archivePath, cleanupFn, fmt.Errorf("unable to copy archive: %w", err) + } + + return contentDir, archivePath, cleanupFn, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/tar_wrapped_archive_parser.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/tar_wrapped_archive_parser.go new file mode 100644 index 0000000000000000000000000000000000000000..4d0a6042046d58738d3e229c6b3d84f30d427bdd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/tar_wrapped_archive_parser.go @@ -0,0 +1,68 @@ +package java + +import ( + "fmt" + "io" + + "github.com/anchore/syft/internal/file" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseTarWrappedJavaArchive + +var genericTarGlobs = []string{ + "**/*.tar", + // gzipped tar + "**/*.tar.gz", + "**/*.tgz", + // bzip2 + "**/*.tar.bz", + "**/*.tar.bz2", + "**/*.tbz", + "**/*.tbz2", + // brotli + "**/*.tar.br", + "**/*.tbr", + // lz4 + "**/*.tar.lz4", + "**/*.tlz4", + // sz + "**/*.tar.sz", + "**/*.tsz", + // xz + "**/*.tar.xz", + "**/*.txz", + // zst + "**/*.tar.zst", +} + +// TODO: when the generic archive cataloger is implemented, this should be removed (https://github.com/anchore/syft/issues/246) + +// parseTarWrappedJavaArchive is a parser function for java archive contents contained within arbitrary tar files. +// note: for compressed tars this is an extremely expensive operation and can lead to performance degradation. This is +// due to the fact that there is no central directory header (say as in zip), which means that in order to get +// a file listing within the archive you must decompress the entire archive and seek through all of the entries. +func parseTarWrappedJavaArchive(virtualPath string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + contentPath, archivePath, cleanupFn, err := saveArchiveToTmp(virtualPath, reader) + // note: even on error, we should always run cleanup functions + defer cleanupFn() + if err != nil { + return nil, nil, err + } + + // look for java archives within the tar archive + return discoverPkgsFromTar(virtualPath, archivePath, contentPath) +} + +func discoverPkgsFromTar(virtualPath, archivePath, contentPath string) ([]*pkg.Package, []artifact.Relationship, error) { + openers, err := file.ExtractGlobsFromTarToUniqueTempFile(archivePath, contentPath, archiveFormatGlobs...) + if err != nil { + return nil, nil, fmt.Errorf("unable to extract files from tar: %w", err) + } + + return discoverPkgsFromOpeners(virtualPath, openers, nil) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/tar_wrapped_archive_parser_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/tar_wrapped_archive_parser_test.go new file mode 100644 index 0000000000000000000000000000000000000000..8a1f73162d547e99ff1cc62f7f7027560a04c607 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/tar_wrapped_archive_parser_test.go @@ -0,0 +1,53 @@ +package java + +import ( + "os" + "path" + "testing" + + "github.com/stretchr/testify/require" + + "github.com/stretchr/testify/assert" +) + +func Test_parseTarWrappedJavaArchive(t *testing.T) { + tests := []struct { + fixture string + expected []string + }{ + { + fixture: "test-fixtures/java-builds/packages/example-java-app-maven-0.1.0.tar", + expected: []string{ + "example-java-app-maven", + "joda-time", + }, + }, + { + fixture: "test-fixtures/java-builds/packages/example-java-app-maven-0.1.0.tar.gz", + expected: []string{ + "example-java-app-maven", + "joda-time", + }, + }, + } + for _, test := range tests { + t.Run(path.Base(test.fixture), func(t *testing.T) { + generateJavaBuildFixture(t, test.fixture) + + fixture, err := os.Open(test.fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actualPkgs, _, err := parseTarWrappedJavaArchive(test.fixture, fixture) + require.NoError(t, err) + + var actualNames []string + for _, p := range actualPkgs { + actualNames = append(actualNames, p.Name) + } + + assert.ElementsMatch(t, test.expected, actualNames) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/.gitignore b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..1685225cc769b7b5350ef739f5f31e7aaee26b8e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/.gitignore @@ -0,0 +1,5 @@ +/packages/* +*.fingerprint +# maven when running in a volume may spit out directories like this +**/\?/ +\?/ \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/Makefile b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..70710b8a57a71ce7562305107936ff465dd30505 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/Makefile @@ -0,0 +1,69 @@ +PKGSDIR=packages + +ifndef PKGSDIR + $(error PKGSDIR is not set) +endif + +all: jars archives + +clean: clean-examples + rm -f $(PKGSDIR)/* + +clean-examples: clean-gradle clean-maven clean-jenkins clean-nestedjar + +.PHONY: maven gradle clean clean-gradle clean-maven clean-jenkins clean-examples clean-nestedjar jars archives + +jars: $(PKGSDIR)/example-java-app-maven-0.1.0.jar $(PKGSDIR)/example-java-app-gradle-0.1.0.jar $(PKGSDIR)/example-jenkins-plugin.hpi $(PKGSDIR)/spring-boot-0.0.1-SNAPSHOT.jar + +archives: $(PKGSDIR)/example-java-app-maven-0.1.0.zip $(PKGSDIR)/example-java-app-maven-0.1.0.tar $(PKGSDIR)/example-java-app-maven-0.1.0.tar.gz + +# jars within archives... + +$(PKGSDIR)/example-java-app-maven-0.1.0.zip: $(PKGSDIR)/example-java-app-maven-0.1.0.jar + zip $(PKGSDIR)/example-java-app-maven-0.1.0.zip $(PKGSDIR)/example-java-app-maven-0.1.0.jar + +$(PKGSDIR)/example-java-app-maven-0.1.0.tar: $(PKGSDIR)/example-java-app-maven-0.1.0.jar + tar -cvf $(PKGSDIR)/example-java-app-maven-0.1.0.tar $(PKGSDIR)/example-java-app-maven-0.1.0.jar + +$(PKGSDIR)/example-java-app-maven-0.1.0.tar.gz: $(PKGSDIR)/example-java-app-maven-0.1.0.jar + tar -czvf $(PKGSDIR)/example-java-app-maven-0.1.0.tar.gz $(PKGSDIR)/example-java-app-maven-0.1.0.jar + +# Nested jar... + +$(PKGSDIR)/spring-boot-0.0.1-SNAPSHOT.jar: + ./build-example-sb-app-nestedjar.sh $(PKGSDIR) + +clean-nestedjar: + rm -rf example-sb-app/target + +# Maven... +$(PKGSDIR)/example-java-app-maven-0.1.0.jar: + ./build-example-java-app-maven.sh $(PKGSDIR) + +clean-maven: + rm -rf example-java-app/\? \ + example-java-app/target \ + example-java-app/dependency-reduced-pom.xml + +# Gradle... +$(PKGSDIR)/example-java-app-gradle-0.1.0.jar: + ./build-example-java-app-gradle.sh $(PKGSDIR) + +clean-gradle: + rm -rf example-java-app/.gradle \ + example-java-app/build + +# Jenkins plugin +$(PKGSDIR)/example-jenkins-plugin.hpi , $(PKGSDIR)/example-jenkins-plugin.jar: + ./build-example-jenkins-plugin.sh $(PKGSDIR) + +clean-jenkins: + rm -rf example-jenkins-plugin/target \ + example-jenkins-plugin/dependency-reduced-pom.xml \ + example-jenkins-plugin/*.exploding + +# we need a way to determine if CI should bust the test cache based on the source material +$(PKGSDIR).fingerprint: clean-examples + mkdir -p $(PKGSDIR) + find example-* -type f -exec sha256sum {} \; | sort | tee /dev/stderr | tee $(PKGSDIR).fingerprint + sha256sum $(PKGSDIR).fingerprint diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-java-app-gradle.sh b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-java-app-gradle.sh new file mode 100755 index 0000000000000000000000000000000000000000..345542c93ee6e4b1f25e524215c5c5a8fd5391f9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-java-app-gradle.sh @@ -0,0 +1,19 @@ +#!/usr/bin/env bash +set -uxe + +# note: this can be easily done in a 1-liner, however circle CI does NOT allow volume mounts from the host in docker executors (since they are on remote hosts, where the host files are inaccessible) + +PKGSDIR=$1 +CTRID=$(docker create -u "$(id -u):$(id -g)" -v /example-java-app -w /example-java-app gradle:6.8.3-jdk gradle build) + +function cleanup() { + docker rm "${CTRID}" +} + +trap cleanup EXIT +set +e + +docker cp "$(pwd)/example-java-app" "${CTRID}:/" +docker start -a "${CTRID}" +mkdir -p "$PKGSDIR" +docker cp "${CTRID}:/example-java-app/build/libs/example-java-app-gradle-0.1.0.jar" "$PKGSDIR" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-java-app-maven.sh b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-java-app-maven.sh new file mode 100755 index 0000000000000000000000000000000000000000..2521a37f29482d4a97f2fec0785ddd2fd624fe55 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-java-app-maven.sh @@ -0,0 +1,19 @@ +#!/usr/bin/env bash +set -uxe + +# note: this can be easily done in a 1-liner, however circle CI does NOT allow volume mounts from the host in docker executors (since they are on remote hosts, where the host files are inaccessible) + +PKGSDIR=$1 +CTRID=$(docker create -u "$(id -u):$(id -g)" -e MAVEN_CONFIG=/tmp/.m2 -v /example-java-app -w /example-java-app maven:3.8.6-openjdk-18 mvn -Duser.home=/tmp -DskipTests package) + +function cleanup() { + docker rm "${CTRID}" +} + +trap cleanup EXIT +set +e + +docker cp "$(pwd)/example-java-app" "${CTRID}:/" +docker start -a "${CTRID}" +mkdir -p "$PKGSDIR" +docker cp "${CTRID}:/example-java-app/target/example-java-app-maven-0.1.0.jar" "$PKGSDIR" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-jenkins-plugin.sh b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-jenkins-plugin.sh new file mode 100755 index 0000000000000000000000000000000000000000..3c24b582a645f77d3861b1274f4ddf276561bb05 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-jenkins-plugin.sh @@ -0,0 +1,20 @@ +#!/usr/bin/env bash +set -uxe + +# note: this can be easily done in a 1-liner, however circle CI does NOT allow volume mounts from the host in docker executors (since they are on remote hosts, where the host files are inaccessible) + +PKGSDIR=$1 +CTRID=$(docker create -u "$(id -u):$(id -g)" -e MAVEN_CONFIG=/tmp/.m2 -v /example-jenkins-plugin -w /example-jenkins-plugin maven:3.8.6-openjdk-18 mvn -Duser.home=/tmp -DskipTests package) + +function cleanup() { + docker rm "${CTRID}" +} + +trap cleanup EXIT +set +e + +docker cp "$(pwd)/example-jenkins-plugin" "${CTRID}:/" +docker start -a "${CTRID}" +mkdir -p "$PKGSDIR" +docker cp "${CTRID}:/example-jenkins-plugin/target/example-jenkins-plugin.hpi" "$PKGSDIR" +docker cp "${CTRID}:/example-jenkins-plugin/target/example-jenkins-plugin.jar" "$PKGSDIR" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-sb-app-nestedjar.sh b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-sb-app-nestedjar.sh new file mode 100755 index 0000000000000000000000000000000000000000..80dfbeb129f853325f2aa131356cfa0729620b28 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/build-example-sb-app-nestedjar.sh @@ -0,0 +1,19 @@ +#!/usr/bin/env bash +set -uxe + +# note: this can be easily done in a 1-liner, however circle CI does NOT allow volume mounts from the host in docker executors (since they are on remote hosts, where the host files are inaccessible) + +PKGSDIR=$1 +CTRID=$(docker create -u "$(id -u):$(id -g)" -e MAVEN_CONFIG=/tmp/.m2 -v /example-sb-app -w /example-sb-app maven:3.8.6-openjdk-18 mvn -Duser.home=/tmp -DskipTests package spring-boot:repackage) + +function cleanup() { + docker rm "${CTRID}" +} + +trap cleanup EXIT +set +e + +docker cp "$(pwd)/example-sb-app" "${CTRID}:/" +docker start -a "${CTRID}" +mkdir -p "$PKGSDIR" +docker cp "${CTRID}:/example-sb-app/target/spring-boot-0.0.1-SNAPSHOT.jar" "$PKGSDIR" diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/.gitignore b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..a8a4d8556274a630aba0aa604111a4bb42950380 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/.gitignore @@ -0,0 +1,6 @@ +# maven build creates this when in a container volume +/?/ +/.gradle/ +/build/ +target/ +dependency-reduced-pom.xml diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/build.gradle b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/build.gradle new file mode 100644 index 0000000000000000000000000000000000000000..0dac0e13b0a5bbfa415f7f6334eebf070869f8ae --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/build.gradle @@ -0,0 +1,31 @@ +apply plugin: 'java' +apply plugin: 'eclipse' +apply plugin: 'application' + +mainClassName = 'hello.HelloWorld' + +// tag::repositories[] +repositories { + mavenCentral() +} +// end::repositories[] + +// tag::jar[] +jar { + baseName = 'example-java-app-gradle' + version = '0.1.0' +} +// end::jar[] + +// tag::dependencies[] +sourceCompatibility = 1.8 +targetCompatibility = 1.8 + +dependencies { + compile "joda-time:joda-time:2.2" + testCompile "junit:junit:4.12" +} +// end::dependencies[] + +// tag::wrapper[] +// end::wrapper[] \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/pom.xml b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/pom.xml new file mode 100644 index 0000000000000000000000000000000000000000..4ab76d1d914b056b5854312c5b2f01b57ddd365c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/pom.xml @@ -0,0 +1,59 @@ + + + 4.0.0 + + org.anchore + example-java-app-maven + jar + 0.1.0 + + + 1.8 + 1.8 + + + + + + joda-time + joda-time + 2.9.2 + + + + + junit + junit + 4.12 + test + + + + + + + + org.apache.maven.plugins + maven-shade-plugin + 2.1 + + + package + + shade + + + + + hello.HelloWorld + + + + + + + + + + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/src/main/java/hello/Greeter.java b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/src/main/java/hello/Greeter.java new file mode 100644 index 0000000000000000000000000000000000000000..74eb8d441737d03b8623068e3564c4c7b6c02c40 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/src/main/java/hello/Greeter.java @@ -0,0 +1,7 @@ +package hello; + +public class Greeter { + public String sayHello() { + return "Hello world!"; + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/src/main/java/hello/HelloWorld.java b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/src/main/java/hello/HelloWorld.java new file mode 100644 index 0000000000000000000000000000000000000000..d9e61fe5d534fd51d0783d687051427f2363d275 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-java-app/src/main/java/hello/HelloWorld.java @@ -0,0 +1,13 @@ +package hello; + +import org.joda.time.LocalTime; + +public class HelloWorld { + public static void main(String[] args) { + LocalTime currentTime = new LocalTime(); + System.out.println("The current local time is: " + currentTime); + + Greeter greeter = new Greeter(); + System.out.println(greeter.sayHello()); + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/pom.xml b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/pom.xml new file mode 100644 index 0000000000000000000000000000000000000000..e1abe106b96db5f1a08dceb4ecc52834b48938c5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/pom.xml @@ -0,0 +1,100 @@ + + + 4.0.0 + + org.jenkins-ci.plugins + plugin + 4.46 + + + io.jenkins.plugins + example-jenkins-plugin + 1.0-SNAPSHOT + hpi + + + 2.204 + 8 + + + Example Jenkins Plugin + + + + MIT License + https://opensource.org/licenses/MIT + + + + + + + io.jenkins.tools.bom + bom-2.164.x + 3 + import + pom + + + + + + org.jenkins-ci.plugins + structs + + + org.jenkins-ci.plugins.workflow + workflow-cps + test + + + org.jenkins-ci.plugins.workflow + workflow-job + test + + + org.jenkins-ci.plugins.workflow + workflow-basic-steps + test + + + org.jenkins-ci.plugins.workflow + workflow-durable-task-step + test + + + + + + + + + repo.jenkins-ci.org + https://repo.jenkins-ci.org/public/ + + + + + repo.jenkins-ci.org + https://repo.jenkins-ci.org/public/ + + + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/java/io/jenkins/plugins/sample/HelloWorldBuilder.java b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/java/io/jenkins/plugins/sample/HelloWorldBuilder.java new file mode 100644 index 0000000000000000000000000000000000000000..ec7bbc62d72b88803e6e3a4f9303020ad6cf67d8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/java/io/jenkins/plugins/sample/HelloWorldBuilder.java @@ -0,0 +1,81 @@ +package io.jenkins.plugins.sample; + +import hudson.Launcher; +import hudson.Extension; +import hudson.FilePath; +import hudson.util.FormValidation; +import hudson.model.AbstractProject; +import hudson.model.Run; +import hudson.model.TaskListener; +import hudson.tasks.Builder; +import hudson.tasks.BuildStepDescriptor; +import org.kohsuke.stapler.DataBoundConstructor; +import org.kohsuke.stapler.QueryParameter; + +import javax.servlet.ServletException; +import java.io.IOException; +import jenkins.tasks.SimpleBuildStep; +import org.jenkinsci.Symbol; +import org.kohsuke.stapler.DataBoundSetter; + +public class HelloWorldBuilder extends Builder implements SimpleBuildStep { + + private final String name; + private boolean useFrench; + + @DataBoundConstructor + public HelloWorldBuilder(String name) { + this.name = name; + } + + public String getName() { + return name; + } + + public boolean isUseFrench() { + return useFrench; + } + + @DataBoundSetter + public void setUseFrench(boolean useFrench) { + this.useFrench = useFrench; + } + + @Override + public void perform(Run run, FilePath workspace, Launcher launcher, TaskListener listener) throws InterruptedException, IOException { + if (useFrench) { + listener.getLogger().println("Bonjour, " + name + "!"); + } else { + listener.getLogger().println("Hello, " + name + "!"); + } + } + + @Symbol("greet") + @Extension + public static final class DescriptorImpl extends BuildStepDescriptor { + + public FormValidation doCheckName(@QueryParameter String value, @QueryParameter boolean useFrench) + throws IOException, ServletException { + if (value.length() == 0) + return FormValidation.error(Messages.HelloWorldBuilder_DescriptorImpl_errors_missingName()); + if (value.length() < 4) + return FormValidation.warning(Messages.HelloWorldBuilder_DescriptorImpl_warnings_tooShort()); + if (!useFrench && value.matches(".*[éáàç].*")) { + return FormValidation.warning(Messages.HelloWorldBuilder_DescriptorImpl_warnings_reallyFrench()); + } + return FormValidation.ok(); + } + + @Override + public boolean isApplicable(Class aClass) { + return true; + } + + @Override + public String getDisplayName() { + return Messages.HelloWorldBuilder_DescriptorImpl_DisplayName(); + } + + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/index.jelly b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/index.jelly new file mode 100644 index 0000000000000000000000000000000000000000..4fd118507b8c0f061d824d72a510e5c559e68522 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/index.jelly @@ -0,0 +1,3 @@ + +
+
diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config.jelly b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config.jelly new file mode 100644 index 0000000000000000000000000000000000000000..e97fba056899fb02670f7720a6ab6befdf6b334d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config.jelly @@ -0,0 +1,12 @@ + + + + + + + + + + + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config.properties new file mode 100644 index 0000000000000000000000000000000000000000..7ebd98b2e0d4c80d11f853b3a97d5f4c3366e3d1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config.properties @@ -0,0 +1,3 @@ +Name=Name +French=French +FrenchDescr=Check if we should say hello in French \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config_fr.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config_fr.properties new file mode 100644 index 0000000000000000000000000000000000000000..393218bd1c13464f05985522a2129c0064d199f7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/config_fr.properties @@ -0,0 +1,3 @@ +Name=Nom +French=Fran\u00e7ais +FrenchDescr=V\u00e9rifie qu'on dit bien hello en fran\u00e7ais diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-name.html b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-name.html new file mode 100644 index 0000000000000000000000000000000000000000..e7122106617224bc0ca4e06b1611117b36a72d91 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-name.html @@ -0,0 +1,3 @@ +
+ Your name. +
diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-name_fr.html b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-name_fr.html new file mode 100644 index 0000000000000000000000000000000000000000..3c49c7ac14e92c2d4bc2bd68e8fd6d6985f1066b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-name_fr.html @@ -0,0 +1,3 @@ +
+ Votre nom. +
diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-useFrench.html b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-useFrench.html new file mode 100644 index 0000000000000000000000000000000000000000..b4eadd6cf28d4b26675192822b32243ee2a83f7e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-useFrench.html @@ -0,0 +1,3 @@ +
+ Use French? +
diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-useFrench_fr.html b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-useFrench_fr.html new file mode 100644 index 0000000000000000000000000000000000000000..3f9137625c3e92c691b0b1da5c8e7ad5de88361c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/HelloWorldBuilder/help-useFrench_fr.html @@ -0,0 +1,3 @@ +
+ Utiliser le français ? +
diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/Messages.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/Messages.properties new file mode 100644 index 0000000000000000000000000000000000000000..eb02a09409262c934198616ffc6faded367b848c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/Messages.properties @@ -0,0 +1,5 @@ +HelloWorldBuilder.DescriptorImpl.errors.missingName=Please set a name +HelloWorldBuilder.DescriptorImpl.warnings.tooShort=Isn't the name too short? +HelloWorldBuilder.DescriptorImpl.warnings.reallyFrench=Are you actually French? + +HelloWorldBuilder.DescriptorImpl.DisplayName=Say hello world \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/Messages_fr.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/Messages_fr.properties new file mode 100644 index 0000000000000000000000000000000000000000..a6a510c8f3c2525b882785f5b1e0904dfb8998d0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-jenkins-plugin/src/main/resources/io/jenkins/plugins/sample/Messages_fr.properties @@ -0,0 +1,5 @@ +HelloWorldBuilder.DescriptorImpl.errors.missingName=Veuillez saisir un nom +HelloWorldBuilder.DescriptorImpl.warnings.tooShort=Le nom n'est-il pas trop court ? +HelloWorldBuilder.DescriptorImpl.warnings.reallyFrench=\u00CAtes vous vraiment fran\u00E7ais ? + +HelloWorldBuilder.DescriptorImpl.DisplayName=Dis hello world diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/.gitignore b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..a8a4d8556274a630aba0aa604111a4bb42950380 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/.gitignore @@ -0,0 +1,6 @@ +# maven build creates this when in a container volume +/?/ +/.gradle/ +/build/ +target/ +dependency-reduced-pom.xml diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/pom.xml b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/pom.xml new file mode 100644 index 0000000000000000000000000000000000000000..92128cca9ece1ed3ee6b1b90f816cb0662c40814 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/pom.xml @@ -0,0 +1,73 @@ + + + 4.0.0 + + org.springframework.boot + spring-boot-starter-parent + 2.2.2.RELEASE + + + com.example + spring-boot + 0.0.1-SNAPSHOT + spring-boot + Demo project for Spring Boot + + + 1.8 + + + + + org.springframework.boot + spring-boot-starter-web + + + + + org.springframework.boot + spring-boot-starter-actuator + + + + + + org.springframework.boot + spring-boot-starter-test + test + + + org.junit.vintage + junit-vintage-engine + + + + + + + + + + + org.springframework.boot + spring-boot-maven-plugin + 2.1.5.RELEASE + + ${start-class} + ZIP + + true + + + + + repackage + + + + + + + + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/main/java/com/example/springboot/Application.java b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/main/java/com/example/springboot/Application.java new file mode 100644 index 0000000000000000000000000000000000000000..42b36896eae69e5b333599b762f98af22670255d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/main/java/com/example/springboot/Application.java @@ -0,0 +1,33 @@ +package com.example.springboot; + +import java.util.Arrays; + +import org.springframework.boot.CommandLineRunner; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.context.ApplicationContext; +import org.springframework.context.annotation.Bean; + +@SpringBootApplication +public class Application { + + public static void main(String[] args) { + SpringApplication.run(Application.class, args); + } + + @Bean + public CommandLineRunner commandLineRunner(ApplicationContext ctx) { + return args -> { + + System.out.println("Let's inspect the beans provided by Spring Boot:"); + + String[] beanNames = ctx.getBeanDefinitionNames(); + Arrays.sort(beanNames); + for (String beanName : beanNames) { + System.out.println(beanName); + } + + }; + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/main/java/com/example/springboot/HelloController.java b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/main/java/com/example/springboot/HelloController.java new file mode 100644 index 0000000000000000000000000000000000000000..3a853ff7b3e9e33c56ef3187a6be59c7824e49ee --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/main/java/com/example/springboot/HelloController.java @@ -0,0 +1,14 @@ +package com.example.springboot; + +import org.springframework.web.bind.annotation.RestController; +import org.springframework.web.bind.annotation.RequestMapping; + +@RestController +public class HelloController { + + @RequestMapping("/") + public String index() { + return "Greetings from Spring Boot!"; + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/test/java/com/example/springboot/HelloControllerIT.java b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/test/java/com/example/springboot/HelloControllerIT.java new file mode 100644 index 0000000000000000000000000000000000000000..055f54a7ae0c836862ca8674fdc18206a255ce53 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/test/java/com/example/springboot/HelloControllerIT.java @@ -0,0 +1,38 @@ +package com.example.springboot; + +import static org.assertj.core.api.Assertions.*; + +import java.net.URL; + +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.test.web.client.TestRestTemplate; +import org.springframework.boot.web.server.LocalServerPort; +import org.springframework.http.ResponseEntity; + +@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) +public class HelloControllerIT { + + @LocalServerPort + private int port; + + private URL base; + + @Autowired + private TestRestTemplate template; + + @BeforeEach + public void setUp() throws Exception { + this.base = new URL("http://localhost:" + port + "/"); + } + + @Test + public void getHello() throws Exception { + ResponseEntity response = template.getForEntity(base.toString(), + String.class); + assertThat(response.getBody()).isEqualTo("Greetings from Spring Boot!"); + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/test/java/com/example/springboot/HelloControllerTest.java b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/test/java/com/example/springboot/HelloControllerTest.java new file mode 100644 index 0000000000000000000000000000000000000000..81262f4c1d5a71b71a7f5e1fe7692b17a4d8fb45 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/java-builds/example-sb-app/src/test/java/com/example/springboot/HelloControllerTest.java @@ -0,0 +1,29 @@ +package com.example.springboot; + +import static org.hamcrest.Matchers.equalTo; +import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.content; +import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status; + +import org.junit.jupiter.api.Test; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.http.MediaType; +import org.springframework.test.web.servlet.MockMvc; +import org.springframework.test.web.servlet.request.MockMvcRequestBuilders; + +@SpringBootTest +@AutoConfigureMockMvc +public class HelloControllerTest { + + @Autowired + private MockMvc mvc; + + @Test + public void getHello() throws Exception { + mvc.perform(MockMvcRequestBuilders.get("/").accept(MediaType.APPLICATION_JSON)) + .andExpect(status().isOk()) + .andExpect(content().string(equalTo("Greetings from Spring Boot!"))); + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/continuation b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/continuation new file mode 100644 index 0000000000000000000000000000000000000000..7c80313a65d1d3709d01d42290055ca14d59c206 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/continuation @@ -0,0 +1,4 @@ +Manifest-Version: 1.0 +Plugin-ScmUrl: https://github.com/jenkinsci/plugin-pom/example-jenkins + -plugin + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/extra-empty-lines b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/extra-empty-lines new file mode 100644 index 0000000000000000000000000000000000000000..4f89731ff09c47c613b914710bdfa23284b780f8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/extra-empty-lines @@ -0,0 +1,22 @@ +Manifest-Version: 1.0 +Archiver-Version: Plexus Archiver +Created-By: Apache Maven 3.6.3 + + +Name: thing-1 +Built-By: ? + +. + +Name: thing-2 +Built-By: someone! + + + : + +Other: things +junk + +: + +Last: item \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/extra-info b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/extra-info new file mode 100644 index 0000000000000000000000000000000000000000..c1fa40e5c6029f9eecd0478fc1bf2c076152a77d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/extra-info @@ -0,0 +1,9 @@ +Manifest-Version: 1.0 +Archiver-Version: Plexus Archiver +Created-By: Apache Maven 3.6.3 + +Name: thing-1 +Built-By: ? + +Build-Jdk: 14.0.1 +Main-Class: hello.HelloWorld diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/small b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/small new file mode 100644 index 0000000000000000000000000000000000000000..59499bce4a2bd51cba227b7c00fcf745b19c95a4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/small @@ -0,0 +1,2 @@ +Manifest-Version: 1.0 + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/standard-info b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/standard-info new file mode 100644 index 0000000000000000000000000000000000000000..2a52186a19f6bd717e9a7f5791b4b95fca714743 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/standard-info @@ -0,0 +1,9 @@ +Manifest-Version: 1.0 +Name: the-best-name +Specification-Title: the-spec-title +Specification-Vendor: the-spec-vendor +Specification-Version: the-spec-version +Implementation-Title: the-impl-title +Implementation-Vendor: the-impl-vendor +Implementation-Version: the-impl-version + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/version-with-date b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/version-with-date new file mode 100644 index 0000000000000000000000000000000000000000..2baeeecbdf4a7e38866e4ac228dfc4894a1a6f23 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/manifest/version-with-date @@ -0,0 +1,2 @@ +Manifest-Version: 1.0 +Implementation-Version: 1.3 2244 October 5 2005 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/colon-delimited-with-equals.pom.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/colon-delimited-with-equals.pom.properties new file mode 100644 index 0000000000000000000000000000000000000000..68721e96bb9a34a369ce45d812edd30625d510d0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/colon-delimited-with-equals.pom.properties @@ -0,0 +1,5 @@ +#Generated by Maven +#Tue Jul 07 18:59:56 GMT 2020 +groupId:org.anchore +artifactId: example-java=app-maven +version: 0.1.0=something \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/colon-delimited.pom.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/colon-delimited.pom.properties new file mode 100644 index 0000000000000000000000000000000000000000..a32d166e6c6f96bb7deeee56f754413be6c4e288 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/colon-delimited.pom.properties @@ -0,0 +1,5 @@ +#Generated by Maven +#Tue Jul 07 18:59:56 GMT 2020 +groupId:org.anchore +artifactId: example-java-app-maven +version: 0.1.0 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/commons-codec.pom.xml b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/commons-codec.pom.xml new file mode 100644 index 0000000000000000000000000000000000000000..c9299e195aeffb7e6bae6977e68df6d35901ed35 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/commons-codec.pom.xml @@ -0,0 +1,410 @@ + + + + + 4.0.0 + + org.apache.commons + commons-parent + 42 + + commons-codec + commons-codec + + 1.11 + Apache Commons Codec + 2002 + + The Apache Commons Codec package contains simple encoder and decoders for + various formats such as Base64 and Hexadecimal. In addition to these + widely used encoders and decoders, the codec package also maintains a + collection of phonetic encoding utilities. + + + 3.0.0 + + http://commons.apache.org/proper/commons-codec/ + + jira + http://issues.apache.org/jira/browse/CODEC + + + scm:svn:http://svn.apache.org/repos/asf/commons/proper/codec/trunk + scm:svn:https://svn.apache.org/repos/asf/commons/proper/codec/trunk + http://svn.apache.org/viewvc/commons/proper/codec/trunk + + + + stagingSite + Apache Staging Website + ${commons.deployment.protocol}://people.apache.org/www/commons.apache.org/${commons.componentid}/ + + + + + Henri Yandell + bayard + bayard@apache.org + + + Tim OBrien + tobrien + tobrien@apache.org + -6 + + + Scott Sanders + sanders + sanders@totalsync.com + + + Rodney Waldhoff + rwaldhoff + rwaldhoff@apache.org + + + Daniel Rall + dlr + dlr@finemaltcoding.com + + + Jon S. Stevens + jon + jon@collab.net + + + Gary Gregory + ggregory + ggregory@apache.org + http://www.garygregory.com + -8 + + + David Graham + dgraham + dgraham@apache.org + + + Julius Davies + julius + julius@apache.org + http://juliusdavies.ca/ + -8 + + + Thomas Neidhart + tn + tn@apache.org + + + + + Christopher O'Brien + siege@preoccupied.net + + hex + md5 + architecture + + + + Martin Redington + + Representing xml-rpc + + + + Jeffery Dever + + Representing http-client + + + + Steve Zimmermann + steve.zimmermann@heii.com + + Documentation + + + + Benjamin Walstrum + ben@walstrum.com + + + Oleg Kalnichevski + oleg@ural.ru + + Representing http-client + + + + Dave Dribin + apache@dave.dribin.org + + DigestUtil + + + + Alex Karasulu + aok123 at bellsouth.net + + Submitted Binary class and test + + + + Matthew Inger + mattinger at yahoo.com + + Submitted DIFFERENCE algorithm for Soundex and RefinedSoundex + + + + Jochen Wiedmann + jochen@apache.org + + Base64 code [CODEC-69] + + + + Sebastian Bazley + sebb@apache.org + + Streaming Base64 + + + + Matthew Pocock + turingatemyhamster@gmail.com + + Beider-Morse phonetic matching + + + + Colm Rice + colm_rice at hotmail dot com + + Submitted Match Rating Approach (MRA) phonetic encoder and tests [CODEC-161] + + + + + + + junit + junit + 4.12 + test + + + org.apache.commons + commons-lang3 + 3.5 + test + + + + 1.6 + 1.6 + codec + org.apache.commons.codec + 1.11 + + RC1 + CODEC + 12310464 + + UTF-8 + UTF-8 + UTF-8 + ${basedir}/LICENSE-header.txt + 2.17 + 2.8 + + + + + + org.apache.maven.plugins + maven-scm-publish-plugin + ${commons.scm-publish.version} + + + archive** + + + + + + + + + org.apache.rat + apache-rat-plugin + + + src/site/resources/.htaccess + + + + + + + maven-jar-plugin + + + + + ${commons.module.name} + + + + + + org.apache.maven.plugins + maven-surefire-plugin + + + **/*AbstractTest.java + **/*PerformanceTest.java + + + + + org.apache.maven.plugins + maven-assembly-plugin + + + src/assembly/bin.xml + src/assembly/src.xml + + gnu + + + + + org.apache.maven.plugins + maven-checkstyle-plugin + ${checkstyle.version} + + ${basedir}/checkstyle.xml + false + ${basedir}/LICENSE-header.txt + + + + + + + + org.apache.maven.plugins + maven-checkstyle-plugin + ${checkstyle.version} + + ${basedir}/checkstyle.xml + false + ${basedir}/LICENSE-header.txt + + + + + + checkstyle + + + + + + org.apache.maven.plugins + maven-pmd-plugin + 3.8 + + ${maven.compiler.target} + true + + ${basedir}/pmd.xml + + + + + org.codehaus.mojo + findbugs-maven-plugin + ${commons.findbugs.version} + + + org.codehaus.mojo + taglist-maven-plugin + 2.4 + + + TODO + NOPMD + NOTE + + + + + org.codehaus.mojo + javancss-maven-plugin + 2.1 + + + org.apache.rat + apache-rat-plugin + + + src/site/resources/.htaccess + + + + + + + + travis + + + env.TRAVIS + true + + + + + + org.codehaus.mojo + cobertura-maven-plugin + ${commons.cobertura.version} + + + xml + + + + + org.eluder.coveralls + coveralls-maven-plugin + 4.3.0 + + + + + + \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/equals-delimited-with-colons.pom.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/equals-delimited-with-colons.pom.properties new file mode 100644 index 0000000000000000000000000000000000000000..144b78b8122d1f36730599e69af840dcdc8d56d8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/equals-delimited-with-colons.pom.properties @@ -0,0 +1,5 @@ +#Generated by Maven +#Tue Jul 07 18:59:56 GMT 2020 +groupId=org.anchore +artifactId= example-java:app-maven +version= 0.1.0:something \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/extra.pom.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/extra.pom.properties new file mode 100644 index 0000000000000000000000000000000000000000..2f5e714920ebab66a3026a3104135e771b868f6c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/extra.pom.properties @@ -0,0 +1,8 @@ +#Generated by Maven +#Tue Jul 07 18:59:56 GMT 2020 +groupId=org.anchore +artifactId=example-java-app-maven +version=0.1.0 +name=something-here +another=thing +sweet=work diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/pom.xml b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/pom.xml new file mode 100644 index 0000000000000000000000000000000000000000..6dec1a75aa07cec1ff16a4c774a9ac5a24bd8779 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/pom.xml @@ -0,0 +1,58 @@ + + + 4.0.0 + + org.anchore + example-java-app-maven + jar + 0.1.0 + + + 1.8 + 1.8 + + + + + + com.joda + joda-time + 2.9.2 + + + + + junit + junit + 4.12 + test + + + + + + + + org.apache.maven.plugins + maven-shade-plugin + 2.1 + + + package + + shade + + + + + hello.HelloWorld + + + + + + + + + + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/small.pom.properties b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/small.pom.properties new file mode 100644 index 0000000000000000000000000000000000000000..93ccac17fe7ca8602942c3fb8136a2fe398dc603 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/test-fixtures/pom/small.pom.properties @@ -0,0 +1,5 @@ +#Generated by Maven +#Tue Jul 07 18:59:56 GMT 2020 +groupId=org.anchore +artifactId= example-java-app-maven +version= 0.1.0 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/zip_wrapped_archive_parser.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/zip_wrapped_archive_parser.go new file mode 100644 index 0000000000000000000000000000000000000000..6e32ed42881688fb1b64639c0a89050d76c6cc7c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/zip_wrapped_archive_parser.go @@ -0,0 +1,43 @@ +package java + +import ( + "fmt" + "io" + + "github.com/anchore/syft/internal/file" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseZipWrappedJavaArchive + +var genericZipGlobs = []string{ + "**/*.zip", +} + +// TODO: when the generic archive cataloger is implemented, this should be removed (https://github.com/anchore/syft/issues/246) + +// parseZipWrappedJavaArchive is a parser function for java archive contents contained within arbitrary zip files. +func parseZipWrappedJavaArchive(virtualPath string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + contentPath, archivePath, cleanupFn, err := saveArchiveToTmp(virtualPath, reader) + // note: even on error, we should always run cleanup functions + defer cleanupFn() + if err != nil { + return nil, nil, err + } + + // we use our zip helper functions instead of that from the archiver package or the standard lib. Why? These helper + // functions support zips with shell scripts prepended to the file. Specifically, the helpers use the central + // header at the end of the file to determine where the beginning of the zip payload is (unlike the standard lib + // or archiver). + fileManifest, err := file.NewZipFileManifest(archivePath) + if err != nil { + return nil, nil, fmt.Errorf("unable to read files from java archive: %w", err) + } + + // look for java archives within the zip archive + return discoverPkgsFromZip(virtualPath, archivePath, contentPath, fileManifest, nil) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/zip_wrapped_archive_parser_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/zip_wrapped_archive_parser_test.go new file mode 100644 index 0000000000000000000000000000000000000000..5f062fd2584cb5a4aa59d17d6e2b9180b5a7fcb2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/java/zip_wrapped_archive_parser_test.go @@ -0,0 +1,45 @@ +package java + +import ( + "os" + "path" + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func Test_parseZipWrappedJavaArchive(t *testing.T) { + tests := []struct { + fixture string + expected []string + }{ + { + fixture: "test-fixtures/java-builds/packages/example-java-app-maven-0.1.0.zip", + expected: []string{ + "example-java-app-maven", + "joda-time", + }, + }, + } + for _, test := range tests { + t.Run(path.Base(test.fixture), func(t *testing.T) { + generateJavaBuildFixture(t, test.fixture) + + fixture, err := os.Open(test.fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actualPkgs, _, err := parseZipWrappedJavaArchive(test.fixture, fixture) + require.NoError(t, err) + + var actualNames []string + for _, p := range actualPkgs { + actualNames = append(actualNames, p.Name) + } + + assert.ElementsMatch(t, test.expected, actualNames) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..cefbaccb5703e0f5f31fdeb5b6dc971f765bbc5d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/cataloger.go @@ -0,0 +1,84 @@ +/* +Package javascript provides a concrete Cataloger implementation for JavaScript ecosystem files (yarn and npm). +*/ +package javascript + +import ( + "encoding/json" + "io" + "path" + "strings" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "github.com/anchore/syft/syft/source" +) + +// NewJavascriptPackageCataloger returns a new JavaScript cataloger object based on detection of npm based packages. +func NewJavascriptPackageCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/package.json": parsePackageJSON, + } + + return common.NewGenericCataloger(nil, globParsers, "javascript-package-cataloger") +} + +// NewJavascriptLockCataloger returns a new Javascript cataloger object base on package lock files. +func NewJavascriptLockCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/package-lock.json": parsePackageLock, + "**/yarn.lock": parseYarnLock, + "**/pnpm-lock.yaml": parsePnpmLock, + } + + return common.NewGenericCataloger(nil, globParsers, "javascript-lock-cataloger", addLicenses) +} + +func addLicenses(resolver source.FileResolver, location source.Location, p *pkg.Package) error { + dir := path.Dir(location.RealPath) + pkgPath := []string{dir, "node_modules"} + pkgPath = append(pkgPath, strings.Split(p.Name, "/")...) + pkgPath = append(pkgPath, "package.json") + pkgFile := path.Join(pkgPath...) + locations, err := resolver.FilesByPath(pkgFile) + if err != nil { + log.Debugf("an error occurred attempting to read: %s - %+v", pkgFile, err) + return nil + } + + if len(locations) == 0 { + return nil + } + + for _, location := range locations { + contentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + log.Debugf("error getting file content reader for %s: %v", pkgFile, err) + return nil + } + + contents, err := io.ReadAll(contentReader) + if err != nil { + log.Debugf("error reading file contents for %s: %v", pkgFile, err) + return nil + } + + var pkgJSON packageJSON + err = json.Unmarshal(contents, &pkgJSON) + if err != nil { + log.Debugf("error parsing %s: %v", pkgFile, err) + return nil + } + + licenses, err := pkgJSON.licensesFromJSON() + if err != nil { + log.Debugf("error getting licenses from %s: %v", pkgFile, err) + return nil + } + + p.Licenses = append(p.Licenses, licenses...) + } + + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..325d0b65fd6c8cd21bb88ac73ece57b79b1fe606 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/cataloger_test.go @@ -0,0 +1,102 @@ +package javascript + +import ( + "testing" + + "github.com/stretchr/testify/require" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +func Test_JavascriptCataloger(t *testing.T) { + expected := map[string]pkg.Package{ + "@actions/core": { + Name: "@actions/core", + Version: "1.6.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + Licenses: []string{"MIT"}, + }, + "wordwrap": { + Name: "wordwrap", + Version: "0.0.3", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "get-stdin": { + Name: "get-stdin", + Version: "5.0.1", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "minimist": { + Name: "minimist", + Version: "0.0.10", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "optimist": { + Name: "optimist", + Version: "0.6.1", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "string-width": { + Name: "string-width", + Version: "2.1.1", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "strip-ansi": { + Name: "strip-ansi", + Version: "4.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "strip-eof": { + Name: "wordwrap", + Version: "1.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "ansi-regex": { + Name: "ansi-regex", + Version: "3.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "is-fullwidth-code-point": { + Name: "is-fullwidth-code-point", + Version: "2.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "cowsay": { + Name: "cowsay", + Version: "1.4.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + Licenses: []string{"MIT"}, + }, + } + + s, err := source.NewFromDirectory("test-fixtures/pkg-lock") + require.NoError(t, err) + + resolver, err := s.FileResolver(source.AllLayersScope) + require.NoError(t, err) + + actual, _, err := NewJavascriptLockCataloger().Catalog(resolver) + if err != nil { + t.Fatalf("failed to parse package-lock.json: %+v", err) + } + + var pkgs []*pkg.Package + for _, p := range actual { + p2 := p + pkgs = append(pkgs, &p2) + } + + assertPkgsEqual(t, pkgs, expected) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_json.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_json.go new file mode 100644 index 0000000000000000000000000000000000000000..32a67b5072a3bc537ae367eec6524fae1d9f1fb6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_json.go @@ -0,0 +1,240 @@ +package javascript + +import ( + "encoding/json" + "errors" + "fmt" + "io" + "regexp" + + "github.com/anchore/syft/internal/log" + + "github.com/anchore/syft/internal" + + "github.com/mitchellh/mapstructure" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parsePackageJSON + +// packageJSON represents a JavaScript package.json file +type packageJSON struct { + Version string `json:"version"` + Latest []string `json:"latest"` + Author author `json:"author"` + License json.RawMessage `json:"license"` + Licenses json.RawMessage `json:"licenses"` + Name string `json:"name"` + Homepage string `json:"homepage"` + Description string `json:"description"` + Dependencies map[string]string `json:"dependencies"` + Repository repository `json:"repository"` + Private bool `json:"private"` +} + +type author struct { + Name string `json:"name" mapstruct:"name"` + Email string `json:"email" mapstruct:"email"` + URL string `json:"url" mapstruct:"url"` +} + +type repository struct { + Type string `json:"type" mapstructure:"type"` + URL string `json:"url" mapstructure:"url"` +} + +// match example: "author": "Isaac Z. Schlueter (http://blog.izs.me)" +// ---> name: "Isaac Z. Schlueter" email: "i@izs.me" url: "http://blog.izs.me" +var authorPattern = regexp.MustCompile(`^\s*(?P[^<(]*)(\s+<(?P.*)>)?(\s\((?P.*)\))?\s*$`) + +func (a *author) UnmarshalJSON(b []byte) error { + var authorStr string + var fields map[string]string + var auth author + + if err := json.Unmarshal(b, &authorStr); err != nil { + // string parsing did not work, assume a map was given + // for more information: https://docs.npmjs.com/files/package.json#people-fields-author-contributors + if err := json.Unmarshal(b, &fields); err != nil { + return fmt.Errorf("unable to parse package.json author: %w", err) + } + } else { + // parse out "name (url)" into an author struct + fields = internal.MatchNamedCaptureGroups(authorPattern, authorStr) + } + + // translate the map into a structure + if err := mapstructure.Decode(fields, &auth); err != nil { + return fmt.Errorf("unable to decode package.json author: %w", err) + } + + *a = auth + + return nil +} + +func (a *author) AuthorString() string { + result := a.Name + if a.Email != "" { + result += fmt.Sprintf(" <%s>", a.Email) + } + if a.URL != "" { + result += fmt.Sprintf(" (%s)", a.URL) + } + return result +} + +func (r *repository) UnmarshalJSON(b []byte) error { + var repositoryStr string + var fields map[string]string + var repo repository + + if err := json.Unmarshal(b, &repositoryStr); err != nil { + // string parsing did not work, assume a map was given + // for more information: https://docs.npmjs.com/files/package.json#people-fields-author-contributors + if err := json.Unmarshal(b, &fields); err != nil { + return fmt.Errorf("unable to parse package.json author: %w", err) + } + // translate the map into a structure + if err := mapstructure.Decode(fields, &repo); err != nil { + return fmt.Errorf("unable to decode package.json author: %w", err) + } + + *r = repo + } else { + r.URL = repositoryStr + } + + return nil +} + +type license struct { + Type string `json:"type"` + URL string `json:"url"` +} + +func licenseFromJSON(b []byte) (string, error) { + // first try as string + var licenseString string + err := json.Unmarshal(b, &licenseString) + if err == nil { + return licenseString, nil + } + + // then try as object (this format is deprecated) + var licenseObject license + err = json.Unmarshal(b, &licenseObject) + if err == nil { + return licenseObject.Type, nil + } + + return "", errors.New("unable to unmarshal license field as either string or object") +} + +func (p packageJSON) licensesFromJSON() ([]string, error) { + if p.License == nil && p.Licenses == nil { + // This package.json doesn't specify any licenses whatsoever + return []string{}, nil + } + + singleLicense, err := licenseFromJSON(p.License) + if err == nil { + return []string{singleLicense}, nil + } + + multiLicense, err := licensesFromJSON(p.Licenses) + + // The "licenses" field is deprecated. It should be inspected as a last resort. + if multiLicense != nil && err == nil { + mapLicenses := func(licenses []license) []string { + mappedLicenses := make([]string, len(licenses)) + for i, l := range licenses { + mappedLicenses[i] = l.Type + } + return mappedLicenses + } + + return mapLicenses(multiLicense), nil + } + + return nil, err +} + +func licensesFromJSON(b []byte) ([]license, error) { + var licenseObject []license + err := json.Unmarshal(b, &licenseObject) + if err == nil { + return licenseObject, nil + } + + return nil, errors.New("unmarshal failed") +} + +// parsePackageJSON parses a package.json and returns the discovered JavaScript packages. +func parsePackageJSON(path string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + var packages []*pkg.Package + dec := json.NewDecoder(reader) + + for { + var p packageJSON + if err := dec.Decode(&p); err == io.EOF { + break + } else if err != nil { + return nil, nil, fmt.Errorf("failed to parse package.json file: %w", err) + } + + if !p.hasNameAndVersionValues() { + log.Debugf("encountered package.json file without a name and/or version field, ignoring (path=%q)", path) + return nil, nil, nil + } + + packages = append(packages, newPackageJSONPackage(p)) + } + + return packages, nil, nil +} + +func newPackageJSONPackage(p packageJSON) *pkg.Package { + licenses, err := p.licensesFromJSON() + if err != nil { + log.Warnf("unable to extract licenses from javascript package.json: %+v", err) + } + + return &pkg.Package{ + Name: p.Name, + Version: p.Version, + Licenses: licenses, + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: p.Name, + Version: p.Version, + Author: p.Author.AuthorString(), + Homepage: p.Homepage, + URL: p.Repository.URL, + Licenses: licenses, + Private: p.Private, + }, + } +} + +func (p packageJSON) hasNameAndVersionValues() bool { + return p.Name != "" && p.Version != "" +} + +// this supports both windows and unix paths +var filepathSeparator = regexp.MustCompile(`[\\/]`) + +func pathContainsNodeModulesDirectory(p string) bool { + for _, subPath := range filepathSeparator.Split(p, -1) { + if subPath == "node_modules" { + return true + } + } + return false +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_json_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_json_test.go new file mode 100644 index 0000000000000000000000000000000000000000..60a2a06cbc5a0d7036612d7df4348f34e8adf26b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_json_test.go @@ -0,0 +1,261 @@ +package javascript + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" + "github.com/stretchr/testify/assert" +) + +func TestParsePackageJSON(t *testing.T) { + tests := []struct { + Fixture string + ExpectedPkg pkg.Package + }{ + { + Fixture: "test-fixtures/pkg-json/package.json", + ExpectedPkg: pkg.Package{ + Name: "npm", + Version: "6.14.6", + Type: pkg.NpmPkg, + Licenses: []string{"Artistic-2.0"}, + Language: pkg.JavaScript, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: "npm", + Version: "6.14.6", + Author: "Isaac Z. Schlueter (http://blog.izs.me)", + Homepage: "https://docs.npmjs.com/", + URL: "https://github.com/npm/cli", + Licenses: []string{"Artistic-2.0"}, + }, + }, + }, + { + Fixture: "test-fixtures/pkg-json/package-license-object.json", + ExpectedPkg: pkg.Package{ + Name: "npm", + Version: "6.14.6", + Type: pkg.NpmPkg, + Licenses: []string{"ISC"}, + Language: pkg.JavaScript, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: "npm", + Version: "6.14.6", + Author: "Isaac Z. Schlueter (http://blog.izs.me)", + Homepage: "https://docs.npmjs.com/", + URL: "https://github.com/npm/cli", + Licenses: []string{"ISC"}, + }, + }, + }, + { + Fixture: "test-fixtures/pkg-json/package-license-objects.json", + ExpectedPkg: pkg.Package{ + Name: "npm", + Version: "6.14.6", + Type: pkg.NpmPkg, + Licenses: []string{"MIT", "Apache-2.0"}, + Language: pkg.JavaScript, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: "npm", + Version: "6.14.6", + Author: "Isaac Z. Schlueter (http://blog.izs.me)", + Homepage: "https://docs.npmjs.com/", + URL: "https://github.com/npm/cli", + Licenses: []string{"MIT", "Apache-2.0"}, + }, + }, + }, + { + Fixture: "test-fixtures/pkg-json/package-malformed-license.json", + ExpectedPkg: pkg.Package{ + Name: "npm", + Version: "6.14.6", + Type: pkg.NpmPkg, + Licenses: nil, + Language: pkg.JavaScript, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: "npm", + Version: "6.14.6", + Author: "Isaac Z. Schlueter (http://blog.izs.me)", + Homepage: "https://docs.npmjs.com/", + URL: "https://github.com/npm/cli", + Licenses: nil, + }, + }, + }, + { + Fixture: "test-fixtures/pkg-json/package-no-license.json", + ExpectedPkg: pkg.Package{ + Name: "npm", + Version: "6.14.6", + Type: pkg.NpmPkg, + Licenses: []string{}, + Language: pkg.JavaScript, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: "npm", + Version: "6.14.6", + Author: "Isaac Z. Schlueter (http://blog.izs.me)", + Homepage: "https://docs.npmjs.com/", + URL: "https://github.com/npm/cli", + Licenses: []string{}, + }, + }, + }, + { + Fixture: "test-fixtures/pkg-json/package-nested-author.json", + ExpectedPkg: pkg.Package{ + Name: "npm", + Version: "6.14.6", + Type: pkg.NpmPkg, + Licenses: []string{"Artistic-2.0"}, + Language: pkg.JavaScript, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: "npm", + Version: "6.14.6", + Author: "Isaac Z. Schlueter (http://blog.izs.me)", + Homepage: "https://docs.npmjs.com/", + URL: "https://github.com/npm/cli", + Licenses: []string{"Artistic-2.0"}, + }, + }, + }, + { + Fixture: "test-fixtures/pkg-json/package-repo-string.json", + ExpectedPkg: pkg.Package{ + Name: "function-bind", + Version: "1.1.1", + Type: pkg.NpmPkg, + Licenses: []string{"MIT"}, + Language: pkg.JavaScript, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: "function-bind", + Version: "1.1.1", + Author: "Raynos ", + Homepage: "https://github.com/Raynos/function-bind", + URL: "git://github.com/Raynos/function-bind.git", + Licenses: []string{"MIT"}, + }, + }, + }, + { + Fixture: "test-fixtures/pkg-json/package-private.json", + ExpectedPkg: pkg.Package{ + Name: "npm", + Version: "6.14.6", + Type: pkg.NpmPkg, + Licenses: []string{"Artistic-2.0"}, + Language: pkg.JavaScript, + MetadataType: pkg.NpmPackageJSONMetadataType, + Metadata: pkg.NpmPackageJSONMetadata{ + Name: "npm", + Version: "6.14.6", + Author: "Isaac Z. Schlueter (http://blog.izs.me)", + Homepage: "https://docs.npmjs.com/", + URL: "https://github.com/npm/cli", + Licenses: []string{"Artistic-2.0"}, + Private: true, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.Fixture, func(t *testing.T) { + fixture, err := os.Open(test.Fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, _, err := parsePackageJSON("", fixture) + if err != nil { + t.Fatalf("failed to parse package-lock.json: %+v", err) + } + if len(actual) != 1 { + for _, a := range actual { + t.Log(" ", a) + } + t.Fatalf("unexpected package count: %d!=1", len(actual)) + } + + for _, d := range deep.Equal(actual[0], &test.ExpectedPkg) { + + t.Errorf("diff: %+v", d) + } + }) + } +} + +func TestParsePackageJSON_Partial(t *testing.T) { // see https://github.com/anchore/syft/issues/311 + const fixtureFile = "test-fixtures/pkg-json/package-partial.json" + fixture, err := os.Open(fixtureFile) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parsePackageJSON("", fixture) + if err != nil { + t.Fatalf("failed to parse package-lock.json: %+v", err) + } + + if actualCount := len(actual); actualCount != 0 { + t.Errorf("no packages should've been returned (but got %d packages)", actualCount) + } +} + +func Test_pathContainsNodeModulesDirectory(t *testing.T) { + tests := []struct { + path string + expected bool + }{ + // positive + { + path: "something/node_modules/package", + expected: true, + }, + { + path: "node_modules/package", + expected: true, + }, + { + path: "something/node_modules", + expected: true, + }, + { + path: "\\something\\node_modules\\", + expected: true, + }, + { + path: "\\something\\node_modules", + expected: true, + }, + // negative + { + path: "something/node_bogus_modules", + expected: false, + }, + { + path: "something/node_modules_bogus", + expected: false, + }, + { + path: "something/node_bogus_modules/package", + expected: false, + }, + } + for _, test := range tests { + t.Run(test.path, func(t *testing.T) { + assert.Equal(t, test.expected, pathContainsNodeModulesDirectory(test.path)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..5b98135bc6aab76d998622f085a5293fd0d6ab8f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_lock.go @@ -0,0 +1,84 @@ +package javascript + +import ( + "encoding/json" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parsePackageLock + +// PackageLock represents a JavaScript package.lock json file +type PackageLock struct { + Requires bool `json:"requires"` + LockfileVersion int `json:"lockfileVersion"` + Dependencies map[string]Dependency + Packages map[string]Package +} + +// Dependency represents a single package dependency listed in the package.lock json file +type Dependency struct { + Version string `json:"version"` + Resolved string `json:"resolved"` + Integrity string `json:"integrity"` +} + +type Package struct { + Version string `json:"version"` + Resolved string `json:"resolved"` + Integrity string `json:"integrity"` + License string `json:""` +} + +// parsePackageLock parses a package-lock.json and returns the discovered JavaScript packages. +func parsePackageLock(path string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + // in the case we find package-lock.json files in the node_modules directories, skip those + // as the whole purpose of the lock file is for the specific dependencies of the root project + if pathContainsNodeModulesDirectory(path) { + return nil, nil, nil + } + + var packages []*pkg.Package + dec := json.NewDecoder(reader) + + for { + var lock PackageLock + if err := dec.Decode(&lock); err == io.EOF { + break + } else if err != nil { + return nil, nil, fmt.Errorf("failed to parse package-lock.json file: %w", err) + } + licenseMap := make(map[string]string) + for _, pkgMeta := range lock.Packages { + var sb strings.Builder + sb.WriteString(pkgMeta.Resolved) + sb.WriteString(pkgMeta.Integrity) + licenseMap[sb.String()] = pkgMeta.License + } + + for name, pkgMeta := range lock.Dependencies { + var sb strings.Builder + sb.WriteString(pkgMeta.Resolved) + sb.WriteString(pkgMeta.Integrity) + var licenses []string + if license, exists := licenseMap[sb.String()]; exists { + licenses = append(licenses, license) + } + packages = append(packages, &pkg.Package{ + Name: name, + Version: pkgMeta.Version, + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + Licenses: licenses, + }) + } + } + + return packages, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..c280a61cb517c94a21f1d5c7defd795ab9804ff4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_package_lock_test.go @@ -0,0 +1,157 @@ +package javascript + +import ( + "os" + "testing" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/pkg" +) + +func assertPkgsEqual(t *testing.T, actual []*pkg.Package, expected map[string]pkg.Package) { + t.Helper() + if len(actual) != len(expected) { + for _, a := range actual { + t.Log(" ", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(expected)) + } + + for _, a := range actual { + expectedPkg, ok := expected[a.Name] + assert.True(t, ok) + assert.Equal(t, expectedPkg.Version, a.Version, "bad version") + assert.Equal(t, expectedPkg.Language, a.Language, "bad language") + assert.Equal(t, expectedPkg.Type, a.Type, "bad type") + assert.Equal(t, expectedPkg.Licenses, a.Licenses, "bad license count") + } +} + +func TestParsePackageLock(t *testing.T) { + expected := map[string]pkg.Package{ + "@actions/core": { + Name: "@actions/core", + Version: "1.6.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "wordwrap": { + Name: "wordwrap", + Version: "0.0.3", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "get-stdin": { + Name: "get-stdin", + Version: "5.0.1", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "minimist": { + Name: "minimist", + Version: "0.0.10", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "optimist": { + Name: "optimist", + Version: "0.6.1", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "string-width": { + Name: "string-width", + Version: "2.1.1", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "strip-ansi": { + Name: "strip-ansi", + Version: "4.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "strip-eof": { + Name: "wordwrap", + Version: "1.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "ansi-regex": { + Name: "ansi-regex", + Version: "3.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "is-fullwidth-code-point": { + Name: "is-fullwidth-code-point", + Version: "2.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "cowsay": { + Name: "cowsay", + Version: "1.4.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + } + fixture, err := os.Open("test-fixtures/pkg-lock/package-lock.json") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parsePackageLock(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse package-lock.json: %+v", err) + } + + assertPkgsEqual(t, actual, expected) + +} + +func TestParsePackageLockV2(t *testing.T) { + expected := map[string]pkg.Package{ + "@types/prop-types": { + Name: "@types/prop-types", + Version: "15.7.5", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + Licenses: []string{"MIT"}, + }, + "@types/react": { + Name: "@types/prop-types", + Version: "18.0.17", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + Licenses: []string{"MIT"}, + }, + "@types/scheduler": { + Name: "@types/scheduler", + Version: "0.16.2", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + Licenses: []string{"MIT"}, + }, + "csstype": { + Name: "csstype", + Version: "3.1.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + Licenses: []string{"MIT"}, + }, + } + fixture, err := os.Open("test-fixtures/pkg-lock/package-lock-2.json") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, _, err := parsePackageLock(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse package-lock.json: %+v", err) + } + + assertPkgsEqual(t, actual, expected) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_pnpm_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_pnpm_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..fc0cb2cb493117fce3c533626960c80d688ecd74 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_pnpm_lock.go @@ -0,0 +1,43 @@ +package javascript + +import ( + "fmt" + "io" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "gopkg.in/yaml.v3" +) + +// integrity check +var _ common.ParserFn = parsePnpmLock + +type pnpmLockYaml struct { + Dependencies map[string]string `json:"dependencies"` +} + +func parsePnpmLock(path string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + bytes, err := io.ReadAll(reader) + if err != nil { + return nil, nil, fmt.Errorf("failed to load pnpm-lock.yaml file: %w", err) + } + + var pkgs []*pkg.Package + var lockFile pnpmLockYaml + + if err := yaml.Unmarshal(bytes, &lockFile); err != nil { + return nil, nil, fmt.Errorf("failed to parse pnpm-lock.yaml file: %w", err) + } + + for name, version := range lockFile.Dependencies { + pkgs = append(pkgs, &pkg.Package{ + Name: name, + Version: version, + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }) + } + + return pkgs, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_pnpm_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_pnpm_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..af626eef20836f656e41ab9bf8462efdada7b479 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_pnpm_lock_test.go @@ -0,0 +1,58 @@ +package javascript + +import ( + "os" + "sort" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func fixtureP(str string) *string { + return &str +} + +func TestParsePnpmLock(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "nanoid", + Version: "3.3.4", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + { + Name: "picocolors", + Version: "1.0.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + { + Name: "source-map-js", + Version: "1.0.2", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + } + + fixture, err := os.Open("test-fixtures/pnpm/pnpm-lock.yaml") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parsePnpmLock(fixture.Name(), fixture) + if err != nil { + t.Error(err) + } + + // we have to sort this for expected to match actual since yaml maps are unordered + sort.Slice(actual, func(p, q int) bool { + return actual[p].Name < actual[q].Name + }) + + differences := deep.Equal(expected, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_yarn_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_yarn_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..91ab8043a488a3df758e67da66420cdc30e8636e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_yarn_lock.go @@ -0,0 +1,125 @@ +package javascript + +import ( + "bufio" + "fmt" + "io" + "regexp" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseYarnLock + +var ( + // packageNameExp matches the name of the dependency in yarn.lock + // including scope/namespace prefix if found. + // For example: "aws-sdk@2.706.0" returns "aws-sdk" + // "@babel/code-frame@^7.0.0" returns "@babel/code-frame" + packageNameExp = regexp.MustCompile(`^"?((?:@\w[\w-_.]*\/)?\w[\w-_.]*)@`) + + // versionExp matches the "version" line of a yarn.lock entry and captures the version value. + // For example: version "4.10.1" (...and the value "4.10.1" is captured) + versionExp = regexp.MustCompile(`^\W+version(?:\W+"|:\W+)([\w-_.]+)"?`) + + // packageURLExp matches the name and version of the dependency in yarn.lock + // from the resolved URL, including scope/namespace prefix if any. + // For example: + // `resolved "https://registry.yarnpkg.com/async/-/async-3.2.3.tgz#ac53dafd3f4720ee9e8a160628f18ea91df196c9"` + // would return "async" and "3.2.3" + // + // `resolved "https://registry.yarnpkg.com/@4lolo/resize-observer-polyfill/-/resize-observer-polyfill-1.5.2.tgz#58868fc7224506236b5550d0c68357f0a874b84b"` + // would return "@4lolo/resize-observer-polyfill" and "1.5.2" + packageURLExp = regexp.MustCompile(`^\s+resolved\s+"https://registry\.(?:yarnpkg\.com|npmjs\.org)/(.+?)/-/(?:.+?)-(\d+\..+?)\.tgz`) +) + +const ( + noPackage = "" + noVersion = "" +) + +func parseYarnLock(path string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + // in the case we find yarn.lock files in the node_modules directories, skip those + // as the whole purpose of the lock file is for the specific dependencies of the project + if pathContainsNodeModulesDirectory(path) { + return nil, nil, nil + } + + var packages []*pkg.Package + scanner := bufio.NewScanner(reader) + parsedPackages := internal.NewStringSet() + currentPackage := noPackage + currentVersion := noVersion + + for scanner.Scan() { + line := scanner.Text() + + if packageName := findPackageName(line); packageName != noPackage { + // When we find a new package, check if we have unsaved identifiers + if currentPackage != noPackage && currentVersion != noVersion && !parsedPackages.Contains(currentPackage+"@"+currentVersion) { + packages = append(packages, newYarnLockPackage(currentPackage, currentVersion)) + parsedPackages.Add(currentPackage + "@" + currentVersion) + } + + currentPackage = packageName + } else if version := findPackageVersion(line); version != noVersion { + currentVersion = version + } else if packageName, version := findPackageAndVersion(line); packageName != noPackage && version != noVersion && !parsedPackages.Contains(packageName+"@"+version) { + packages = append(packages, newYarnLockPackage(packageName, version)) + parsedPackages.Add(packageName + "@" + version) + + // Cleanup to indicate no unsaved identifiers + currentPackage = noPackage + currentVersion = noVersion + } + } + + // check if we have valid unsaved data after end-of-file has reached + if currentPackage != noPackage && currentVersion != noVersion && !parsedPackages.Contains(currentPackage+"@"+currentVersion) { + packages = append(packages, newYarnLockPackage(currentPackage, currentVersion)) + parsedPackages.Add(currentPackage + "@" + currentVersion) + } + + if err := scanner.Err(); err != nil { + return nil, nil, fmt.Errorf("failed to parse yarn.lock file: %w", err) + } + + return packages, nil, nil +} + +func findPackageName(line string) string { + if matches := packageNameExp.FindStringSubmatch(line); len(matches) >= 2 { + return matches[1] + } + + return noPackage +} + +func findPackageVersion(line string) string { + if matches := versionExp.FindStringSubmatch(line); len(matches) >= 2 { + return matches[1] + } + + return noVersion +} + +func findPackageAndVersion(line string) (string, string) { + if matches := packageURLExp.FindStringSubmatch(line); len(matches) >= 2 { + return matches[1], matches[2] + } + + return noPackage, noVersion +} + +func newYarnLockPackage(name, version string) *pkg.Package { + return &pkg.Package{ + Name: name, + Version: version, + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_yarn_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_yarn_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..fbe2ce7a7a25b759ccc8755757a13b5487d9ee5a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/parse_yarn_lock_test.go @@ -0,0 +1,325 @@ +package javascript + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func TestParseYarnBerry(t *testing.T) { + expected := map[string]pkg.Package{ + "@babel/code-frame": { + Name: "@babel/code-frame", + Version: "7.10.4", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "@types/minimatch": { + Name: "@types/minimatch", + Version: "3.0.3", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "@types/qs": { + Name: "@types/qs", + Version: "6.9.4", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "ajv": { + Name: "ajv", + Version: "6.12.3", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "atob": { + Name: "atob", + Version: "2.1.2", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "aws-sdk": { + Name: "aws-sdk", + Version: "2.706.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "jhipster-core": { + Name: "jhipster-core", + Version: "7.3.4", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "asn1.js": { + Name: "asn1.js", + Version: "4.10.1", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "c0n-fab_u.laTION": { + Name: "c0n-fab_u.laTION", + Version: "7.7.7", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + } + testFixtures := []string{ + "test-fixtures/yarn-berry/yarn.lock", + } + + for _, file := range testFixtures { + file := file + t.Run(file, func(t *testing.T) { + t.Parallel() + + fixture, err := os.Open(file) + require.NoError(t, err) + + // TODO: no relationships are under test yet + actual, _, err := parseYarnLock(fixture.Name(), fixture) + require.NoError(t, err) + + assertPkgsEqual(t, actual, expected) + }) + } +} + +func TestParseYarnLock(t *testing.T) { + expected := map[string]pkg.Package{ + "@babel/code-frame": { + Name: "@babel/code-frame", + Version: "7.10.4", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "@types/minimatch": { + Name: "@types/minimatch", + Version: "3.0.3", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "@types/qs": { + Name: "@types/qs", + Version: "6.9.4", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "ajv": { + Name: "ajv", + Version: "6.12.3", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "atob": { + Name: "atob", + Version: "2.1.2", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "aws-sdk": { + Name: "aws-sdk", + Version: "2.706.0", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "jhipster-core": { + Name: "jhipster-core", + Version: "7.3.4", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "asn1.js": { + Name: "asn1.js", + Version: "4.10.1", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + "something-i-made-up": { + Name: "something-i-made-up", + Version: "7.7.7", + Language: pkg.JavaScript, + Type: pkg.NpmPkg, + }, + } + + testFixtures := []string{ + "test-fixtures/yarn/yarn.lock", + } + + for _, file := range testFixtures { + file := file + t.Run(file, func(t *testing.T) { + t.Parallel() + + fixture, err := os.Open(file) + require.NoError(t, err) + + // TODO: no relationships are under test yet + actual, _, err := parseYarnLock(fixture.Name(), fixture) + require.NoError(t, err) + + assertPkgsEqual(t, actual, expected) + }) + } +} + +func TestParseYarnFindPackageNames(t *testing.T) { + tests := []struct { + line string + expected string + }{ + { + line: `"@babel/code-frame@npm:7.10.4":`, + expected: "@babel/code-frame", + }, + { + line: `"@babel/code-frame@^7.0.0", "@babel/code-frame@^7.10.4":`, + expected: "@babel/code-frame", + }, + { + line: "ajv@^6.10.2, ajv@^6.5.5:", + expected: "ajv", + }, + { + line: "aws-sdk@2.706.0:", + expected: "aws-sdk", + }, + { + line: "asn1.js@^4.0.0:", + expected: "asn1.js", + }, + { + line: "c0n-fab_u.laTION@^7.0.0", + expected: "c0n-fab_u.laTION", + }, + { + line: `"newtest@workspace:.":`, + expected: "newtest", + }, + { + line: `"color-convert@npm:^1.9.0":`, + expected: "color-convert", + }, + { + line: `"@npmcorp/code-frame@^7.1.0", "@npmcorp/code-frame@^7.10.4":`, + expected: "@npmcorp/code-frame", + }, + { + line: `"@npmcorp/code-frame@^7.2.3":`, + expected: "@npmcorp/code-frame", + }, + { + line: `"@s/odd-name@^7.1.2":`, + expected: "@s/odd-name", + }, + { + line: `"@/code-frame@^7.3.4":`, + expected: "", + }, + { + line: `"code-frame":`, + expected: "", + }, + } + + for _, test := range tests { + test := test + t.Run(test.expected, func(t *testing.T) { + t.Parallel() + actual := findPackageName(test.line) + assert.Equal(t, test.expected, actual) + }) + } +} + +func TestParseYarnFindPackageVersions(t *testing.T) { + tests := []struct { + line string + expected string + }{ + { + line: ` version "7.10.4"`, + expected: "7.10.4", + }, + { + line: ` version "7.11.5"`, + expected: "7.11.5", + }, + { + line: `version "7.12.6"`, + expected: "", + }, + { + line: ` version "0.0.0"`, + expected: "0.0.0", + }, + { + line: ` version "2" `, + expected: "2", + }, + { + line: ` version "9.3"`, + expected: "9.3", + }, + { + line: "ajv@^6.10.2, ajv@^6.5.5", + expected: "", + }, + { + line: "atob@^2.1.2:", + expected: "", + }, + { + line: `"color-convert@npm:^1.9.0":`, + expected: "", + }, + { + line: " version: 1.9.3", + expected: "1.9.3", + }, + { + line: " version: 2", + expected: "2", + }, + { + line: " version: 9.3", + expected: "9.3", + }, + { + line: "ajv@^6.10.2, ajv@^6.5.5", + expected: "", + }, + { + line: "atob@^2.1.2:", + expected: "", + }, + { + line: " version: 1.0.0-alpha+001", + expected: "1.0.0-alpha", + }, + { + line: " version: 1.0.0-beta_test+exp.sha.5114f85", + expected: "1.0.0-beta_test", + }, + { + line: " version: 1.0.0+21AF26D3-117B344092BD", + expected: "1.0.0", + }, + { + line: " version: 0.0.0-use.local", + expected: "0.0.0-use.local", + }, + } + + for _, test := range tests { + test := test + t.Run(test.expected, func(t *testing.T) { + t.Parallel() + actual := findPackageVersion(test.line) + assert.Equal(t, test.expected, actual) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-license-object.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-license-object.json new file mode 100644 index 0000000000000000000000000000000000000000..9c5d615674aebee0343e85eee874f2957086b2fa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-license-object.json @@ -0,0 +1,22 @@ +{ + "version": "6.14.6", + "name": "npm", + "description": "a package manager for JavaScript", + "homepage": "https://docs.npmjs.com/", + "author": "Isaac Z. Schlueter (http://blog.izs.me)", + "repository": { + "type": "git", + "url": "https://github.com/npm/cli" + }, + "bugs": { + "url": "https://npm.community/c/bugs" + }, + "main": "./lib/npm.js", + "license": { + "type" : "ISC", + "url" : "https://opensource.org/licenses/ISC" + }, + "engines": { + "node": "6 >=6.2.0 || 8 || >=9.3.0" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-license-objects.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-license-objects.json new file mode 100644 index 0000000000000000000000000000000000000000..605bc3ec98c3966bcd497ddb3308681b8062ff81 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-license-objects.json @@ -0,0 +1,26 @@ +{ + "version": "6.14.6", + "name": "npm", + "description": "a package manager for JavaScript", + "homepage": "https://docs.npmjs.com/", + "author": "Isaac Z. Schlueter (http://blog.izs.me)", + "repository": { + "type": "git", + "url": "https://github.com/npm/cli" + }, + "bugs": { + "url": "https://npm.community/c/bugs" + }, + "main": "./lib/npm.js", + "licenses": [ + { "type": "MIT", + "url": "https://www.opensource.org/licenses/mit-license.php" + }, + { "type": "Apache-2.0", + "url": "https://opensource.org/licenses/apache2.0.php" + } + ], + "engines": { + "node": "6 >=6.2.0 || 8 || >=9.3.0" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-malformed-license.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-malformed-license.json new file mode 100644 index 0000000000000000000000000000000000000000..3ddba4d85c3590419920b2205416b5255735c1e6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-malformed-license.json @@ -0,0 +1,19 @@ +{ + "version": "6.14.6", + "name": "npm", + "description": "a package manager for JavaScript", + "homepage": "https://docs.npmjs.com/", + "author": "Isaac Z. Schlueter (http://blog.izs.me)", + "repository": { + "type": "git", + "url": "https://github.com/npm/cli" + }, + "bugs": { + "url": "https://npm.community/c/bugs" + }, + "main": "./lib/npm.js", + "licenses": [ "MIT" ], + "engines": { + "node": "6 >=6.2.0 || 8 || >=9.3.0" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-nested-author.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-nested-author.json new file mode 100644 index 0000000000000000000000000000000000000000..ac2438a116bcfb35795429a292209708c5dbab5e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-nested-author.json @@ -0,0 +1,16 @@ +{ + "version": "6.14.6", + "name": "npm", + "description": "a package manager for JavaScript", + "homepage": "https://docs.npmjs.com/", + "author": { + "name": "Isaac Z. Schlueter", + "email": "i@izs.me", + "url": "http://blog.izs.me" + }, + "repository": { + "type": "git", + "url": "https://github.com/npm/cli" + }, + "license": "Artistic-2.0" +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-no-license.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-no-license.json new file mode 100644 index 0000000000000000000000000000000000000000..9c1b29e24380d6073d5751aaf45c586c15b13373 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-no-license.json @@ -0,0 +1,18 @@ +{ + "version": "6.14.6", + "name": "npm", + "description": "a package manager for JavaScript", + "homepage": "https://docs.npmjs.com/", + "author": "Isaac Z. Schlueter (http://blog.izs.me)", + "repository": { + "type": "git", + "url": "https://github.com/npm/cli" + }, + "bugs": { + "url": "https://npm.community/c/bugs" + }, + "main": "./lib/npm.js", + "engines": { + "node": "6 >=6.2.0 || 8 || >=9.3.0" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-partial.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-partial.json new file mode 100644 index 0000000000000000000000000000000000000000..db7a90b51dfe866ba7e29133b923aac05351d5fa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-partial.json @@ -0,0 +1,5 @@ +{ + "sideEffects": false, + "module": "../../esm/fp/isSaturday/index.js", + "typings": "../../typings.d.ts" +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-private.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-private.json new file mode 100644 index 0000000000000000000000000000000000000000..4c00b66da49a8aaaac0245890f954c2ffaa6a351 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-private.json @@ -0,0 +1,315 @@ +{ + "version": "6.14.6", + "name": "npm", + "private": true, + "description": "a package manager for JavaScript", + "keywords": [ + "install", + "modules", + "package manager", + "package.json" + ], + "preferGlobal": true, + "config": { + "publishtest": false + }, + "homepage": "https://docs.npmjs.com/", + "author": "Isaac Z. Schlueter (http://blog.izs.me)", + "repository": { + "type": "git", + "url": "https://github.com/npm/cli" + }, + "bugs": { + "url": "https://npm.community/c/bugs" + }, + "directories": { + "bin": "./bin", + "doc": "./doc", + "lib": "./lib", + "man": "./man" + }, + "main": "./lib/npm.js", + "bin": { + "npm": "./bin/npm-cli.js", + "npx": "./bin/npx-cli.js" + }, + "dependencies": { + "JSONStream": "^1.3.5", + "abbrev": "~1.1.1", + "ansicolors": "~0.3.2", + "ansistyles": "~0.1.3", + "aproba": "^2.0.0", + "archy": "~1.0.0", + "bin-links": "^1.1.7", + "bluebird": "^3.5.5", + "byte-size": "^5.0.1", + "cacache": "^12.0.3", + "call-limit": "^1.1.1", + "chownr": "^1.1.4", + "ci-info": "^2.0.0", + "cli-columns": "^3.1.2", + "cli-table3": "^0.5.1", + "cmd-shim": "^3.0.3", + "columnify": "~1.5.4", + "config-chain": "^1.1.12", + "detect-indent": "~5.0.0", + "detect-newline": "^2.1.0", + "dezalgo": "~1.0.3", + "editor": "~1.0.0", + "figgy-pudding": "^3.5.1", + "find-npm-prefix": "^1.0.2", + "fs-vacuum": "~1.2.10", + "fs-write-stream-atomic": "~1.0.10", + "gentle-fs": "^2.3.0", + "glob": "^7.1.6", + "graceful-fs": "^4.2.4", + "has-unicode": "~2.0.1", + "hosted-git-info": "^2.8.8", + "iferr": "^1.0.2", + "infer-owner": "^1.0.4", + "inflight": "~1.0.6", + "inherits": "^2.0.4", + "ini": "^1.3.5", + "init-package-json": "^1.10.3", + "is-cidr": "^3.0.0", + "json-parse-better-errors": "^1.0.2", + "lazy-property": "~1.0.0", + "libcipm": "^4.0.7", + "libnpm": "^3.0.1", + "libnpmaccess": "^3.0.2", + "libnpmhook": "^5.0.3", + "libnpmorg": "^1.0.1", + "libnpmsearch": "^2.0.2", + "libnpmteam": "^1.0.2", + "libnpx": "^10.2.2", + "lock-verify": "^2.1.0", + "lockfile": "^1.0.4", + "lodash._baseuniq": "~4.6.0", + "lodash.clonedeep": "~4.5.0", + "lodash.union": "~4.6.0", + "lodash.uniq": "~4.5.0", + "lodash.without": "~4.4.0", + "lru-cache": "^5.1.1", + "meant": "~1.0.1", + "mississippi": "^3.0.0", + "mkdirp": "^0.5.5", + "move-concurrently": "^1.0.1", + "node-gyp": "^5.1.0", + "nopt": "^4.0.3", + "normalize-package-data": "^2.5.0", + "npm-audit-report": "^1.3.2", + "npm-cache-filename": "~1.0.2", + "npm-install-checks": "^3.0.2", + "npm-lifecycle": "^3.1.4", + "npm-package-arg": "^6.1.1", + "npm-packlist": "^1.4.8", + "npm-pick-manifest": "^3.0.2", + "npm-profile": "^4.0.4", + "npm-registry-fetch": "^4.0.5", + "npm-user-validate": "~1.0.0", + "npmlog": "~4.1.2", + "once": "~1.4.0", + "opener": "^1.5.1", + "osenv": "^0.1.5", + "pacote": "^9.5.12", + "path-is-inside": "~1.0.2", + "promise-inflight": "~1.0.1", + "qrcode-terminal": "^0.12.0", + "query-string": "^6.8.2", + "qw": "~1.0.1", + "read": "~1.0.7", + "read-cmd-shim": "^1.0.5", + "read-installed": "~4.0.3", + "read-package-json": "^2.1.1", + "read-package-tree": "^5.3.1", + "readable-stream": "^3.6.0", + "readdir-scoped-modules": "^1.1.0", + "request": "^2.88.0", + "retry": "^0.12.0", + "rimraf": "^2.7.1", + "safe-buffer": "^5.1.2", + "semver": "^5.7.1", + "sha": "^3.0.0", + "slide": "~1.1.6", + "sorted-object": "~2.0.1", + "sorted-union-stream": "~2.1.3", + "ssri": "^6.0.1", + "stringify-package": "^1.0.1", + "tar": "^4.4.13", + "text-table": "~0.2.0", + "tiny-relative-date": "^1.3.0", + "uid-number": "0.0.6", + "umask": "~1.1.0", + "unique-filename": "^1.1.1", + "unpipe": "~1.0.0", + "update-notifier": "^2.5.0", + "uuid": "^3.3.3", + "validate-npm-package-license": "^3.0.4", + "validate-npm-package-name": "~3.0.0", + "which": "^1.3.1", + "worker-farm": "^1.7.0", + "write-file-atomic": "^2.4.3" + }, + "bundleDependencies": [ + "abbrev", + "ansicolors", + "ansistyles", + "aproba", + "archy", + "bin-links", + "bluebird", + "byte-size", + "cacache", + "call-limit", + "chownr", + "ci-info", + "cli-columns", + "cli-table3", + "cmd-shim", + "columnify", + "config-chain", + "debuglog", + "detect-indent", + "detect-newline", + "dezalgo", + "editor", + "figgy-pudding", + "find-npm-prefix", + "fs-vacuum", + "fs-write-stream-atomic", + "gentle-fs", + "glob", + "graceful-fs", + "has-unicode", + "hosted-git-info", + "iferr", + "imurmurhash", + "infer-owner", + "inflight", + "inherits", + "ini", + "init-package-json", + "is-cidr", + "json-parse-better-errors", + "JSONStream", + "lazy-property", + "libcipm", + "libnpm", + "libnpmaccess", + "libnpmhook", + "libnpmorg", + "libnpmsearch", + "libnpmteam", + "libnpx", + "lock-verify", + "lockfile", + "lodash._baseindexof", + "lodash._baseuniq", + "lodash._bindcallback", + "lodash._cacheindexof", + "lodash._createcache", + "lodash._getnative", + "lodash.clonedeep", + "lodash.restparam", + "lodash.union", + "lodash.uniq", + "lodash.without", + "lru-cache", + "meant", + "mississippi", + "mkdirp", + "move-concurrently", + "node-gyp", + "nopt", + "normalize-package-data", + "npm-audit-report", + "npm-cache-filename", + "npm-install-checks", + "npm-lifecycle", + "npm-package-arg", + "npm-packlist", + "npm-pick-manifest", + "npm-profile", + "npm-registry-fetch", + "npm-user-validate", + "npmlog", + "once", + "opener", + "osenv", + "pacote", + "path-is-inside", + "promise-inflight", + "qrcode-terminal", + "query-string", + "qw", + "read-cmd-shim", + "read-installed", + "read-package-json", + "read-package-tree", + "read", + "readable-stream", + "readdir-scoped-modules", + "request", + "retry", + "rimraf", + "safe-buffer", + "semver", + "sha", + "slide", + "sorted-object", + "sorted-union-stream", + "ssri", + "stringify-package", + "tar", + "text-table", + "tiny-relative-date", + "uid-number", + "umask", + "unique-filename", + "unpipe", + "update-notifier", + "uuid", + "validate-npm-package-license", + "validate-npm-package-name", + "which", + "worker-farm", + "write-file-atomic" + ], + "devDependencies": { + "deep-equal": "^1.0.1", + "get-stream": "^4.1.0", + "licensee": "^7.0.3", + "marked": "^0.6.3", + "marked-man": "^0.6.0", + "npm-registry-couchapp": "^2.7.4", + "npm-registry-mock": "^1.3.1", + "require-inject": "^1.4.4", + "sprintf-js": "^1.1.2", + "standard": "^11.0.1", + "tacks": "^1.3.0", + "tap": "^12.7.0", + "tar-stream": "^2.1.0" + }, + "scripts": { + "dumpconf": "env | grep npm | sort | uniq", + "prepare": "node bin/npm-cli.js rebuild && node bin/npm-cli.js --no-audit --no-timing prune --prefix=. --no-global && rimraf test/*/*/node_modules && make -j4 mandocs", + "preversion": "bash scripts/update-authors.sh && git add AUTHORS && git commit -m \"update AUTHORS\" || true", + "licenses": "licensee --production --errors-only", + "tap": "tap -J --timeout 300 --no-esm", + "tap-cover": "tap -J --nyc-arg=--cache --coverage --timeout 600 --no-esm", + "lint": "standard", + "pretest": "npm run lint", + "test": "npm run test-tap --", + "test:nocleanup": "NO_TEST_CLEANUP=1 npm run test --", + "sudotest": "sudo npm run tap -- \"test/tap/*.js\"", + "sudotest:nocleanup": "sudo NO_TEST_CLEANUP=1 npm run tap -- \"test/tap/*.js\"", + "posttest": "rimraf test/npm_cache*", + "test-coverage": "npm run tap-cover -- \"test/tap/*.js\" \"test/network/*.js\"", + "test-tap": "npm run tap -- \"test/tap/*.js\" \"test/network/*.js\"", + "test-node": "tap --timeout 240 \"test/tap/*.js\" \"test/network/*.js\"" + }, + "license": "Artistic-2.0", + "engines": { + "node": "6 >=6.2.0 || 8 || >=9.3.0" + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-repo-string.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-repo-string.json new file mode 100644 index 0000000000000000000000000000000000000000..d42a73b5cdf9ecbaaa4d7bf4bd68398a294d291e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package-repo-string.json @@ -0,0 +1,66 @@ +{ + "name": "function-bind", + "version": "1.1.1", + "description": "Implementation of Function.prototype.bind", + "keywords": [ + "function", + "bind", + "shim", + "es5" + ], + "author": "Raynos ", + "repository": "git://github.com/Raynos/function-bind.git", + "main": "index", + "homepage": "https://github.com/Raynos/function-bind", + "contributors": [ + { + "name": "Raynos" + }, + { + "name": "Jordan Harband", + "url": "https://github.com/ljharb" + } + ], + "bugs": { + "url": "https://github.com/Raynos/function-bind/issues", + "email": "raynos2@gmail.com" + }, + "dependencies": {}, + "devDependencies": { + "@ljharb/eslint-config": "^12.2.1", + "covert": "^1.1.0", + "eslint": "^4.5.0", + "jscs": "^3.0.7", + "tape": "^4.8.0" + }, + "license": "MIT", + "scripts": { + "pretest": "npm run lint", + "test": "npm run tests-only", + "posttest": "npm run coverage -- --quiet", + "tests-only": "node test", + "coverage": "covert test/*.js", + "lint": "npm run jscs && npm run eslint", + "jscs": "jscs *.js */*.js", + "eslint": "eslint *.js */*.js" + }, + "testling": { + "files": "test/index.js", + "browsers": [ + "ie/8..latest", + "firefox/16..latest", + "firefox/nightly", + "chrome/22..latest", + "chrome/canary", + "opera/12..latest", + "opera/next", + "safari/5.1..latest", + "ipad/6.0..latest", + "iphone/6.0..latest", + "android-browser/4.2..latest" + ] + } +,"_resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz" +,"_integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" +,"_from": "function-bind@1.1.1" +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package.json new file mode 100644 index 0000000000000000000000000000000000000000..aba48c6bd3d3c0254bedb0e681f0b08bbe212a0f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-json/package.json @@ -0,0 +1,314 @@ +{ + "version": "6.14.6", + "name": "npm", + "description": "a package manager for JavaScript", + "keywords": [ + "install", + "modules", + "package manager", + "package.json" + ], + "preferGlobal": true, + "config": { + "publishtest": false + }, + "homepage": "https://docs.npmjs.com/", + "author": "Isaac Z. Schlueter (http://blog.izs.me)", + "repository": { + "type": "git", + "url": "https://github.com/npm/cli" + }, + "bugs": { + "url": "https://npm.community/c/bugs" + }, + "directories": { + "bin": "./bin", + "doc": "./doc", + "lib": "./lib", + "man": "./man" + }, + "main": "./lib/npm.js", + "bin": { + "npm": "./bin/npm-cli.js", + "npx": "./bin/npx-cli.js" + }, + "dependencies": { + "JSONStream": "^1.3.5", + "abbrev": "~1.1.1", + "ansicolors": "~0.3.2", + "ansistyles": "~0.1.3", + "aproba": "^2.0.0", + "archy": "~1.0.0", + "bin-links": "^1.1.7", + "bluebird": "^3.5.5", + "byte-size": "^5.0.1", + "cacache": "^12.0.3", + "call-limit": "^1.1.1", + "chownr": "^1.1.4", + "ci-info": "^2.0.0", + "cli-columns": "^3.1.2", + "cli-table3": "^0.5.1", + "cmd-shim": "^3.0.3", + "columnify": "~1.5.4", + "config-chain": "^1.1.12", + "detect-indent": "~5.0.0", + "detect-newline": "^2.1.0", + "dezalgo": "~1.0.3", + "editor": "~1.0.0", + "figgy-pudding": "^3.5.1", + "find-npm-prefix": "^1.0.2", + "fs-vacuum": "~1.2.10", + "fs-write-stream-atomic": "~1.0.10", + "gentle-fs": "^2.3.0", + "glob": "^7.1.6", + "graceful-fs": "^4.2.4", + "has-unicode": "~2.0.1", + "hosted-git-info": "^2.8.8", + "iferr": "^1.0.2", + "infer-owner": "^1.0.4", + "inflight": "~1.0.6", + "inherits": "^2.0.4", + "ini": "^1.3.5", + "init-package-json": "^1.10.3", + "is-cidr": "^3.0.0", + "json-parse-better-errors": "^1.0.2", + "lazy-property": "~1.0.0", + "libcipm": "^4.0.7", + "libnpm": "^3.0.1", + "libnpmaccess": "^3.0.2", + "libnpmhook": "^5.0.3", + "libnpmorg": "^1.0.1", + "libnpmsearch": "^2.0.2", + "libnpmteam": "^1.0.2", + "libnpx": "^10.2.2", + "lock-verify": "^2.1.0", + "lockfile": "^1.0.4", + "lodash._baseuniq": "~4.6.0", + "lodash.clonedeep": "~4.5.0", + "lodash.union": "~4.6.0", + "lodash.uniq": "~4.5.0", + "lodash.without": "~4.4.0", + "lru-cache": "^5.1.1", + "meant": "~1.0.1", + "mississippi": "^3.0.0", + "mkdirp": "^0.5.5", + "move-concurrently": "^1.0.1", + "node-gyp": "^5.1.0", + "nopt": "^4.0.3", + "normalize-package-data": "^2.5.0", + "npm-audit-report": "^1.3.2", + "npm-cache-filename": "~1.0.2", + "npm-install-checks": "^3.0.2", + "npm-lifecycle": "^3.1.4", + "npm-package-arg": "^6.1.1", + "npm-packlist": "^1.4.8", + "npm-pick-manifest": "^3.0.2", + "npm-profile": "^4.0.4", + "npm-registry-fetch": "^4.0.5", + "npm-user-validate": "~1.0.0", + "npmlog": "~4.1.2", + "once": "~1.4.0", + "opener": "^1.5.1", + "osenv": "^0.1.5", + "pacote": "^9.5.12", + "path-is-inside": "~1.0.2", + "promise-inflight": "~1.0.1", + "qrcode-terminal": "^0.12.0", + "query-string": "^6.8.2", + "qw": "~1.0.1", + "read": "~1.0.7", + "read-cmd-shim": "^1.0.5", + "read-installed": "~4.0.3", + "read-package-json": "^2.1.1", + "read-package-tree": "^5.3.1", + "readable-stream": "^3.6.0", + "readdir-scoped-modules": "^1.1.0", + "request": "^2.88.0", + "retry": "^0.12.0", + "rimraf": "^2.7.1", + "safe-buffer": "^5.1.2", + "semver": "^5.7.1", + "sha": "^3.0.0", + "slide": "~1.1.6", + "sorted-object": "~2.0.1", + "sorted-union-stream": "~2.1.3", + "ssri": "^6.0.1", + "stringify-package": "^1.0.1", + "tar": "^4.4.13", + "text-table": "~0.2.0", + "tiny-relative-date": "^1.3.0", + "uid-number": "0.0.6", + "umask": "~1.1.0", + "unique-filename": "^1.1.1", + "unpipe": "~1.0.0", + "update-notifier": "^2.5.0", + "uuid": "^3.3.3", + "validate-npm-package-license": "^3.0.4", + "validate-npm-package-name": "~3.0.0", + "which": "^1.3.1", + "worker-farm": "^1.7.0", + "write-file-atomic": "^2.4.3" + }, + "bundleDependencies": [ + "abbrev", + "ansicolors", + "ansistyles", + "aproba", + "archy", + "bin-links", + "bluebird", + "byte-size", + "cacache", + "call-limit", + "chownr", + "ci-info", + "cli-columns", + "cli-table3", + "cmd-shim", + "columnify", + "config-chain", + "debuglog", + "detect-indent", + "detect-newline", + "dezalgo", + "editor", + "figgy-pudding", + "find-npm-prefix", + "fs-vacuum", + "fs-write-stream-atomic", + "gentle-fs", + "glob", + "graceful-fs", + "has-unicode", + "hosted-git-info", + "iferr", + "imurmurhash", + "infer-owner", + "inflight", + "inherits", + "ini", + "init-package-json", + "is-cidr", + "json-parse-better-errors", + "JSONStream", + "lazy-property", + "libcipm", + "libnpm", + "libnpmaccess", + "libnpmhook", + "libnpmorg", + "libnpmsearch", + "libnpmteam", + "libnpx", + "lock-verify", + "lockfile", + "lodash._baseindexof", + "lodash._baseuniq", + "lodash._bindcallback", + "lodash._cacheindexof", + "lodash._createcache", + "lodash._getnative", + "lodash.clonedeep", + "lodash.restparam", + "lodash.union", + "lodash.uniq", + "lodash.without", + "lru-cache", + "meant", + "mississippi", + "mkdirp", + "move-concurrently", + "node-gyp", + "nopt", + "normalize-package-data", + "npm-audit-report", + "npm-cache-filename", + "npm-install-checks", + "npm-lifecycle", + "npm-package-arg", + "npm-packlist", + "npm-pick-manifest", + "npm-profile", + "npm-registry-fetch", + "npm-user-validate", + "npmlog", + "once", + "opener", + "osenv", + "pacote", + "path-is-inside", + "promise-inflight", + "qrcode-terminal", + "query-string", + "qw", + "read-cmd-shim", + "read-installed", + "read-package-json", + "read-package-tree", + "read", + "readable-stream", + "readdir-scoped-modules", + "request", + "retry", + "rimraf", + "safe-buffer", + "semver", + "sha", + "slide", + "sorted-object", + "sorted-union-stream", + "ssri", + "stringify-package", + "tar", + "text-table", + "tiny-relative-date", + "uid-number", + "umask", + "unique-filename", + "unpipe", + "update-notifier", + "uuid", + "validate-npm-package-license", + "validate-npm-package-name", + "which", + "worker-farm", + "write-file-atomic" + ], + "devDependencies": { + "deep-equal": "^1.0.1", + "get-stream": "^4.1.0", + "licensee": "^7.0.3", + "marked": "^0.6.3", + "marked-man": "^0.6.0", + "npm-registry-couchapp": "^2.7.4", + "npm-registry-mock": "^1.3.1", + "require-inject": "^1.4.4", + "sprintf-js": "^1.1.2", + "standard": "^11.0.1", + "tacks": "^1.3.0", + "tap": "^12.7.0", + "tar-stream": "^2.1.0" + }, + "scripts": { + "dumpconf": "env | grep npm | sort | uniq", + "prepare": "node bin/npm-cli.js rebuild && node bin/npm-cli.js --no-audit --no-timing prune --prefix=. --no-global && rimraf test/*/*/node_modules && make -j4 mandocs", + "preversion": "bash scripts/update-authors.sh && git add AUTHORS && git commit -m \"update AUTHORS\" || true", + "licenses": "licensee --production --errors-only", + "tap": "tap -J --timeout 300 --no-esm", + "tap-cover": "tap -J --nyc-arg=--cache --coverage --timeout 600 --no-esm", + "lint": "standard", + "pretest": "npm run lint", + "test": "npm run test-tap --", + "test:nocleanup": "NO_TEST_CLEANUP=1 npm run test --", + "sudotest": "sudo npm run tap -- \"test/tap/*.js\"", + "sudotest:nocleanup": "sudo NO_TEST_CLEANUP=1 npm run tap -- \"test/tap/*.js\"", + "posttest": "rimraf test/npm_cache*", + "test-coverage": "npm run tap-cover -- \"test/tap/*.js\" \"test/network/*.js\"", + "test-tap": "npm run tap -- \"test/tap/*.js\" \"test/network/*.js\"", + "test-node": "tap --timeout 240 \"test/tap/*.js\" \"test/network/*.js\"" + }, + "license": "Artistic-2.0", + "engines": { + "node": "6 >=6.2.0 || 8 || >=9.3.0" + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/node_modules/@actions/core/package.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/node_modules/@actions/core/package.json new file mode 100644 index 0000000000000000000000000000000000000000..8d7a3997488de1681ea1185e968b5bf4e2986d37 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/node_modules/@actions/core/package.json @@ -0,0 +1,44 @@ +{ + "name": "@actions/core", + "version": "1.6.0", + "description": "Actions core lib", + "keywords": [ + "github", + "actions", + "core" + ], + "homepage": "https://github.com/actions/toolkit/tree/main/packages/core", + "license": "MIT", + "main": "lib/core.js", + "types": "lib/core.d.ts", + "directories": { + "lib": "lib", + "test": "__tests__" + }, + "files": [ + "lib", + "!.DS_Store" + ], + "publishConfig": { + "access": "public" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/actions/toolkit.git", + "directory": "packages/core" + }, + "scripts": { + "audit-moderate": "npm install && npm audit --json --audit-level=moderate > audit.json", + "test": "echo \"Error: run tests from root\" && exit 1", + "tsc": "tsc" + }, + "bugs": { + "url": "https://github.com/actions/toolkit/issues" + }, + "dependencies": { + "@actions/http-client": "^1.0.11" + }, + "devDependencies": { + "@types/node": "^12.0.2" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/node_modules/cowsay/package.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/node_modules/cowsay/package.json new file mode 100644 index 0000000000000000000000000000000000000000..7492c95f16d90232564e6d7f53b17a104d4e6e9c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/node_modules/cowsay/package.json @@ -0,0 +1,59 @@ +{ + "name": "cowsay", + "version": "1.4.0", + "description": "cowsay is a configurable talking cow", + "keywords": [ + "cow", + "cowsay", + "cowthink", + "figlet", + "talking", + "ASCII" + ], + "homepage": "https://github.com/piuccio/cowsay", + "author": { + "name": "Fabio Crisci", + "email": "piuccio@gmail.com", + "url": "https://github.com/piuccio/" + }, + "license": "MIT", + "main": "./index", + "module": "./build/cowsay.es.js", + "browser": "./build/cowsay.umd.js", + "bin": { + "cowsay": "./cli.js", + "cowthink": "./cli.js" + }, + "files": [ + "index.js", + "cli.js", + "build/", + "cows/", + "lib/" + ], + "repository": { + "type": "git", + "url": "https://github.com/piuccio/cowsay.git" + }, + "scripts": { + "prepublish": "rollup -c", + "test": "node test.js" + }, + "dependencies": { + "get-stdin": "^5.0.1", + "optimist": "~0.6.1", + "string-width": "~2.1.1", + "strip-eof": "^1.0.0" + }, + "devDependencies": { + "nodeunit": "~0.11.1", + "rollup": "^0.48.2", + "rollup-plugin-commonjs": "^8.2.0", + "rollup-plugin-node-resolve": "^3.0.0", + "rollup-plugin-string": "^2.0.2" + }, + "preferGlobal": true, + "engines": { + "node": ">= 4" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/package-lock-2.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/package-lock-2.json new file mode 100644 index 0000000000000000000000000000000000000000..2373f27ca0acdfde12638abf434943b4fa321c2c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/package-lock-2.json @@ -0,0 +1,71 @@ +{ + "name": "npm", + "version": "6.14.6", + "lockfileVersion": 2, + "requires": true, + "packages": { + "": { + "name": "npm", + "version": "6.14.6", + "dependencies": { + "@types/react": "^18.0.9" + } + }, + "node_modules/@types/prop-types": { + "version": "15.7.5", + "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.5.tgz", + "integrity": "sha1-XxnSuFqY6VWANvajysyIGUIPBc8=", + "license": "MIT" + }, + "node_modules/@types/react": { + "version": "18.0.17", + "resolved": "https://registry.npmjs.org/@types/react/-/react-18.0.17.tgz", + "integrity": "sha1-RYPZwyLWfv5LOak10iPtzHBQzPQ=", + "license": "MIT", + "dependencies": { + "@types/prop-types": "*", + "@types/scheduler": "*", + "csstype": "^3.0.2" + } + }, + "node_modules/@types/scheduler": { + "version": "0.16.2", + "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.2.tgz", + "integrity": "sha1-GmL4lSVyPd4kuhsBsJK/XfitTTk=", + "license": "MIT" + }, + "node_modules/csstype": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.0.tgz", + "integrity": "sha1-TdysNxjXh8+d8NG30VAzklyPKfI=", + "license": "MIT" + } + }, + "dependencies": { + "@types/prop-types": { + "version": "15.7.5", + "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.5.tgz", + "integrity": "sha1-XxnSuFqY6VWANvajysyIGUIPBc8=" + }, + "@types/react": { + "version": "18.0.17", + "resolved": "https://registry.npmjs.org/@types/react/-/react-18.0.17.tgz", + "integrity": "sha1-RYPZwyLWfv5LOak10iPtzHBQzPQ=", + "requires": { + "@types/prop-types": "*", + "@types/scheduler": "*", + "csstype": "^3.0.2" + } + }, + "@types/scheduler": { + "version": "0.16.2", + "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.2.tgz", + "integrity": "sha1-GmL4lSVyPd4kuhsBsJK/XfitTTk=" + }, + "csstype": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.0.tgz", + "integrity": "sha1-TdysNxjXh8+d8NG30VAzklyPKfI=" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/package-lock.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/package-lock.json new file mode 100644 index 0000000000000000000000000000000000000000..7a14a9e21207d43cd5db97d3f6a4cc2c057de057 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pkg-lock/package-lock.json @@ -0,0 +1,81 @@ +{ + "requires": true, + "lockfileVersion": 1, + "dependencies": { + "@actions/core": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/@actions/core/-/core-1.6.0.tgz", + "integrity": "sha512-NB1UAZomZlCV/LmJqkLhNTqtKfFXJZAUPcfl/zqG7EfsQdeUJtaWO98SGbuQ3pydJ3fHl2CvI/51OKYlCYYcaw==", + "requires": { + "@actions/http-client": "^1.0.11" + } + }, + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" + }, + "cowsay": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/cowsay/-/cowsay-1.4.0.tgz", + "integrity": "sha512-rdg5k5PsHFVJheO/pmE3aDg2rUDDTfPJau6yYkZYlHFktUz+UxbE+IgnUAEyyCyv4noL5ltxXD0gZzmHPCy/9g==", + "requires": { + "get-stdin": "^5.0.1", + "optimist": "~0.6.1", + "string-width": "~2.1.1", + "strip-eof": "^1.0.0" + } + }, + "get-stdin": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-5.0.1.tgz", + "integrity": "sha1-Ei4WFZHiH/TFJTAwVpPyDmOTo5g=" + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" + }, + "minimist": { + "version": "0.0.10", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.10.tgz", + "integrity": "sha1-3j+YVD2/lggr5IrRoMfNqDYwHc8=" + }, + "optimist": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz", + "integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=", + "requires": { + "minimist": "~0.0.1", + "wordwrap": "~0.0.2" + } + }, + "string-width": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } + }, + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "requires": { + "ansi-regex": "^3.0.0" + } + }, + "strip-eof": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", + "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" + }, + "wordwrap": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz", + "integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pnpm/pnpm-lock.yaml b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pnpm/pnpm-lock.yaml new file mode 100644 index 0000000000000000000000000000000000000000..70e3575188e6a12a679f8df8b81f1a9a71005183 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/pnpm/pnpm-lock.yaml @@ -0,0 +1,72 @@ +lockfileVersion: 5.4 + +specifiers: + '@logux/eslint-config': ^47.2.0 + '@size-limit/preset-small-lib': ^8.0.0 + '@types/fs-extra': ^9.0.13 + '@types/node': ^18.6.4 + '@typescript-eslint/eslint-plugin': ^5.32.0 + '@typescript-eslint/parser': ^5.32.0 + c8: ^7.12.0 + check-dts: ^0.6.7 + clean-publish: ^4.0.1 + concat-with-sourcemaps: ^1.1.0 + eslint: ^8.21.0 + eslint-config-standard: ^17.0.0 + eslint-plugin-import: ^2.26.0 + eslint-plugin-n: ^15.2.4 + eslint-plugin-prefer-let: ^3.0.1 + eslint-plugin-promise: ^6.0.0 + fs-extra: ^10.1.0 + nanodelay: ^1.0.8 + nanoid: ^3.3.4 + nanospy: ^0.5.0 + picocolors: ^1.0.0 + postcss-parser-tests: ^8.5.1 + simple-git-hooks: ^2.8.0 + size-limit: ^8.0.0 + source-map-js: ^1.0.2 + strip-ansi: ^6.0.1 + ts-node: ^10.9.1 + typescript: ^4.7.4 + uvu: ^0.5.6 + +dependencies: + nanoid: 3.3.4 + picocolors: 1.0.0 + source-map-js: 1.0.2 + +devDependencies: + '@logux/eslint-config': 47.2.0_7hz3xvmviof7onfgk6hpedqcom + '@size-limit/preset-small-lib': 8.0.0_size-limit@8.0.0 + '@types/fs-extra': 9.0.13 + '@types/node': 18.6.4 + '@typescript-eslint/eslint-plugin': 5.32.0_iosr3hrei2tubxveewluhu5lhy + '@typescript-eslint/parser': 5.32.0_qugx7qdu5zevzvxaiqyxfiwquq + c8: 7.12.0 + check-dts: 0.6.7_typescript@4.7.4 + clean-publish: 4.0.1 + concat-with-sourcemaps: 1.1.0 + eslint: 8.21.0 + eslint-config-standard: 17.0.0_dfwa53o44x4e5xhsfv5mvfhk5a + eslint-plugin-import: 2.26.0_wuikv5nqgdfyng42xxm7lklfmi + eslint-plugin-n: 15.2.4_eslint@8.21.0 + eslint-plugin-prefer-let: 3.0.1 + eslint-plugin-promise: 6.0.0_eslint@8.21.0 + fs-extra: 10.1.0 + nanodelay: 1.0.8 + nanospy: 0.5.0 + postcss-parser-tests: 8.5.1 + simple-git-hooks: 2.8.0 + size-limit: 8.0.0 + strip-ansi: 6.0.1 + ts-node: 10.9.1_hn66opzbaneygq52jmwjxha6su + typescript: 4.7.4 + uvu: 0.5.6 + +packages: + /@bcoe/v8-coverage/0.2.3: + resolution: {integrity: sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw==} + dev: true + + # removed other packages diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/yarn-berry/yarn.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/yarn-berry/yarn.lock new file mode 100644 index 0000000000000000000000000000000000000000..8ceaa5008500bc15fc719c6c9835b8bd7f81cb28 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/yarn-berry/yarn.lock @@ -0,0 +1,110 @@ +# This file is generated by running "yarn install" inside your project. +# Manual changes might be lost - proceed with caution! + +__metadata: + version: 6 + cacheKey: 8 + +"@babel/code-frame@npm:7.10.4": + version: 7.10.4 + resolution: "@babel/code-frame@npm:7.10.4" + dependencies: + "@babel/highlight": ^7.10.4 + checksum: feb4543c8a509fe30f0f6e8d7aa84f82b41148b963b826cd330e34986f649a85cb63b2f13dd4effdf434ac555d16f14940b8ea5f4433297c2f5ff85486ded019 + languageName: node + linkType: hard + +"@types/minimatch@npm:3.0.3": + version: 3.0.3 + resolution: "@types/minimatch@npm:3.0.3" + checksum: b80259d55b96ef24cb3bb961b6dc18b943f2bb8838b4d8e7bead204f3173e551a416ffa49f9aaf1dc431277fffe36214118628eacf4aea20119df8835229901b + languageName: node + linkType: hard + +"@types/qs@npm:6.9.4": + version: 6.9.4 + resolution: "@types/qs@npm:6.9.4" + checksum: 77e509ed213f7694ae35f84a58b88da8744aad019e93556af6aeab4289287abbe71836c051d00649dbac0289ea199e408442590cfb1785009de11c3c8d0cbbea + languageName: node + linkType: hard + +"@types/qs@npm:6.9.4": + version: 6.9.4 + resolution: "@types/qs@npm:6.9.4" + checksum: 77e509ed213f7694ae35f84a58b88da8744aad019e93556af6aeab4289287abbe71836c051d00649dbac0289ea199e408442590cfb1785009de11c3c8d0cbbea + languageName: node + linkType: hard + +"ajv@npm:6.12.3": + version: 6.12.3 + resolution: "ajv@npm:6.12.3" + dependencies: + fast-deep-equal: ^3.1.1 + fast-json-stable-stringify: ^2.0.0 + json-schema-traverse: ^0.4.1 + uri-js: ^4.2.2 + checksum: ca559d34710e6969d33bc1316282e1ece4d4d99ff5fdca4bfe31947740f8f90e7824238cdc2954e499cf75b2432e3e6c56b32814ebe04fccf8abcc3fbf36b348 + languageName: node + linkType: hard + +"atob@npm:2.1.2": + version: 2.1.2 + resolution: "atob@npm:2.1.2" + bin: + atob: bin/atob.js + checksum: dfeeeb70090c5ebea7be4b9f787f866686c645d9f39a0d184c817252d0cf08455ed25267d79c03254d3be1f03ac399992a792edcd5ffb9c91e097ab5ef42833a + languageName: node + linkType: hard + +"aws-sdk@npm:2.706.0": + version: 2.706.0 + resolution: "aws-sdk@npm:2.706.0" + dependencies: + buffer: 4.9.2 + events: 1.1.1 + ieee754: 1.1.13 + jmespath: 0.15.0 + querystring: 0.2.0 + sax: 1.2.1 + url: 0.10.3 + uuid: 3.3.2 + xml2js: 0.4.19 + checksum: bf8ca2fc4f758bdebd04051ec15729affad3eb0e18eed4ae41db5b7d6ff2aed2cf3a12ae082c11b955df0125378c57b8406e1f91006e48f0c162fdbe4ee4e330 + languageName: node + linkType: hard + +"jhipster-core@npm:7.3.4": + version: 7.3.4 + resolution: "jhipster-core@npm:7.3.4" + dependencies: + chevrotain: 7.0.1 + fs-extra: 8.1.0 + lodash: 4.17.15 + winston: 3.2.1 + checksum: 6a97741d574a42a138f98596c668370b41ec8870335bcd758b6b890e279ba30d4d2be447f8cecbf416286f2c53636b406a63a773c7b00709c95af0a9a3f9b397 + languageName: node + linkType: hard + +"asn1.js@npm:4.10.1": + version: 4.10.1 + resolution: "asn1.js@npm:4.10.1" + dependencies: + bn.js: ^4.0.0 + inherits: ^2.0.1 + minimalistic-assert: ^1.0.0 + checksum: 9289a1a55401238755e3142511d7b8f6fc32f08c86ff68bd7100da8b6c186179dd6b14234fba2f7f6099afcd6758a816708485efe44bc5b2a6ec87d9ceeddbb5 + languageName: node + linkType: hard + +"c0n-fab_u.laTION@workspace:.": + version: 7.7.7 + resolution: "newtest@workspace:." + dependencies: + "@babel/code-frame": 7.10.4 + "@types/minimatch": 3.0.3 + "@types/qs": 6.9.4 + ajv: 6.12.3 + asn1.js: 4.10.1 + atob: 2.1.2 + languageName: unknown + linkType: soft diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/yarn/yarn.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/yarn/yarn.lock new file mode 100644 index 0000000000000000000000000000000000000000..f7ff8d510cc9d6ed6e1fa1a0d7d33f13a534d8e4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/javascript/test-fixtures/yarn/yarn.lock @@ -0,0 +1,84 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +"@babel/code-frame@^7.0.0", "@babel/code-frame@^7.10.4": + version "7.10.4" + resolved "https://registry.yarnpkg.com/@babel/code-frame/-/code-frame-7.10.4.tgz#168da1a36e90da68ae8d49c0f1b48c7c6249213a" + integrity sha512-vG6SvB6oYEhvgisZNFRmRCUkLz11c7rp+tbNTynGqc6mS1d5ATd/sGyV6W0KZZnXRKMTzZDRgQT3Ou9jhpAfUg== + dependencies: + "@babel/highlight" "^7.10.4" + +"@types/minimatch@*", "@types/minimatch@^3.0.3": + version "3.0.3" + resolved "https://registry.yarnpkg.com/@types/minimatch/-/minimatch-3.0.3.tgz#3dca0e3f33b200fc7d1139c0cd96c1268cadfd9d" + integrity sha512-tHq6qdbT9U1IRSGf14CL0pUlULksvY9OZ+5eEgl1N7t+OA3tGvNpxJCzuKQlsNgCVwbAs670L1vcVQi8j9HjnA== + +"@types/qs@^6.2.31": + version "6.9.4" + resolved "https://registry.yarnpkg.com/@types/qs/-/qs-6.9.4.tgz#a59e851c1ba16c0513ea123830dd639a0a15cb6a" + integrity sha512-+wYo+L6ZF6BMoEjtf8zB2esQsqdV6WsjRK/GP9WOgLPrq87PbNWgIxS76dS5uvl/QXtHGakZmwTznIfcPXcKlQ== + +"@types/qs@^6.2.31": + version "6.9.4" + resolved "https://registry.yarnpkg.com/@types/qs/-/qs-6.9.4.tgz#a59e851c1ba16c0513ea123830dd639a0a15cb6a" + integrity sha512-+wYo+L6ZF6BMoEjtf8zB2esQsqdV6WsjRK/GP9WOgLPrq87PbNWgIxS76dS5uvl/QXtHGakZmwTznIfcPXcKlQ== + +ajv@^6.10.2, ajv@^6.5.5: + version "6.12.3" + resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.12.3.tgz#18c5af38a111ddeb4f2697bd78d68abc1cabd706" + integrity sha512-4K0cK3L1hsqk9xIb2z9vs/XU+PGJZ9PNpJRDS9YLzmNdX6jmVPfamLvTJr0aDAusnHyCHO6MjzlkAsgtqp9teA== + dependencies: + fast-deep-equal "^3.1.1" + fast-json-stable-stringify "^2.0.0" + json-schema-traverse "^0.4.1" + uri-js "^4.2.2" + +atob@^2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/atob/-/atob-2.1.2.tgz#6d9517eb9e030d2436666651e86bd9f6f13533c9" + integrity sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg== + +atob@^2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/atob/-/atob-2.1.2.tgz#6d9517eb9e030d2436666651e86bd9f6f13533c9" + integrity sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg== + +aws-sdk@2.706.0: + version "2.706.0" + resolved "https://registry.yarnpkg.com/aws-sdk/-/aws-sdk-2.706.0.tgz#09f65e9a91ecac5a635daf934082abae30eca953" + integrity sha512-7GT+yrB5Wb/zOReRdv/Pzkb2Qt+hz6B/8FGMVaoysX3NryHvQUdz7EQWi5yhg9CxOjKxdw5lFwYSs69YlSp1KA== + dependencies: + buffer "4.9.2" + events "1.1.1" + ieee754 "1.1.13" + jmespath "0.15.0" + querystring "0.2.0" + sax "1.2.1" + url "0.10.3" + uuid "3.3.2" + xml2js "0.4.19" + +jhipster-core@7.3.4: + version "7.3.4" + resolved "https://registry.yarnpkg.com/jhipster-core/-/jhipster-core-7.3.4.tgz#c34b8c97c7f4e8b7518dae015517e2112c73cc80" + integrity sha512-AUhT69kNkqppaJZVfan/xnKG4Gs9Ggj7YLtTZFVe+xg+THrbMb5Ng7PL07PDlDw4KAEA33GMCwuAf65E8EpC4g== + dependencies: + chevrotain "7.0.1" + fs-extra "8.1.0" + lodash "4.17.15" + winston "3.2.1" + +asn1.js@^4.0.0: + version "4.10.1" + resolved "https://registry.yarnpkg.com/asn1.js/-/asn1.js-4.10.1.tgz#b9c2bf5805f1e64aadeed6df3a2bfafb5a73f5a0" + integrity sha512-p32cOF5q0Zqs9uBiONKYLm6BClCoBCM5O9JfeUSlnQLBTxYdTK+pW+nXflm8UkKd2UYlEbYz5qEi0JuZR9ckSw== + dependencies: + bn.js "^4.0.0" + inherits "^2.0.1" + minimalistic-assert "^1.0.0" + +c0n-fab_u.laTION@^7.0.0: + version "7.7.7" + resolved "https://registry.yarnpkg.com/something-i-made-up/-/c0n-fab_u.laTION-7.7.7.tgz#b9c2bf5805f1e64aadeed6df3a2bfafb5a73f5a0" + integrity sha512-p32cOF5q0Zqs9uBiONKYLm6BClCoBCM5O9JfeUSlnQLBTxYdTK+pW+nXflm8UkKd2UYlEbYz5qEi0JuZR9ckSw== diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..6528bac66fd162983559f1e702ae9c5001eb9f5b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/cataloger.go @@ -0,0 +1,26 @@ +/* +Package php provides a concrete Cataloger implementation for PHP ecosystem files. +*/ +package php + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewPHPComposerInstalledCataloger returns a new cataloger for PHP installed.json files. +func NewPHPComposerInstalledCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/installed.json": parseInstalledJSON, + } + + return common.NewGenericCataloger(nil, globParsers, "php-composer-installed-cataloger") +} + +// NewPHPComposerLockCataloger returns a new cataloger for PHP composer.lock files. +func NewPHPComposerLockCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/composer.lock": parseComposerLock, + } + + return common.NewGenericCataloger(nil, globParsers, "php-composer-lock-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_composer_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_composer_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..1ee120e609c544576a74f00d1d0d77ccf81e4ff8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_composer_lock.go @@ -0,0 +1,44 @@ +package php + +import ( + "encoding/json" + "fmt" + "io" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" +) + +type composerLock struct { + Packages []pkg.PhpComposerJSONMetadata `json:"packages"` + PackageDev []pkg.PhpComposerJSONMetadata `json:"packages-dev"` +} + +// parseComposerLock is a parser function for Composer.lock contents, returning "Default" php packages discovered. +func parseComposerLock(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + packages := make([]*pkg.Package, 0) + dec := json.NewDecoder(reader) + + for { + var lock composerLock + if err := dec.Decode(&lock); err == io.EOF { + break + } else if err != nil { + return nil, nil, fmt.Errorf("failed to parse composer.lock file: %w", err) + } + for _, pkgMeta := range lock.Packages { + version := pkgMeta.Version + name := pkgMeta.Name + packages = append(packages, &pkg.Package{ + Name: name, + Version: version, + Language: pkg.PHP, + Type: pkg.PhpComposerPkg, + MetadataType: pkg.PhpComposerJSONMetadataType, + Metadata: pkgMeta, + }) + } + } + + return packages, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_composer_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_composer_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..c0658aa51c4af4a638e500441ffd85fb544e4ac7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_composer_lock_test.go @@ -0,0 +1,122 @@ +package php + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseComposerFileLock(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "adoy/fastcgi-client", + Version: "1.0.2", + Language: pkg.PHP, + Type: pkg.PhpComposerPkg, + MetadataType: pkg.PhpComposerJSONMetadataType, + Metadata: pkg.PhpComposerJSONMetadata{ + Name: "adoy/fastcgi-client", + Version: "1.0.2", + Source: pkg.PhpComposerExternalReference{ + Type: "git", + URL: "https://github.com/adoy/PHP-FastCGI-Client.git", + Reference: "6d9a552f0206a1db7feb442824540aa6c55e5b27", + }, + Dist: pkg.PhpComposerExternalReference{ + Type: "zip", + URL: "https://api.github.com/repos/adoy/PHP-FastCGI-Client/zipball/6d9a552f0206a1db7feb442824540aa6c55e5b27", + Reference: "6d9a552f0206a1db7feb442824540aa6c55e5b27", + }, + Type: "library", + NotificationURL: "https://packagist.org/downloads/", + License: []string{ + "MIT", + }, + Authors: []pkg.PhpComposerAuthors{ + { + Name: "Pierrick Charron", + Email: "pierrick@adoy.net", + }, + }, + Description: "Lightweight, single file FastCGI client for PHP.", + Keywords: []string{ + "fastcgi", + "fcgi", + }, + Time: "2019-12-11T13:49:21+00:00", + }, + }, + { + Name: "alcaeus/mongo-php-adapter", + Version: "1.1.11", + Language: pkg.PHP, + Type: pkg.PhpComposerPkg, + MetadataType: pkg.PhpComposerJSONMetadataType, + Metadata: pkg.PhpComposerJSONMetadata{ + Name: "alcaeus/mongo-php-adapter", + Version: "1.1.11", + Source: pkg.PhpComposerExternalReference{ + Type: "git", + URL: "https://github.com/alcaeus/mongo-php-adapter.git", + Reference: "43b6add94c8b4cb9890d662cba4c0defde733dcf", + }, + Dist: pkg.PhpComposerExternalReference{ + Type: "zip", + URL: "https://api.github.com/repos/alcaeus/mongo-php-adapter/zipball/43b6add94c8b4cb9890d662cba4c0defde733dcf", + Reference: "43b6add94c8b4cb9890d662cba4c0defde733dcf", + }, + Require: map[string]string{ + "ext-ctype": "*", + "ext-hash": "*", + "ext-mongodb": "^1.2.0", + "mongodb/mongodb": "^1.0.1", + "php": "^5.6 || ^7.0", + }, + Provide: map[string]string{ + "ext-mongo": "1.6.14", + }, + RequireDev: map[string]string{ + "phpunit/phpunit": "^5.7.27 || ^6.0 || ^7.0", + "squizlabs/php_codesniffer": "^3.2", + }, + Type: "library", + NotificationURL: "https://packagist.org/downloads/", + License: []string{ + "MIT", + }, + Authors: []pkg.PhpComposerAuthors{ + { + Name: "alcaeus", + Email: "alcaeus@alcaeus.org", + }, + { + Name: "Olivier Lechevalier", + Email: "olivier.lechevalier@gmail.com", + }, + }, + Description: "Adapter to provide ext-mongo interface on top of mongo-php-libary", + Keywords: []string{ + "database", + "mongodb", + }, + Time: "2019-11-11T20:47:32+00:00", + }, + }, + } + fixture, err := os.Open("test-fixtures/composer.lock") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseComposerLock(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse requirements: %+v", err) + } + + for _, d := range deep.Equal(expected, actual) { + t.Errorf("diff: %+v", d) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_installed_json.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_installed_json.go new file mode 100644 index 0000000000000000000000000000000000000000..3afa1f2fe89f41b67225aa4ea9dd8b7d7cbd77c2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_installed_json.go @@ -0,0 +1,69 @@ +package php + +import ( + "encoding/json" + "fmt" + "io" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// Note: composer version 2 introduced a new structure for the installed.json file, so we support both +type installedJSONComposerV2 struct { + Packages []pkg.PhpComposerJSONMetadata `json:"packages"` +} + +func (w *installedJSONComposerV2) UnmarshalJSON(data []byte) error { + type compv2 struct { + Packages []pkg.PhpComposerJSONMetadata `json:"packages"` + } + compv2er := new(compv2) + err := json.Unmarshal(data, &compv2er) + if err != nil { + // If we had an err or, we may be dealing with a composer v.1 installed.json + // which should be all arrays + var packages []pkg.PhpComposerJSONMetadata + err := json.Unmarshal(data, &packages) + if err != nil { + return err + } + w.Packages = packages + return nil + } + w.Packages = compv2er.Packages + return nil +} + +// integrity check +var _ common.ParserFn = parseComposerLock + +// parseComposerLock is a parser function for Composer.lock contents, returning "Default" php packages discovered. +func parseInstalledJSON(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + packages := make([]*pkg.Package, 0) + dec := json.NewDecoder(reader) + + for { + var lock installedJSONComposerV2 + if err := dec.Decode(&lock); err == io.EOF { + break + } else if err != nil { + return nil, nil, fmt.Errorf("failed to parse composer.lock file: %w", err) + } + for _, pkgMeta := range lock.Packages { + version := pkgMeta.Version + name := pkgMeta.Name + packages = append(packages, &pkg.Package{ + Name: name, + Version: version, + Language: pkg.PHP, + Type: pkg.PhpComposerPkg, + MetadataType: pkg.PhpComposerJSONMetadataType, + Metadata: pkgMeta, + }) + } + } + + return packages, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_installed_json_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_installed_json_test.go new file mode 100644 index 0000000000000000000000000000000000000000..9c925afce275e69f907978d190cf6e059488db3b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/parse_installed_json_test.go @@ -0,0 +1,155 @@ +package php + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +var expectedInstalledJsonPackages = []*pkg.Package{ + { + Name: "asm89/stack-cors", + Version: "1.3.0", + Language: pkg.PHP, + Type: pkg.PhpComposerPkg, + MetadataType: pkg.PhpComposerJSONMetadataType, + Metadata: pkg.PhpComposerJSONMetadata{ + Name: "asm89/stack-cors", + Version: "1.3.0", + Source: pkg.PhpComposerExternalReference{ + Type: "git", + URL: "https://github.com/asm89/stack-cors.git", + Reference: "b9c31def6a83f84b4d4a40d35996d375755f0e08", + }, + Dist: pkg.PhpComposerExternalReference{ + Type: "zip", + URL: "https://api.github.com/repos/asm89/stack-cors/zipball/b9c31def6a83f84b4d4a40d35996d375755f0e08", + Reference: "b9c31def6a83f84b4d4a40d35996d375755f0e08", + }, + Require: map[string]string{ + "php": ">=5.5.9", + "symfony/http-foundation": "~2.7|~3.0|~4.0|~5.0", + "symfony/http-kernel": "~2.7|~3.0|~4.0|~5.0", + }, + RequireDev: map[string]string{ + "phpunit/phpunit": "^5.0 || ^4.8.10", + "squizlabs/php_codesniffer": "^2.3", + }, + Time: "2019-12-24T22:41:47+00:00", + Type: "library", + NotificationURL: "https://packagist.org/downloads/", + License: []string{ + "MIT", + }, + Authors: []pkg.PhpComposerAuthors{ + { + Name: "Alexander", + Email: "iam.asm89@gmail.com", + }, + }, + + Description: "Cross-origin resource sharing library and stack middleware", + Homepage: "https://github.com/asm89/stack-cors", + Keywords: []string{ + "cors", + "stack", + }, + }, + }, + { + Name: "behat/mink", + Version: "v1.8.1", + Language: pkg.PHP, + Type: pkg.PhpComposerPkg, + MetadataType: pkg.PhpComposerJSONMetadataType, + Metadata: pkg.PhpComposerJSONMetadata{ + Name: "behat/mink", + Version: "v1.8.1", + Source: pkg.PhpComposerExternalReference{ + Type: "git", + URL: "https://github.com/minkphp/Mink.git", + Reference: "07c6a9fe3fa98c2de074b25d9ed26c22904e3887", + }, + Dist: pkg.PhpComposerExternalReference{ + Type: "zip", + URL: "https://api.github.com/repos/minkphp/Mink/zipball/07c6a9fe3fa98c2de074b25d9ed26c22904e3887", + Reference: "07c6a9fe3fa98c2de074b25d9ed26c22904e3887", + }, + Require: map[string]string{ + "php": ">=5.3.1", + "symfony/css-selector": "^2.7|^3.0|^4.0|^5.0", + }, + RequireDev: map[string]string{ + "phpunit/phpunit": "^4.8.36 || ^5.7.27 || ^6.5.14 || ^7.5.20", + "symfony/debug": "^2.7|^3.0|^4.0", + "symfony/phpunit-bridge": "^3.4.38 || ^5.0.5", + }, + Suggest: map[string]string{ + "behat/mink-browserkit-driver": "extremely fast headless driver for Symfony\\Kernel-based apps (Sf2, Silex)", + "behat/mink-goutte-driver": "fast headless driver for any app without JS emulation", + "behat/mink-selenium2-driver": "slow, but JS-enabled driver for any app (requires Selenium2)", + "behat/mink-zombie-driver": "fast and JS-enabled headless driver for any app (requires node.js)", + "dmore/chrome-mink-driver": "fast and JS-enabled driver for any app (requires chromium or google chrome)", + }, + Time: "2020-03-11T15:45:53+00:00", + Type: "library", + NotificationURL: "https://packagist.org/downloads/", + License: []string{ + "MIT", + }, + Authors: []pkg.PhpComposerAuthors{ + { + Name: "Konstantin Kudryashov", + Email: "ever.zet@gmail.com", + Homepage: "http://everzet.com", + }, + }, + + Description: "Browser controller/emulator abstraction for PHP", + Homepage: "http://mink.behat.org/", + Keywords: []string{ + "browser", + "testing", + "web", + }, + }, + }, +} + +func TestParseInstalledJsonComposerV1(t *testing.T) { + + fixture, err := os.Open("test-fixtures/vendor/composer_1/installed.json") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseInstalledJSON(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse requirements: %+v", err) + } + differences := deep.Equal(expectedInstalledJsonPackages, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} + +func TestParseInstalledJsonComposerV2(t *testing.T) { + fixture, err := os.Open("test-fixtures/vendor/composer_2/installed.json") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseInstalledJSON(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse requirements: %+v", err) + } + differences := deep.Equal(expectedInstalledJsonPackages, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/composer.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/composer.lock new file mode 100644 index 0000000000000000000000000000000000000000..b9388fd7b370c6406176e47efc7a343ede88a98b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/composer.lock @@ -0,0 +1,298 @@ +{ + "_readme": [ + "This file locks the dependencies of your project to a known state", + "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", + "This file is @generated automatically" + ], + "content-hash": "746ba78c06aef0cf954135ea909f9eb9", + "packages": [ + { + "name": "adoy/fastcgi-client", + "version": "1.0.2", + "source": { + "type": "git", + "url": "https://github.com/adoy/PHP-FastCGI-Client.git", + "reference": "6d9a552f0206a1db7feb442824540aa6c55e5b27" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/adoy/PHP-FastCGI-Client/zipball/6d9a552f0206a1db7feb442824540aa6c55e5b27", + "reference": "6d9a552f0206a1db7feb442824540aa6c55e5b27", + "shasum": "" + }, + "type": "library", + "autoload": { + "psr-0": { + "Adoy\\FastCGI\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Pierrick Charron", + "email": "pierrick@adoy.net" + } + ], + "description": "Lightweight, single file FastCGI client for PHP.", + "keywords": [ + "fastcgi", + "fcgi" + ], + "time": "2019-12-11T13:49:21+00:00" + }, + { + "name": "alcaeus/mongo-php-adapter", + "version": "1.1.11", + "source": { + "type": "git", + "url": "https://github.com/alcaeus/mongo-php-adapter.git", + "reference": "43b6add94c8b4cb9890d662cba4c0defde733dcf" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/alcaeus/mongo-php-adapter/zipball/43b6add94c8b4cb9890d662cba4c0defde733dcf", + "reference": "43b6add94c8b4cb9890d662cba4c0defde733dcf", + "shasum": "" + }, + "require": { + "ext-ctype": "*", + "ext-hash": "*", + "ext-mongodb": "^1.2.0", + "mongodb/mongodb": "^1.0.1", + "php": "^5.6 || ^7.0" + }, + "provide": { + "ext-mongo": "1.6.14" + }, + "require-dev": { + "phpunit/phpunit": "^5.7.27 || ^6.0 || ^7.0", + "squizlabs/php_codesniffer": "^3.2" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.1.x-dev" + } + }, + "autoload": { + "psr-0": { + "Mongo": "lib/Mongo" + }, + "psr-4": { + "Alcaeus\\MongoDbAdapter\\": "lib/Alcaeus/MongoDbAdapter" + }, + "files": [ + "lib/Mongo/functions.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "alcaeus", + "email": "alcaeus@alcaeus.org" + }, + { + "name": "Olivier Lechevalier", + "email": "olivier.lechevalier@gmail.com" + } + ], + "description": "Adapter to provide ext-mongo interface on top of mongo-php-libary", + "keywords": [ + "database", + "mongodb" + ], + "time": "2019-11-11T20:47:32+00:00" + } + ], + "packages-dev": [ + { + "name": "behat/gherkin", + "version": "v4.6.2", + "source": { + "type": "git", + "url": "https://github.com/Behat/Gherkin.git", + "reference": "51ac4500c4dc30cbaaabcd2f25694299df666a31" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/Behat/Gherkin/zipball/51ac4500c4dc30cbaaabcd2f25694299df666a31", + "reference": "51ac4500c4dc30cbaaabcd2f25694299df666a31", + "shasum": "" + }, + "require": { + "php": ">=5.3.1" + }, + "require-dev": { + "phpunit/phpunit": "~4.5|~5", + "symfony/phpunit-bridge": "~2.7|~3|~4", + "symfony/yaml": "~2.3|~3|~4" + }, + "suggest": { + "symfony/yaml": "If you want to parse features, represented in YAML files" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.4-dev" + } + }, + "autoload": { + "psr-0": { + "Behat\\Gherkin": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Konstantin Kudryashov", + "email": "ever.zet@gmail.com", + "homepage": "http://everzet.com" + } + ], + "description": "Gherkin DSL parser for PHP 5.3", + "homepage": "http://behat.org/", + "keywords": [ + "BDD", + "Behat", + "Cucumber", + "DSL", + "gherkin", + "parser" + ], + "time": "2020-03-17T14:03:26+00:00" + }, + { + "name": "codeception/codeception", + "version": "4.1.6", + "source": { + "type": "git", + "url": "https://github.com/Codeception/Codeception.git", + "reference": "5515b6a6c6f1e1c909aaff2e5f3a15c177dfd1a9" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/Codeception/Codeception/zipball/5515b6a6c6f1e1c909aaff2e5f3a15c177dfd1a9", + "reference": "5515b6a6c6f1e1c909aaff2e5f3a15c177dfd1a9", + "shasum": "" + }, + "require": { + "behat/gherkin": "^4.4.0", + "codeception/lib-asserts": "^1.0", + "codeception/phpunit-wrapper": ">6.0.15 <6.1.0 | ^6.6.1 | ^7.7.1 | ^8.1.1 | ^9.0", + "codeception/stub": "^2.0 | ^3.0", + "ext-curl": "*", + "ext-json": "*", + "ext-mbstring": "*", + "guzzlehttp/psr7": "~1.4", + "php": ">=5.6.0 <8.0", + "symfony/console": ">=2.7 <6.0", + "symfony/css-selector": ">=2.7 <6.0", + "symfony/event-dispatcher": ">=2.7 <6.0", + "symfony/finder": ">=2.7 <6.0", + "symfony/yaml": ">=2.7 <6.0" + }, + "require-dev": { + "codeception/module-asserts": "*@dev", + "codeception/module-cli": "*@dev", + "codeception/module-db": "*@dev", + "codeception/module-filesystem": "*@dev", + "codeception/module-phpbrowser": "*@dev", + "codeception/specify": "~0.3", + "codeception/util-universalframework": "*@dev", + "monolog/monolog": "~1.8", + "squizlabs/php_codesniffer": "~2.0", + "symfony/process": ">=2.7 <6.0", + "vlucas/phpdotenv": "^2.0 | ^3.0 | ^4.0" + }, + "suggest": { + "codeception/specify": "BDD-style code blocks", + "codeception/verify": "BDD-style assertions", + "hoa/console": "For interactive console functionality", + "stecman/symfony-console-completion": "For BASH autocompletion", + "symfony/phpunit-bridge": "For phpunit-bridge support" + }, + "bin": [ + "codecept" + ], + "type": "library", + "extra": { + "branch-alias": [] + }, + "autoload": { + "psr-4": { + "Codeception\\": "src/Codeception", + "Codeception\\Extension\\": "ext" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Bodnarchuk", + "email": "davert@mail.ua", + "homepage": "http://codegyre.com" + } + ], + "description": "BDD-style testing framework", + "homepage": "http://codeception.com/", + "keywords": [ + "BDD", + "TDD", + "acceptance testing", + "functional testing", + "unit testing" + ], + "time": "2020-06-07T16:31:51+00:00" + } + ], + "aliases": [], + "minimum-stability": "stable", + "stability-flags": { + "intelligence/bt-base": 20, + "intelligence/bt-common": 20, + "intelligence/bt-lib-tools": 20, + "intelligence/ci-lib-cache": 20, + "intelligence/ci-lib-client": 20, + "intelligence/ci-lib-contributed": 20, + "intelligence/ci-lib-eav": 20, + "intelligence/ci-lib-report": 20, + "intelligence/git-leaks-elastic-client": 20, + "intelligence/phishing-elastic-client": 20, + "libs/gib-sso-client": 20, + "mozhin/phplib": 20 + }, + "prefer-stable": false, + "prefer-lowest": false, + "platform": { + "php": "^7.4.0", + "ext-amqp": "^1.9", + "ext-ctype": "*", + "ext-curl": "^7.4", + "ext-date": "^7.4", + "ext-fileinfo": "*", + "ext-geoip": "^1.1", + "ext-gettext": "*", + "ext-iconv": "*", + "ext-imagick": "^3.4", + "ext-imap": "^7.4", + "ext-intl": "^7.4", + "ext-json": "*", + "ext-mbstring": "^7.4", + "ext-mongodb": "^1.4", + "ext-mysqli": "^7.4", + "ext-pdo_mysql": "^7.4", + "ext-redis": ">=3.1" + }, + "platform-dev": [] +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/vendor/composer_1/installed.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/vendor/composer_1/installed.json new file mode 100644 index 0000000000000000000000000000000000000000..2f7274adadad3a121f47154f619d9d899048fb40 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/vendor/composer_1/installed.json @@ -0,0 +1,127 @@ +[ + { + "name": "asm89/stack-cors", + "version": "1.3.0", + "version_normalized": "1.3.0.0", + "source": { + "type": "git", + "url": "https://github.com/asm89/stack-cors.git", + "reference": "b9c31def6a83f84b4d4a40d35996d375755f0e08" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/asm89/stack-cors/zipball/b9c31def6a83f84b4d4a40d35996d375755f0e08", + "reference": "b9c31def6a83f84b4d4a40d35996d375755f0e08", + "shasum": "" + }, + "require": { + "php": ">=5.5.9", + "symfony/http-foundation": "~2.7|~3.0|~4.0|~5.0", + "symfony/http-kernel": "~2.7|~3.0|~4.0|~5.0" + }, + "require-dev": { + "phpunit/phpunit": "^5.0 || ^4.8.10", + "squizlabs/php_codesniffer": "^2.3" + }, + "time": "2019-12-24T22:41:47+00:00", + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.2-dev" + } + }, + "installation-source": "dist", + "autoload": { + "psr-4": { + "Asm89\\Stack\\": "src/Asm89/Stack/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Alexander", + "email": "iam.asm89@gmail.com" + } + ], + "description": "Cross-origin resource sharing library and stack middleware", + "homepage": "https://github.com/asm89/stack-cors", + "keywords": [ + "cors", + "stack" + ], + "support": { + "issues": "https://github.com/asm89/stack-cors/issues", + "source": "https://github.com/asm89/stack-cors/tree/1.3.0" + } + }, + { + "name": "behat/mink", + "version": "v1.8.1", + "version_normalized": "1.8.1.0", + "source": { + "type": "git", + "url": "https://github.com/minkphp/Mink.git", + "reference": "07c6a9fe3fa98c2de074b25d9ed26c22904e3887" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/minkphp/Mink/zipball/07c6a9fe3fa98c2de074b25d9ed26c22904e3887", + "reference": "07c6a9fe3fa98c2de074b25d9ed26c22904e3887", + "shasum": "" + }, + "require": { + "php": ">=5.3.1", + "symfony/css-selector": "^2.7|^3.0|^4.0|^5.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.8.36 || ^5.7.27 || ^6.5.14 || ^7.5.20", + "symfony/debug": "^2.7|^3.0|^4.0", + "symfony/phpunit-bridge": "^3.4.38 || ^5.0.5" + }, + "suggest": { + "behat/mink-browserkit-driver": "extremely fast headless driver for Symfony\\Kernel-based apps (Sf2, Silex)", + "behat/mink-goutte-driver": "fast headless driver for any app without JS emulation", + "behat/mink-selenium2-driver": "slow, but JS-enabled driver for any app (requires Selenium2)", + "behat/mink-zombie-driver": "fast and JS-enabled headless driver for any app (requires node.js)", + "dmore/chrome-mink-driver": "fast and JS-enabled driver for any app (requires chromium or google chrome)" + }, + "time": "2020-03-11T15:45:53+00:00", + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.8.x-dev" + } + }, + "installation-source": "dist", + "autoload": { + "psr-4": { + "Behat\\Mink\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Konstantin Kudryashov", + "email": "ever.zet@gmail.com", + "homepage": "http://everzet.com" + } + ], + "description": "Browser controller/emulator abstraction for PHP", + "homepage": "http://mink.behat.org/", + "keywords": [ + "browser", + "testing", + "web" + ], + "support": { + "issues": "https://github.com/minkphp/Mink/issues", + "source": "https://github.com/minkphp/Mink/tree/v1.8.1" + } + } +] diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/vendor/composer_2/installed.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/vendor/composer_2/installed.json new file mode 100644 index 0000000000000000000000000000000000000000..eb903f214c55c80f82378f3bd2e285428e5138e2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/php/test-fixtures/vendor/composer_2/installed.json @@ -0,0 +1,135 @@ +{ + "packages": [ + { + "name": "asm89/stack-cors", + "version": "1.3.0", + "version_normalized": "1.3.0.0", + "source": { + "type": "git", + "url": "https://github.com/asm89/stack-cors.git", + "reference": "b9c31def6a83f84b4d4a40d35996d375755f0e08" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/asm89/stack-cors/zipball/b9c31def6a83f84b4d4a40d35996d375755f0e08", + "reference": "b9c31def6a83f84b4d4a40d35996d375755f0e08", + "shasum": "" + }, + "require": { + "php": ">=5.5.9", + "symfony/http-foundation": "~2.7|~3.0|~4.0|~5.0", + "symfony/http-kernel": "~2.7|~3.0|~4.0|~5.0" + }, + "require-dev": { + "phpunit/phpunit": "^5.0 || ^4.8.10", + "squizlabs/php_codesniffer": "^2.3" + }, + "time": "2019-12-24T22:41:47+00:00", + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.2-dev" + } + }, + "installation-source": "dist", + "autoload": { + "psr-4": { + "Asm89\\Stack\\": "src/Asm89/Stack/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Alexander", + "email": "iam.asm89@gmail.com" + } + ], + "description": "Cross-origin resource sharing library and stack middleware", + "homepage": "https://github.com/asm89/stack-cors", + "keywords": [ + "cors", + "stack" + ], + "support": { + "issues": "https://github.com/asm89/stack-cors/issues", + "source": "https://github.com/asm89/stack-cors/tree/1.3.0" + }, + "install-path": "../asm89/stack-cors" + }, + { + "name": "behat/mink", + "version": "v1.8.1", + "version_normalized": "1.8.1.0", + "source": { + "type": "git", + "url": "https://github.com/minkphp/Mink.git", + "reference": "07c6a9fe3fa98c2de074b25d9ed26c22904e3887" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/minkphp/Mink/zipball/07c6a9fe3fa98c2de074b25d9ed26c22904e3887", + "reference": "07c6a9fe3fa98c2de074b25d9ed26c22904e3887", + "shasum": "" + }, + "require": { + "php": ">=5.3.1", + "symfony/css-selector": "^2.7|^3.0|^4.0|^5.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.8.36 || ^5.7.27 || ^6.5.14 || ^7.5.20", + "symfony/debug": "^2.7|^3.0|^4.0", + "symfony/phpunit-bridge": "^3.4.38 || ^5.0.5" + }, + "suggest": { + "behat/mink-browserkit-driver": "extremely fast headless driver for Symfony\\Kernel-based apps (Sf2, Silex)", + "behat/mink-goutte-driver": "fast headless driver for any app without JS emulation", + "behat/mink-selenium2-driver": "slow, but JS-enabled driver for any app (requires Selenium2)", + "behat/mink-zombie-driver": "fast and JS-enabled headless driver for any app (requires node.js)", + "dmore/chrome-mink-driver": "fast and JS-enabled driver for any app (requires chromium or google chrome)" + }, + "time": "2020-03-11T15:45:53+00:00", + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.8.x-dev" + } + }, + "installation-source": "dist", + "autoload": { + "psr-4": { + "Behat\\Mink\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Konstantin Kudryashov", + "email": "ever.zet@gmail.com", + "homepage": "http://everzet.com" + } + ], + "description": "Browser controller/emulator abstraction for PHP", + "homepage": "http://mink.behat.org/", + "keywords": [ + "browser", + "testing", + "web" + ], + "support": { + "issues": "https://github.com/minkphp/Mink/issues", + "source": "https://github.com/minkphp/Mink/tree/v1.8.1" + }, + "install-path": "../behat/mink" + } + ], + "dev": true, + "dev-package-names": [ + "behat/mink" + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..a8cd5b7964605f7ea29271dea7446d9f10e51168 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/cataloger.go @@ -0,0 +1,151 @@ +/* +Package portage provides a concrete Cataloger implementation for Gentoo Portage. +*/ +package portage + +import ( + "bufio" + "fmt" + "path" + "path/filepath" + "regexp" + "sort" + "strconv" + "strings" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +var ( + cpvRe = regexp.MustCompile(`/([^/]*/[\w+][\w+-]*)-((\d+)((\.\d+)*)([a-z]?)((_(pre|p|beta|alpha|rc)\d*)*)(-r\d+)?)/CONTENTS$`) +) + +type Cataloger struct{} + +// NewPortageCataloger returns a new Portage package cataloger object. +func NewPortageCataloger() *Cataloger { + return &Cataloger{} +} + +// Name returns a string that uniquely describes a cataloger +func (c *Cataloger) Name() string { + return "portage-cataloger" +} + +// Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing portage support files. +func (c *Cataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + dbFileMatches, err := resolver.FilesByGlob(pkg.PortageDBGlob) + if err != nil { + return nil, nil, fmt.Errorf("failed to find portage files by glob: %w", err) + } + var allPackages []pkg.Package + for _, dbLocation := range dbFileMatches { + cpvMatch := cpvRe.FindStringSubmatch(dbLocation.RealPath) + if cpvMatch == nil { + return nil, nil, fmt.Errorf("failed to match package and version in %s", dbLocation.RealPath) + } + entry := pkg.PortageMetadata{ + // ensure the default value for a collection is never nil since this may be shown as JSON + Files: make([]pkg.PortageFileRecord, 0), + Package: cpvMatch[1], + Version: cpvMatch[2], + } + + err = addFiles(resolver, dbLocation, &entry) + if err != nil { + return nil, nil, err + } + + addSize(resolver, dbLocation, &entry) + + p := pkg.Package{ + Name: entry.Package, + Version: entry.Version, + Type: pkg.PortagePkg, + MetadataType: pkg.PortageMetadataType, + Metadata: entry, + } + addLicenses(resolver, dbLocation, &p) + p.FoundBy = c.Name() + p.Locations.Add(dbLocation) + p.SetID() + allPackages = append(allPackages, p) + } + return allPackages, nil, nil +} + +func addFiles(resolver source.FileResolver, dbLocation source.Location, entry *pkg.PortageMetadata) error { + contentsReader, err := resolver.FileContentsByLocation(dbLocation) + if err != nil { + return err + } + + scanner := bufio.NewScanner(contentsReader) + for scanner.Scan() { + line := strings.Trim(scanner.Text(), "\n") + fields := strings.Split(line, " ") + + if fields[0] == "obj" { + record := pkg.PortageFileRecord{ + Path: fields[1], + } + record.Digest = &file.Digest{ + Algorithm: "md5", + Value: fields[2], + } + entry.Files = append(entry.Files, record) + } + } + return nil +} + +func addLicenses(resolver source.FileResolver, dbLocation source.Location, p *pkg.Package) { + parentPath := filepath.Dir(dbLocation.RealPath) + + location := resolver.RelativeFileByPath(dbLocation, path.Join(parentPath, "LICENSE")) + + if location != nil { + licenseReader, err := resolver.FileContentsByLocation(*location) + if err == nil { + findings := internal.NewStringSet() + scanner := bufio.NewScanner(licenseReader) + scanner.Split(bufio.ScanWords) + for scanner.Scan() { + token := scanner.Text() + if token != "||" && token != "(" && token != ")" { + findings.Add(token) + } + } + p.Licenses = findings.ToSlice() + + sort.Strings(p.Licenses) + } + } +} + +func addSize(resolver source.FileResolver, dbLocation source.Location, entry *pkg.PortageMetadata) { + parentPath := filepath.Dir(dbLocation.RealPath) + + location := resolver.RelativeFileByPath(dbLocation, path.Join(parentPath, "SIZE")) + + if location != nil { + sizeReader, err := resolver.FileContentsByLocation(*location) + if err != nil { + log.Warnf("failed to fetch portage SIZE (package=%s): %+v", entry.Package, err) + } else { + scanner := bufio.NewScanner(sizeReader) + for scanner.Scan() { + line := strings.Trim(scanner.Text(), "\n") + size, err := strconv.Atoi(line) + if err == nil { + entry.InstalledSize = size + } + } + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..26aad66fbe075a13b2624d6e962a35239110022c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/cataloger_test.go @@ -0,0 +1,106 @@ +package portage + +import ( + "testing" + + "github.com/anchore/syft/syft/file" + + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/go-test/deep" +) + +func TestPortageCataloger(t *testing.T) { + tests := []struct { + name string + expected []pkg.Package + }{ + { + name: "go-case", + expected: []pkg.Package{ + { + Name: "app-containers/skopeo", + Version: "1.5.1", + FoundBy: "portage-cataloger", + Licenses: []string{"Apache-2.0", "BSD", "BSD-2", "CC-BY-SA-4.0", "ISC", "MIT"}, + Type: pkg.PortagePkg, + MetadataType: pkg.PortageMetadataType, + Metadata: pkg.PortageMetadata{ + Package: "app-containers/skopeo", + Version: "1.5.1", + InstalledSize: 27937835, + Files: []pkg.PortageFileRecord{ + { + Path: "/usr/bin/skopeo", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "376c02bd3b22804df8fdfdc895e7dbfb", + }, + }, + { + Path: "/etc/containers/policy.json", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "c01eb6950f03419e09d4fc88cb42ff6f", + }, + }, + { + Path: "/etc/containers/registries.d/default.yaml", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "e6e66cd3c24623e0667f26542e0e08f6", + }, + }, + { + Path: "/var/lib/atomic/sigstore/.keep_app-containers_skopeo-0", + Digest: &file.Digest{ + Algorithm: "md5", + Value: "d41d8cd98f00b204e9800998ecf8427e", + }, + }, + }, + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + img := imagetest.GetFixtureImage(t, "docker-archive", "image-portage") + + s, err := source.NewFromImage(img, "") + if err != nil { + t.Fatal(err) + } + + c := NewPortageCataloger() + + resolver, err := s.FileResolver(source.SquashedScope) + if err != nil { + t.Errorf("could not get resolver error: %+v", err) + } + + actual, _, err := c.Catalog(resolver) + if err != nil { + t.Fatalf("failed to catalog: %+v", err) + } + + if len(actual) != len(test.expected) { + for _, a := range actual { + t.Logf(" %+v", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(test.expected)) + } + + // test remaining fields... + for _, d := range deep.Equal(actual, test.expected) { + t.Errorf("diff: %+v", d) + } + + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/test-fixtures/image-portage/Dockerfile b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/test-fixtures/image-portage/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..770e60b56041910528ff605926f15d2b18bb157f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/portage/test-fixtures/image-portage/Dockerfile @@ -0,0 +1,2 @@ +FROM scratch +COPY . . \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/index_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/index_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..4ebfe408eb217dcd1700890b94075cb69e7efe9c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/index_cataloger.go @@ -0,0 +1,20 @@ +/* +Package python provides a concrete Cataloger implementation for Python ecosystem files (egg, wheel, requirements.txt). +*/ +package python + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewPythonIndexCataloger returns a new cataloger for python packages referenced from poetry lock files, requirements.txt files, and setup.py files. +func NewPythonIndexCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/*requirements*.txt": parseRequirementsTxt, + "**/poetry.lock": parsePoetryLock, + "**/Pipfile.lock": parsePipfileLock, + "**/setup.py": parseSetup, + } + + return common.NewGenericCataloger(nil, globParsers, "python-index-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/package_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/package_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..d58fe7ccd3b9ad7b864e69a6b7a78c2b184f1405 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/package_cataloger.go @@ -0,0 +1,231 @@ +package python + +import ( + "bufio" + "encoding/json" + "fmt" + "io/ioutil" + "path/filepath" + + "github.com/anchore/syft/internal" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + + "github.com/anchore/syft/syft/source" +) + +const ( + eggMetadataGlob = "**/*egg-info/PKG-INFO" + eggFileMetadataGlob = "**/*.egg-info" + wheelMetadataGlob = "**/*dist-info/METADATA" +) + +type PackageCataloger struct{} + +// NewPythonPackageCataloger returns a new cataloger for python packages within egg or wheel installation directories. +func NewPythonPackageCataloger() *PackageCataloger { + return &PackageCataloger{} +} + +// Name returns a string that uniquely describes a cataloger +func (c *PackageCataloger) Name() string { + return "python-package-cataloger" +} + +// Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing python egg and wheel installations. +func (c *PackageCataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + var fileMatches []source.Location + + for _, glob := range []string{eggMetadataGlob, wheelMetadataGlob, eggFileMetadataGlob} { + matches, err := resolver.FilesByGlob(glob) + if err != nil { + return nil, nil, fmt.Errorf("failed to find files by glob: %s", glob) + } + fileMatches = append(fileMatches, matches...) + } + + var pkgs []pkg.Package + for _, location := range fileMatches { + p, err := c.catalogEggOrWheel(resolver, location) + if err != nil { + return nil, nil, fmt.Errorf("unable to catalog python package=%+v: %w", location.RealPath, err) + } + if pkg.IsValid(p) { + pkgs = append(pkgs, *p) + } + } + return pkgs, nil, nil +} + +// catalogEggOrWheel takes the primary metadata file reference and returns the python package it represents. +func (c *PackageCataloger) catalogEggOrWheel(resolver source.FileResolver, metadataLocation source.Location) (*pkg.Package, error) { + metadata, sources, err := c.assembleEggOrWheelMetadata(resolver, metadataLocation) + if err != nil { + return nil, err + } + + // This can happen for Python 2.7 where it is reported from an egg-info, but Python is + // the actual runtime, it isn't a "package". The special-casing here allows to skip it + if metadata.Name == "Python" { + return nil, nil + } + + var licenses []string + if metadata.License != "" { + licenses = []string{metadata.License} + } + + p := &pkg.Package{ + Name: metadata.Name, + Version: metadata.Version, + FoundBy: c.Name(), + Locations: source.NewLocationSet(sources...), + Licenses: licenses, + Language: pkg.Python, + Type: pkg.PythonPkg, + MetadataType: pkg.PythonPackageMetadataType, + Metadata: *metadata, + } + + p.SetID() + + return p, nil +} + +// fetchRecordFiles finds a corresponding RECORD file for the given python package metadata file and returns the set of file records contained. +func (c *PackageCataloger) fetchRecordFiles(resolver source.FileResolver, metadataLocation source.Location) (files []pkg.PythonFileRecord, sources []source.Location, err error) { + // we've been given a file reference to a specific wheel METADATA file. note: this may be for a directory + // or for an image... for an image the METADATA file may be present within multiple layers, so it is important + // to reconcile the RECORD path to the same layer (or the next adjacent lower layer). + + // lets find the RECORD file relative to the directory where the METADATA file resides (in path AND layer structure) + recordPath := filepath.Join(filepath.Dir(metadataLocation.RealPath), "RECORD") + recordRef := resolver.RelativeFileByPath(metadataLocation, recordPath) + + if recordRef != nil { + sources = append(sources, *recordRef) + + recordContents, err := resolver.FileContentsByLocation(*recordRef) + if err != nil { + return nil, nil, err + } + defer internal.CloseAndLogError(recordContents, recordPath) + + // parse the record contents + records, err := parseWheelOrEggRecord(recordContents) + if err != nil { + return nil, nil, err + } + + files = append(files, records...) + } + return files, sources, nil +} + +// fetchTopLevelPackages finds a corresponding top_level.txt file for the given python package metadata file and returns the set of package names contained. +func (c *PackageCataloger) fetchTopLevelPackages(resolver source.FileResolver, metadataLocation source.Location) (pkgs []string, sources []source.Location, err error) { + // a top_level.txt file specifies the python top-level packages (provided by this python package) installed into site-packages + parentDir := filepath.Dir(metadataLocation.RealPath) + topLevelPath := filepath.Join(parentDir, "top_level.txt") + topLevelLocation := resolver.RelativeFileByPath(metadataLocation, topLevelPath) + + if topLevelLocation == nil { + return nil, nil, nil + } + + sources = append(sources, *topLevelLocation) + + topLevelContents, err := resolver.FileContentsByLocation(*topLevelLocation) + if err != nil { + return nil, nil, err + } + defer internal.CloseAndLogError(topLevelContents, topLevelLocation.VirtualPath) + + scanner := bufio.NewScanner(topLevelContents) + for scanner.Scan() { + pkgs = append(pkgs, scanner.Text()) + } + + if err := scanner.Err(); err != nil { + return nil, nil, fmt.Errorf("could not read python package top_level.txt: %w", err) + } + + return pkgs, sources, nil +} + +func (c *PackageCataloger) fetchDirectURLData(resolver source.FileResolver, metadataLocation source.Location) (d *pkg.PythonDirectURLOriginInfo, sources []source.Location, err error) { + parentDir := filepath.Dir(metadataLocation.RealPath) + directURLPath := filepath.Join(parentDir, "direct_url.json") + directURLLocation := resolver.RelativeFileByPath(metadataLocation, directURLPath) + + if directURLLocation == nil { + return nil, nil, nil + } + + sources = append(sources, *directURLLocation) + + directURLContents, err := resolver.FileContentsByLocation(*directURLLocation) + if err != nil { + return nil, nil, err + } + defer internal.CloseAndLogError(directURLContents, directURLLocation.VirtualPath) + + buffer, err := ioutil.ReadAll(directURLContents) + if err != nil { + return nil, nil, err + } + + var directURLJson pkg.DirectURLOrigin + if err := json.Unmarshal(buffer, &directURLJson); err != nil { + return nil, nil, err + } + + return &pkg.PythonDirectURLOriginInfo{ + URL: directURLJson.URL, + CommitID: directURLJson.VCSInfo.CommitID, + VCS: directURLJson.VCSInfo.VCS, + }, sources, nil +} + +// assembleEggOrWheelMetadata discovers and accumulates python package metadata from multiple file sources and returns a single metadata object as well as a list of files where the metadata was derived from. +func (c *PackageCataloger) assembleEggOrWheelMetadata(resolver source.FileResolver, metadataLocation source.Location) (*pkg.PythonPackageMetadata, []source.Location, error) { + var sources = []source.Location{metadataLocation} + + metadataContents, err := resolver.FileContentsByLocation(metadataLocation) + if err != nil { + return nil, nil, err + } + defer internal.CloseAndLogError(metadataContents, metadataLocation.VirtualPath) + + metadata, err := parseWheelOrEggMetadata(metadataLocation.RealPath, metadataContents) + if err != nil { + return nil, nil, err + } + + // attach any python files found for the given wheel/egg installation + r, s, err := c.fetchRecordFiles(resolver, metadataLocation) + if err != nil { + return nil, nil, err + } + sources = append(sources, s...) + metadata.Files = r + + // attach any top-level package names found for the given wheel/egg installation + p, s, err := c.fetchTopLevelPackages(resolver, metadataLocation) + if err != nil { + return nil, nil, err + } + sources = append(sources, s...) + metadata.TopLevelPackages = p + + // attach any direct-url package data found for the given wheel/egg installation + d, s, err := c.fetchDirectURLData(resolver, metadataLocation) + if err != nil { + return nil, nil, err + } + sources = append(sources, s...) + metadata.DirectURLOrigin = d + + return &metadata, sources, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/package_cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/package_cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..fa6917ac3f8e680b1e60eb1eb5904627f6a840ec --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/package_cataloger_test.go @@ -0,0 +1,206 @@ +package python + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/go-test/deep" +) + +func TestPythonPackageWheelCataloger(t *testing.T) { + tests := []struct { + name string + fixtures []string + expectedPackage pkg.Package + }{ + { + name: "egg-file-no-version", + fixtures: []string{"test-fixtures/no-version-py3.8.egg-info"}, + expectedPackage: pkg.Package{ + Name: "no-version", + Type: pkg.PythonPkg, + Language: pkg.Python, + FoundBy: "python-package-cataloger", + MetadataType: pkg.PythonPackageMetadataType, + Metadata: pkg.PythonPackageMetadata{ + Name: "no-version", + SitePackagesRootPath: "test-fixtures", + }, + }, + }, + { + name: "egg-info directory", + fixtures: []string{ + "test-fixtures/egg-info/PKG-INFO", + "test-fixtures/egg-info/RECORD", + "test-fixtures/egg-info/top_level.txt", + }, + expectedPackage: pkg.Package{ + Name: "requests", + Version: "2.22.0", + Type: pkg.PythonPkg, + Language: pkg.Python, + Licenses: []string{"Apache 2.0"}, + FoundBy: "python-package-cataloger", + MetadataType: pkg.PythonPackageMetadataType, + Metadata: pkg.PythonPackageMetadata{ + Name: "requests", + Version: "2.22.0", + License: "Apache 2.0", + Platform: "UNKNOWN", + Author: "Kenneth Reitz", + AuthorEmail: "me@kennethreitz.org", + SitePackagesRootPath: "test-fixtures", + Files: []pkg.PythonFileRecord{ + {Path: "requests-2.22.0.dist-info/INSTALLER", Digest: &pkg.PythonFileDigest{"sha256", "zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg"}, Size: "4"}, + {Path: "requests/__init__.py", Digest: &pkg.PythonFileDigest{"sha256", "PnKCgjcTq44LaAMzB-7--B2FdewRrE8F_vjZeaG9NhA"}, Size: "3921"}, + {Path: "requests/__pycache__/__version__.cpython-38.pyc"}, + {Path: "requests/__pycache__/utils.cpython-38.pyc"}, + {Path: "requests/__version__.py", Digest: &pkg.PythonFileDigest{"sha256", "Bm-GFstQaFezsFlnmEMrJDe8JNROz9n2XXYtODdvjjc"}, Size: "436"}, + {Path: "requests/utils.py", Digest: &pkg.PythonFileDigest{"sha256", "LtPJ1db6mJff2TJSJWKi7rBpzjPS3mSOrjC9zRhoD3A"}, Size: "30049"}, + }, + TopLevelPackages: []string{"requests"}, + }, + }, + }, + { + name: "dist-info directory", + fixtures: []string{ + "test-fixtures/dist-info/METADATA", + "test-fixtures/dist-info/RECORD", + "test-fixtures/dist-info/top_level.txt", + "test-fixtures/dist-info/direct_url.json", + }, + expectedPackage: pkg.Package{ + Name: "Pygments", + Version: "2.6.1", + Type: pkg.PythonPkg, + Language: pkg.Python, + Licenses: []string{"BSD License"}, + FoundBy: "python-package-cataloger", + MetadataType: pkg.PythonPackageMetadataType, + Metadata: pkg.PythonPackageMetadata{ + Name: "Pygments", + Version: "2.6.1", + License: "BSD License", + Platform: "any", + Author: "Georg Brandl", + AuthorEmail: "georg@python.org", + SitePackagesRootPath: "test-fixtures", + Files: []pkg.PythonFileRecord{ + {Path: "../../../bin/pygmentize", Digest: &pkg.PythonFileDigest{"sha256", "dDhv_U2jiCpmFQwIRHpFRLAHUO4R1jIJPEvT_QYTFp8"}, Size: "220"}, + {Path: "Pygments-2.6.1.dist-info/AUTHORS", Digest: &pkg.PythonFileDigest{"sha256", "PVpa2_Oku6BGuiUvutvuPnWGpzxqFy2I8-NIrqCvqUY"}, Size: "8449"}, + {Path: "Pygments-2.6.1.dist-info/RECORD"}, + {Path: "pygments/__pycache__/__init__.cpython-38.pyc"}, + {Path: "pygments/util.py", Digest: &pkg.PythonFileDigest{"sha256", "586xXHiJGGZxqk5PMBu3vBhE68DLuAe5MBARWrSPGxA"}, Size: "10778"}, + + {Path: "pygments/x_util.py", Digest: &pkg.PythonFileDigest{"sha256", "qpzzsOW31KT955agi-7NS--90I0iNiJCyLJQnRCHgKI="}, Size: "10778"}, + }, + TopLevelPackages: []string{"pygments", "something_else"}, + DirectURLOrigin: &pkg.PythonDirectURLOriginInfo{URL: "https://github.com/python-test/test.git", VCS: "git", CommitID: "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"}, + }, + }, + }, + { + // in cases where the metadata file is available and the record is not we should still record there is a package + // additionally empty top_level.txt files should not result in an error + name: "partial dist-info directory", + fixtures: []string{"test-fixtures/partial.dist-info/METADATA"}, + expectedPackage: pkg.Package{ + Name: "Pygments", + Version: "2.6.1", + Type: pkg.PythonPkg, + Language: pkg.Python, + Licenses: []string{"BSD License"}, + FoundBy: "python-package-cataloger", + MetadataType: pkg.PythonPackageMetadataType, + Metadata: pkg.PythonPackageMetadata{ + Name: "Pygments", + Version: "2.6.1", + License: "BSD License", + Platform: "any", + Author: "Georg Brandl", + AuthorEmail: "georg@python.org", + SitePackagesRootPath: "test-fixtures", + }, + }, + }, + { + name: "egg-info regular file", + fixtures: []string{"test-fixtures/test.egg-info"}, + expectedPackage: pkg.Package{ + Name: "requests", + Version: "2.22.0", + Type: pkg.PythonPkg, + Language: pkg.Python, + Licenses: []string{"Apache 2.0"}, + FoundBy: "python-package-cataloger", + MetadataType: pkg.PythonPackageMetadataType, + Metadata: pkg.PythonPackageMetadata{ + Name: "requests", + Version: "2.22.0", + License: "Apache 2.0", + Platform: "UNKNOWN", + Author: "Kenneth Reitz", + AuthorEmail: "me@kennethreitz.org", + SitePackagesRootPath: "test-fixtures", + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + resolver := source.NewMockResolverForPaths(test.fixtures...) + + locations, err := resolver.FilesByPath(test.fixtures...) + if err != nil { + t.Fatal(err) + } + + test.expectedPackage.Locations = source.NewLocationSet(locations...) + + actual, _, err := NewPythonPackageCataloger().Catalog(resolver) + if err != nil { + t.Fatalf("failed to catalog python package: %+v", err) + } + + if len(actual) != 1 { + t.Fatalf("unexpected number of packages: %d", len(actual)) + } + + for _, d := range deep.Equal(actual[0], test.expectedPackage) { + t.Errorf("diff: %+v", d) + } + }) + } +} + +func TestIgnorePackage(t *testing.T) { + tests := []struct { + MetadataFixture string + }{ + { + MetadataFixture: "test-fixtures/Python-2.7.egg-info", + }, + { + MetadataFixture: "test-fixtures/empty-1.0.0-py3.8.egg-info", + }, + } + + for _, test := range tests { + t.Run(test.MetadataFixture, func(t *testing.T) { + resolver := source.NewMockResolverForPaths(test.MetadataFixture) + + actual, _, err := NewPythonPackageCataloger().Catalog(resolver) + if err != nil { + t.Fatalf("failed to catalog python package: %+v", err) + } + + if len(actual) != 0 { + t.Fatalf("Expected 0 packages but found: %d", len(actual)) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_pipfile_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_pipfile_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..e1790ce1bdec2e27987cfe549b650acf5628a341 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_pipfile_lock.go @@ -0,0 +1,70 @@ +package python + +import ( + "encoding/json" + "fmt" + "io" + "sort" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +type PipfileLock struct { + Meta struct { + Hash struct { + Sha256 string `json:"sha256"` + } `json:"hash"` + PipfileSpec int `json:"pipfile-spec"` + Requires struct { + PythonVersion string `json:"python_version"` + } `json:"requires"` + Sources []struct { + Name string `json:"name"` + URL string `json:"url"` + VerifySsl bool `json:"verify_ssl"` + } `json:"sources"` + } `json:"_meta"` + Default map[string]Dependency `json:"default"` + Develop map[string]Dependency `json:"develop"` +} + +type Dependency struct { + Version string `json:"version"` +} + +// integrity check +var _ common.ParserFn = parsePipfileLock + +// parsePipfileLock is a parser function for Pipfile.lock contents, returning "Default" python packages discovered. +func parsePipfileLock(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + packages := make([]*pkg.Package, 0) + dec := json.NewDecoder(reader) + + for { + var lock PipfileLock + if err := dec.Decode(&lock); err == io.EOF { + break + } else if err != nil { + return nil, nil, fmt.Errorf("failed to parse Pipfile.lock file: %w", err) + } + for name, pkgMeta := range lock.Default { + version := strings.TrimPrefix(pkgMeta.Version, "==") + packages = append(packages, &pkg.Package{ + Name: name, + Version: version, + Language: pkg.Python, + Type: pkg.PythonPkg, + }) + } + } + + // Without sorting the packages slice, the order of packages will be unstable, due to ranging over a map. + sort.Slice(packages, func(i, j int) bool { + return packages[i].String() < packages[j].String() + }) + + return packages, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_pipfile_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_pipfile_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d9fd1a02d3405023a0c3f741b9b8c20bd745d7e9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_pipfile_lock_test.go @@ -0,0 +1,62 @@ +package python + +import ( + "github.com/anchore/syft/syft/source" + "os" + "testing" + + "github.com/google/go-cmp/cmp" + + "github.com/anchore/syft/syft/pkg" +) + +func TestParsePipFileLock(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "aio-pika", + Version: "6.8.0", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "aiodns", + Version: "2.0.0", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "aiohttp", + Version: "3.7.4.post0", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "aiohttp-jinja2", + Version: "1.4.2", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + } + + fixture, err := os.Open("test-fixtures/pipfile-lock/Pipfile.lock") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parsePipfileLock(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse requirements: %+v", err) + } + + if diff := cmp.Diff(expected, actual, + cmp.AllowUnexported(pkg.Package{}), + cmp.Comparer( + func(x, y source.LocationSet) bool { + return cmp.Equal(x.ToSlice(), y.ToSlice()) + }, + ), + ); diff != "" { + t.Errorf("unexpected result from parsing (-expected +actual)\n%s", diff) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_poetry_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_poetry_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..8cae5ed9ea2f0b95681454c57043c73e68d22b12 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_poetry_lock.go @@ -0,0 +1,30 @@ +package python + +import ( + "fmt" + "io" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "github.com/pelletier/go-toml" +) + +// integrity check +var _ common.ParserFn = parsePoetryLock + +// parsePoetryLock is a parser function for poetry.lock contents, returning all python packages discovered. +func parsePoetryLock(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + tree, err := toml.LoadReader(reader) + if err != nil { + return nil, nil, fmt.Errorf("unable to load poetry.lock for parsing: %v", err) + } + + metadata := PoetryMetadata{} + err = tree.Unmarshal(&metadata) + if err != nil { + return nil, nil, fmt.Errorf("unable to parse poetry.lock: %v", err) + } + + return metadata.Pkgs(), nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_poetry_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_poetry_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..a582a834404196503fbce996a61dc583f35f2190 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_poetry_lock_test.go @@ -0,0 +1,58 @@ +package python + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParsePoetryLock(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "added-value", + Version: "0.14.2", + Language: pkg.Python, + Type: pkg.PythonPkg, + Licenses: nil, + }, + { + Name: "alabaster", + Version: "0.7.12", + Language: pkg.Python, + Type: pkg.PythonPkg, + Licenses: nil, + }, + { + Name: "appnope", + Version: "0.1.0", + Language: pkg.Python, + Type: pkg.PythonPkg, + Licenses: nil, + }, + { + Name: "asciitree", + Version: "0.3.3", + Language: pkg.Python, + Type: pkg.PythonPkg, + Licenses: nil, + }, + } + + fixture, err := os.Open("test-fixtures/poetry/poetry.lock") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parsePoetryLock(fixture.Name(), fixture) + if err != nil { + t.Error(err) + } + + differences := deep.Equal(expected, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_requirements.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_requirements.go new file mode 100644 index 0000000000000000000000000000000000000000..62443bcfa6cb8e1bb8123bd1b7fa2973c81959e8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_requirements.go @@ -0,0 +1,95 @@ +package python + +import ( + "bufio" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseRequirementsTxt + +// parseRequirementsTxt takes a Python requirements.txt file, returning all Python packages that are locked to a +// specific version. +func parseRequirementsTxt(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + packages := make([]*pkg.Package, 0) + + scanner := bufio.NewScanner(reader) + for scanner.Scan() { + line := scanner.Text() + line = trimRequirementsTxtLine(line) + + if line == "" { + // nothing to parse on this line + continue + } + + if strings.HasPrefix(line, "-e") { + // editable packages aren't parsed (yet) + continue + } + + if !strings.Contains(line, "==") { + // a package without a version, or a range (unpinned) which does not tell us + // exactly what will be installed. + continue + } + + // parse a new requirement + parts := strings.Split(line, "==") + name := strings.TrimSpace(parts[0]) + version := strings.TrimSpace(parts[1]) + packages = append(packages, &pkg.Package{ + Name: name, + Version: version, + Language: pkg.Python, + Type: pkg.PythonPkg, + }) + } + + if err := scanner.Err(); err != nil { + return nil, nil, fmt.Errorf("failed to parse python requirements file: %w", err) + } + + return packages, nil, nil +} + +// trimRequirementsTxtLine removes content from the given requirements.txt line +// that should not be considered for parsing. +func trimRequirementsTxtLine(line string) string { + line = strings.TrimSpace(line) + line = removeTrailingComment(line) + line = removeEnvironmentMarkers(line) + + return line +} + +// removeTrailingComment takes a requirements.txt line and strips off comment strings. +func removeTrailingComment(line string) string { + parts := strings.SplitN(line, "#", 2) + if len(parts) < 2 { + // there aren't any comments + + return line + } + + return parts[0] +} + +// removeEnvironmentMarkers removes any instances of environment markers (delimited by ';') from the line. +// For more information, see https://www.python.org/dev/peps/pep-0508/#environment-markers. +func removeEnvironmentMarkers(line string) string { + parts := strings.SplitN(line, ";", 2) + if len(parts) < 2 { + // there aren't any environment markers + + return line + } + + return parts[0] +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_requirements_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_requirements_test.go new file mode 100644 index 0000000000000000000000000000000000000000..3a187105996bdea55d0c48f9205488f1623b8d3e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_requirements_test.go @@ -0,0 +1,56 @@ +package python + +import ( + "github.com/anchore/syft/syft/source" + "os" + "testing" + + "github.com/google/go-cmp/cmp" + + "github.com/anchore/syft/syft/pkg" +) + +func TestParseRequirementsTxt(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "flask", + Version: "4.0.0", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "foo", + Version: "1.0.0", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "SomeProject", + Version: "5.4", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + } + + fixture, err := os.Open("test-fixtures/requires/requirements.txt") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseRequirementsTxt(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse requirements: %+v", err) + } + + if diff := cmp.Diff(expected, actual, + cmp.AllowUnexported(pkg.Package{}), + cmp.Comparer( + func(x, y source.LocationSet) bool { + return cmp.Equal(x.ToSlice(), y.ToSlice()) + }, + ), + ); diff != "" { + t.Errorf("unexpected result from parsing (-expected +actual)\n%s", diff) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_setup.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_setup.go new file mode 100644 index 0000000000000000000000000000000000000000..c3943ff1e522351f5271d86bf9acb207fe52cc61 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_setup.go @@ -0,0 +1,52 @@ +package python + +import ( + "bufio" + "io" + "regexp" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseSetup + +// match examples: +// +// 'pathlib3==2.2.0;python_version<"3.6"' --> match(name=pathlib3 version=2.2.0) +// "mypy==v0.770", --> match(name=mypy version=v0.770) +// " mypy2 == v0.770", ' mypy3== v0.770', --> match(name=mypy2 version=v0.770), match(name=mypy3, version=v0.770) +var pinnedDependency = regexp.MustCompile(`['"]\W?(\w+\W?==\W?[\w\.]*)`) + +func parseSetup(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + packages := make([]*pkg.Package, 0) + + scanner := bufio.NewScanner(reader) + + for scanner.Scan() { + line := scanner.Text() + line = strings.TrimRight(line, "\n") + + for _, match := range pinnedDependency.FindAllString(line, -1) { + parts := strings.Split(match, "==") + if len(parts) != 2 { + continue + } + name := strings.Trim(parts[0], "'\"") + name = strings.TrimSpace(name) + + version := strings.TrimSpace(parts[len(parts)-1]) + packages = append(packages, &pkg.Package{ + Name: strings.Trim(name, "'\""), + Version: strings.Trim(version, "'\""), + Language: pkg.Python, + Type: pkg.PythonPkg, + }) + } + } + + return packages, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_setup_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_setup_test.go new file mode 100644 index 0000000000000000000000000000000000000000..b5614fa3d197abcc3bcf440c416061dbd4d79d9a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_setup_test.go @@ -0,0 +1,68 @@ +package python + +import ( + "github.com/anchore/syft/syft/source" + "os" + "testing" + + "github.com/google/go-cmp/cmp" + + "github.com/anchore/syft/syft/pkg" +) + +func TestParseSetup(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "pathlib3", + Version: "2.2.0", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "mypy", + Version: "v0.770", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "mypy1", + Version: "v0.770", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "mypy2", + Version: "v0.770", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + { + Name: "mypy3", + Version: "v0.770", + Language: pkg.Python, + Type: pkg.PythonPkg, + }, + } + + fixture, err := os.Open("test-fixtures/setup/setup.py") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseSetup(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse requirements: %+v", err) + } + + if diff := cmp.Diff(expected, actual, + cmp.AllowUnexported(pkg.Package{}), + cmp.Comparer( + func(x, y source.LocationSet) bool { + return cmp.Equal(x.ToSlice(), y.ToSlice()) + }, + ), + ); diff != "" { + t.Errorf("unexpected result from parsing (-expected +actual)\n%s", diff) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..4c6a880f1d87b625fb8c07a372413be8a9a02989 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_metadata.go @@ -0,0 +1,112 @@ +package python + +import ( + "bufio" + "fmt" + "io" + "path/filepath" + "strings" + + "github.com/anchore/syft/internal/file" + "github.com/anchore/syft/internal/log" + + "github.com/mitchellh/mapstructure" + + "github.com/anchore/syft/syft/pkg" +) + +// parseWheelOrEggMetadata takes a Python Egg or Wheel (which share the same format and values for our purposes), +// returning all Python packages listed. +func parseWheelOrEggMetadata(path string, reader io.Reader) (pkg.PythonPackageMetadata, error) { + fields := make(map[string]string) + var key string + + scanner := bufio.NewScanner(reader) + for scanner.Scan() { + line := scanner.Text() + line = strings.TrimRight(line, "\n") + + // An empty line means we are done parsing (either because there's no more data, + // or because a description follows as specified in + // https://packaging.python.org/specifications/core-metadata/#description; + // and at this time, we're not interested in the description). + if len(line) == 0 { + if len(fields) > 0 { + break + } + + // however, if the field parsing has not started yet, keep scanning lines + continue + } + + switch { + case strings.HasPrefix(line, " "): + // a field-body continuation + updatedValue, err := handleFieldBodyContinuation(key, line, fields) + if err != nil { + return pkg.PythonPackageMetadata{}, err + } + + fields[key] = updatedValue + default: + // parse a new key (note, duplicate keys are overridden) + if i := strings.Index(line, ":"); i > 0 { + // mapstruct cannot map keys with dashes, and we are expected to persist the "Author-email" field + key = strings.ReplaceAll(strings.TrimSpace(line[0:i]), "-", "") + val := strings.TrimSpace(line[i+1:]) + + fields[key] = val + } else { + log.Warnf("cannot parse field from path: %q from line: %q", path, line) + } + } + } + + if err := scanner.Err(); err != nil { + return pkg.PythonPackageMetadata{}, fmt.Errorf("failed to parse python wheel/egg: %w", err) + } + + var metadata pkg.PythonPackageMetadata + if err := mapstructure.Decode(fields, &metadata); err != nil { + return pkg.PythonPackageMetadata{}, fmt.Errorf("unable to parse APK metadata: %w", err) + } + + // add additional metadata not stored in the egg/wheel metadata file + + metadata.SitePackagesRootPath = determineSitePackagesRootPath(path) + + return metadata, nil +} + +// isEggRegularFile determines if the specified path is the regular file variant +// of egg metadata (as opposed to a directory that contains more metadata +// files). +func isEggRegularFile(path string) bool { + return file.GlobMatch(eggFileMetadataGlob, path) +} + +// determineSitePackagesRootPath returns the path of the site packages root, +// given the egg metadata file or directory specified in the path. +func determineSitePackagesRootPath(path string) string { + if isEggRegularFile(path) { + return filepath.Clean(filepath.Dir(path)) + } + + return filepath.Clean(filepath.Dir(filepath.Dir(path))) +} + +// handleFieldBodyContinuation returns the updated value for the specified field after processing the specified line. +// If the continuation cannot be processed, it returns an error. +func handleFieldBodyContinuation(key, line string, fields map[string]string) (string, error) { + if len(key) == 0 { + return "", fmt.Errorf("no match for continuation: line: '%s'", line) + } + + val, ok := fields[key] + if !ok { + return "", fmt.Errorf("no previous key exists, expecting: %s", key) + } + + // concatenate onto previous value + return fmt.Sprintf("%s\n %s", val, strings.TrimSpace(line)), nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..737da67f9618c0b8b7891b74f4fe718def66f0c6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_metadata_test.go @@ -0,0 +1,153 @@ +package python + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseWheelEggMetadata(t *testing.T) { + tests := []struct { + Fixture string + ExpectedMetadata pkg.PythonPackageMetadata + }{ + { + Fixture: "test-fixtures/egg-info/PKG-INFO", + ExpectedMetadata: pkg.PythonPackageMetadata{ + Name: "requests", + Version: "2.22.0", + License: "Apache 2.0", + Platform: "UNKNOWN", + Author: "Kenneth Reitz", + AuthorEmail: "me@kennethreitz.org", + SitePackagesRootPath: "test-fixtures", + }, + }, + { + Fixture: "test-fixtures/dist-info/METADATA", + ExpectedMetadata: pkg.PythonPackageMetadata{ + Name: "Pygments", + Version: "2.6.1", + License: "BSD License", + Platform: "any", + Author: "Georg Brandl", + AuthorEmail: "georg@python.org", + SitePackagesRootPath: "test-fixtures", + }, + }, + } + + for _, test := range tests { + t.Run(test.Fixture, func(t *testing.T) { + fixture, err := os.Open(test.Fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, err := parseWheelOrEggMetadata(test.Fixture, fixture) + if err != nil { + t.Fatalf("failed to parse: %+v", err) + } + + for _, d := range deep.Equal(actual, test.ExpectedMetadata) { + t.Errorf("diff: %+v", d) + } + }) + } +} + +func TestIsRegularEggFile(t *testing.T) { + cases := []struct { + path string + expected bool + }{ + { + "/usr/lib64/python2.6/site-packages/M2Crypto-0.20.2-py2.6.egg-info", + true, + }, + { + "/usr/lib64/python2.6/site-packages/M2Crypto-0.20.2-py2.6.egg-info/PKG-INFO", + false, + }, + { + "/usr/lib64/python2.6/site-packages/M2Crypto-0.20.2-py2.6.dist-info/METADATA", + false, + }, + } + + for _, c := range cases { + t.Run(c.path, func(t *testing.T) { + actual := isEggRegularFile(c.path) + + if actual != c.expected { + t.Errorf("expected %t but got %t", c.expected, actual) + } + }) + } +} + +func TestDetermineSitePackagesRootPath(t *testing.T) { + cases := []struct { + inputPath string + expected string + }{ + { + inputPath: "/usr/lib64/python2.6/site-packages/ethtool-0.6-py2.6.egg-info", + expected: "/usr/lib64/python2.6/site-packages", + }, + { + inputPath: "/usr/lib/python2.7/dist-packages/configobj-5.0.6.egg-info/top_level.txt", + expected: "/usr/lib/python2.7/dist-packages", + }, + { + inputPath: "/usr/lib/python2.7/dist-packages/six-1.10.0.egg-info/PKG-INFO", + expected: "/usr/lib/python2.7/dist-packages", + }, + } + + for _, c := range cases { + t.Run(c.inputPath, func(t *testing.T) { + actual := determineSitePackagesRootPath(c.inputPath) + + if actual != c.expected { + t.Errorf("expected %s but got %s", c.expected, actual) + } + }) + } +} + +func TestParseWheelEggMetadataInvalid(t *testing.T) { + tests := []struct { + Fixture string + ExpectedMetadata pkg.PythonPackageMetadata + }{ + { + Fixture: "test-fixtures/egg-info/PKG-INFO-INVALID", + ExpectedMetadata: pkg.PythonPackageMetadata{ + Name: "mxnet", + Version: "1.8.0", + SitePackagesRootPath: "test-fixtures", + }, + }, + } + + for _, test := range tests { + t.Run(test.Fixture, func(t *testing.T) { + fixture, err := os.Open(test.Fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, err := parseWheelOrEggMetadata(test.Fixture, fixture) + if err != nil { + t.Fatalf("failed to parse: %+v", err) + } + + for _, d := range deep.Equal(actual, test.ExpectedMetadata) { + t.Errorf("diff: %+v", d) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_record.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_record.go new file mode 100644 index 0000000000000000000000000000000000000000..764b6bf08d85633df2b66cc1bf15041a717d930c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_record.go @@ -0,0 +1,61 @@ +package python + +import ( + "encoding/csv" + "fmt" + "io" + "strings" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" +) + +// parseWheelOrEggMetadata takes a Python Egg or Wheel (which share the same format and values for our purposes), +// returning all Python packages listed. +func parseWheelOrEggRecord(reader io.Reader) ([]pkg.PythonFileRecord, error) { + var records []pkg.PythonFileRecord + r := csv.NewReader(reader) + + for { + recordList, err := r.Read() + if err == io.EOF { + break + } + if err != nil { + return nil, fmt.Errorf("unable to read python record file: %w", err) + } + + if len(recordList) != 3 { + return nil, fmt.Errorf("python record an unexpected length=%d: %q", len(recordList), recordList) + } + + var record pkg.PythonFileRecord + + for idx, item := range recordList { + switch idx { + case 0: + record.Path = item + case 1: + if item == "" { + continue + } + fields := strings.SplitN(item, "=", 2) + if len(fields) != 2 { + log.Warnf("unexpected python record digest: %q", item) + continue + } + + record.Digest = &pkg.PythonFileDigest{ + Algorithm: fields[0], + Value: fields[1], + } + case 2: + record.Size = item + } + } + + records = append(records, record) + } + + return records, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_record_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_record_test.go new file mode 100644 index 0000000000000000000000000000000000000000..7b178d9f02ab79893c1db61859ab468e719bb8eb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/parse_wheel_egg_record_test.go @@ -0,0 +1,58 @@ +package python + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseWheelEggRecord(t *testing.T) { + tests := []struct { + Fixture string + ExpectedMetadata []pkg.PythonFileRecord + }{ + { + Fixture: "test-fixtures/egg-info/RECORD", + ExpectedMetadata: []pkg.PythonFileRecord{ + {Path: "requests-2.22.0.dist-info/INSTALLER", Digest: &pkg.PythonFileDigest{"sha256", "zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg"}, Size: "4"}, + {Path: "requests/__init__.py", Digest: &pkg.PythonFileDigest{"sha256", "PnKCgjcTq44LaAMzB-7--B2FdewRrE8F_vjZeaG9NhA"}, Size: "3921"}, + {Path: "requests/__pycache__/__version__.cpython-38.pyc"}, + {Path: "requests/__pycache__/utils.cpython-38.pyc"}, + {Path: "requests/__version__.py", Digest: &pkg.PythonFileDigest{"sha256", "Bm-GFstQaFezsFlnmEMrJDe8JNROz9n2XXYtODdvjjc"}, Size: "436"}, + {Path: "requests/utils.py", Digest: &pkg.PythonFileDigest{"sha256", "LtPJ1db6mJff2TJSJWKi7rBpzjPS3mSOrjC9zRhoD3A"}, Size: "30049"}, + }, + }, + { + Fixture: "test-fixtures/dist-info/RECORD", + ExpectedMetadata: []pkg.PythonFileRecord{ + {Path: "../../../bin/pygmentize", Digest: &pkg.PythonFileDigest{"sha256", "dDhv_U2jiCpmFQwIRHpFRLAHUO4R1jIJPEvT_QYTFp8"}, Size: "220"}, + {Path: "Pygments-2.6.1.dist-info/AUTHORS", Digest: &pkg.PythonFileDigest{"sha256", "PVpa2_Oku6BGuiUvutvuPnWGpzxqFy2I8-NIrqCvqUY"}, Size: "8449"}, + {Path: "Pygments-2.6.1.dist-info/RECORD"}, + {Path: "pygments/__pycache__/__init__.cpython-38.pyc"}, + {Path: "pygments/util.py", Digest: &pkg.PythonFileDigest{"sha256", "586xXHiJGGZxqk5PMBu3vBhE68DLuAe5MBARWrSPGxA"}, Size: "10778"}, + {Path: "pygments/x_util.py", Digest: &pkg.PythonFileDigest{"sha256", "qpzzsOW31KT955agi-7NS--90I0iNiJCyLJQnRCHgKI="}, Size: "10778"}, + }, + }, + } + + for _, test := range tests { + t.Run(test.Fixture, func(t *testing.T) { + fixture, err := os.Open(test.Fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, err := parseWheelOrEggRecord(fixture) + if err != nil { + t.Fatalf("failed to parse: %+v", err) + } + + for _, d := range deep.Equal(actual, test.ExpectedMetadata) { + t.Errorf("diff: %+v", d) + } + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/poetry_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/poetry_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..f7518056645d7e19d1736c6a308dbb5594cb4505 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/poetry_metadata.go @@ -0,0 +1,18 @@ +package python + +import "github.com/anchore/syft/syft/pkg" + +type PoetryMetadata struct { + Packages []PoetryMetadataPackage `toml:"package"` +} + +// Pkgs returns all of the packages referenced within the poetry.lock metadata. +func (m PoetryMetadata) Pkgs() []*pkg.Package { + pkgs := make([]*pkg.Package, 0) + + for _, p := range m.Packages { + pkgs = append(pkgs, p.Pkg()) + } + + return pkgs +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/poetry_metadata_package.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/poetry_metadata_package.go new file mode 100644 index 0000000000000000000000000000000000000000..db75c19f4b354cab2342ad41552177b309d0e334 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/poetry_metadata_package.go @@ -0,0 +1,21 @@ +package python + +import "github.com/anchore/syft/syft/pkg" + +type PoetryMetadataPackage struct { + Name string `toml:"name"` + Version string `toml:"version"` + Category string `toml:"category"` + Description string `toml:"description"` + Optional bool `toml:"optional"` +} + +// Pkg returns the standard `pkg.Package` representation of the package referenced within the poetry.lock metadata. +func (p PoetryMetadataPackage) Pkg() *pkg.Package { + return &pkg.Package{ + Name: p.Name, + Version: p.Version, + Language: pkg.Python, + Type: pkg.PythonPkg, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/Python-2.7.egg-info b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/Python-2.7.egg-info new file mode 100644 index 0000000000000000000000000000000000000000..ec0b76044e213559b797229f149610f34ff025d3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/Python-2.7.egg-info @@ -0,0 +1,31 @@ +Metadata-Version: 1.1 +Name: Python +Version: 2.7.13 +Summary: A high-level object-oriented programming language +Home-page: http://www.python.org/2.7 +Author: Guido van Rossum and the Python community +Author-email: python-dev@python.org +License: PSF license +Description: Python is an interpreted, interactive, object-oriented programming + language. It is often compared to Tcl, Perl, Scheme or Java. + + Python combines remarkable power with very clear syntax. It has + modules, classes, exceptions, very high level dynamic data types, and + dynamic typing. There are interfaces to many system calls and + libraries, as well as to various windowing systems (X11, Motif, Tk, + Mac, MFC). New built-in modules are easily written in C or C++. Python + is also usable as an extension language for applications that need a + programmable interface. + + The Python implementation is portable: it runs on many brands of UNIX, + on Windows, DOS, OS/2, Mac, Amiga... If your favorite system isn't + listed here, it may still be supported, if there's a C compiler for + it. Ask around on comp.lang.python -- or just try compiling Python + yourself. +Platform: Many +Classifier: Development Status :: 6 - Mature +Classifier: License :: OSI Approved :: Python Software Foundation License +Classifier: Natural Language :: English +Classifier: Programming Language :: C +Classifier: Programming Language :: Python +Classifier: Topic :: Software Development \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/METADATA b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/METADATA new file mode 100644 index 0000000000000000000000000000000000000000..924780dfd45ab61f303185f3fa4d969ec2c336aa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/METADATA @@ -0,0 +1,47 @@ +Metadata-Version: 2.1 +Name: Pygments +Version: 2.6.1 +Summary: Pygments is a syntax highlighting package written in Python. +Home-page: https://pygments.org/ +Author: Georg Brandl +Author-email: georg@python.org +License: BSD License +Keywords: syntax highlighting +Platform: any +Classifier: License :: OSI Approved :: BSD License +Classifier: Intended Audience :: Developers +Classifier: Intended Audience :: End Users/Desktop +Classifier: Intended Audience :: System Administrators +Classifier: Development Status :: 6 - Mature +Classifier: Programming Language :: Python +Classifier: Programming Language :: Python :: 3 +Classifier: Programming Language :: Python :: 3.5 +Classifier: Programming Language :: Python :: 3.6 +Classifier: Programming Language :: Python :: 3.7 +Classifier: Programming Language :: Python :: 3.8 +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Programming Language :: Python :: Implementation :: PyPy +Classifier: Operating System :: OS Independent +Classifier: Topic :: Text Processing :: Filters +Classifier: Topic :: Utilities +Requires-Python: >=3.5 + + +Pygments +~~~~~~~~ + +Pygments is a syntax highlighting package written in Python. + +It is a generic syntax highlighter suitable for use in code hosting, forums, +wikis or other applications that need to prettify source code. Highlights +are: + +* a wide range of over 500 languages and other text formats is supported +* special attention is paid to details, increasing quality by a fair amount +* support for new languages and formats are added easily +* a number of output formats, presently HTML, LaTeX, RTF, SVG, all image formats that PIL supports and ANSI sequences +* it is usable as a command-line tool and as a library + +:copyright: Copyright 2006-2019 by the Pygments team, see AUTHORS. +:license: BSD, see LICENSE for details. + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/RECORD b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/RECORD new file mode 100644 index 0000000000000000000000000000000000000000..b7beac37eba77bd28c6cc92c8fb63349a3925f35 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/RECORD @@ -0,0 +1,6 @@ +../../../bin/pygmentize,sha256=dDhv_U2jiCpmFQwIRHpFRLAHUO4R1jIJPEvT_QYTFp8,220 +Pygments-2.6.1.dist-info/AUTHORS,sha256=PVpa2_Oku6BGuiUvutvuPnWGpzxqFy2I8-NIrqCvqUY,8449 +Pygments-2.6.1.dist-info/RECORD,, +pygments/__pycache__/__init__.cpython-38.pyc,, +pygments/util.py,sha256=586xXHiJGGZxqk5PMBu3vBhE68DLuAe5MBARWrSPGxA,10778 +pygments/x_util.py,sha256=qpzzsOW31KT955agi-7NS--90I0iNiJCyLJQnRCHgKI=,10778 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/direct_url.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/direct_url.json new file mode 100644 index 0000000000000000000000000000000000000000..5d42a36e3114f6940e6ef061b9066d91f0d132f9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/direct_url.json @@ -0,0 +1 @@ +{"url": "https://github.com/python-test/test.git", "vcs_info": {"commit_id": "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa", "vcs": "git"}} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/top_level.txt b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/top_level.txt new file mode 100644 index 0000000000000000000000000000000000000000..2c30fc0c4c0e92e38e07144178c7d43927641b00 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/dist-info/top_level.txt @@ -0,0 +1,2 @@ +pygments +something_else \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/PKG-INFO b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/PKG-INFO new file mode 100644 index 0000000000000000000000000000000000000000..a73770668150c2bea1b4d7b807aeb058b18ebcc8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/PKG-INFO @@ -0,0 +1,134 @@ +Metadata-Version: 2.1 +Name: requests +Version: 2.22.0 +Summary: Python HTTP for Humans. +Home-page: http://python-requests.org +Author: Kenneth Reitz +Author-email: me@kennethreitz.org +License: Apache 2.0 +Description: Requests: HTTP for Humans™ + ========================== + + [![image](https://img.shields.io/pypi/v/requests.svg)](https://pypi.org/project/requests/) + [![image](https://img.shields.io/pypi/l/requests.svg)](https://pypi.org/project/requests/) + [![image](https://img.shields.io/pypi/pyversions/requests.svg)](https://pypi.org/project/requests/) + [![codecov.io](https://codecov.io/github/requests/requests/coverage.svg?branch=master)](https://codecov.io/github/requests/requests) + [![image](https://img.shields.io/github/contributors/requests/requests.svg)](https://github.com/requests/requests/graphs/contributors) + [![image](https://img.shields.io/badge/Say%20Thanks-!-1EAEDB.svg)](https://saythanks.io/to/kennethreitz) + + Requests is the only *Non-GMO* HTTP library for Python, safe for human + consumption. + + ![image](https://farm5.staticflickr.com/4317/35198386374_1939af3de6_k_d.jpg) + + Behold, the power of Requests: + + ``` {.sourceCode .python} + >>> import requests + >>> r = requests.get('https://api.github.com/user', auth=('user', 'pass')) + >>> r.status_code + 200 + >>> r.headers['content-type'] + 'application/json; charset=utf8' + >>> r.encoding + 'utf-8' + >>> r.text + u'{"type":"User"...' + >>> r.json() + {u'disk_usage': 368627, u'private_gists': 484, ...} + ``` + + See [the similar code, sans Requests](https://gist.github.com/973705). + + [![image](https://raw.githubusercontent.com/requests/requests/master/docs/_static/requests-logo-small.png)](http://docs.python-requests.org/) + + Requests allows you to send *organic, grass-fed* HTTP/1.1 requests, + without the need for manual labor. There's no need to manually add query + strings to your URLs, or to form-encode your POST data. Keep-alive and + HTTP connection pooling are 100% automatic, thanks to + [urllib3](https://github.com/shazow/urllib3). + + Besides, all the cool kids are doing it. Requests is one of the most + downloaded Python packages of all time, pulling in over 11,000,000 + downloads every month. You don't want to be left out! + + Feature Support + --------------- + + Requests is ready for today's web. + + - International Domains and URLs + - Keep-Alive & Connection Pooling + - Sessions with Cookie Persistence + - Browser-style SSL Verification + - Basic/Digest Authentication + - Elegant Key/Value Cookies + - Automatic Decompression + - Automatic Content Decoding + - Unicode Response Bodies + - Multipart File Uploads + - HTTP(S) Proxy Support + - Connection Timeouts + - Streaming Downloads + - `.netrc` Support + - Chunked Requests + + Requests officially supports Python 2.7 & 3.4–3.7, and runs great on + PyPy. + + Installation + ------------ + + To install Requests, simply use [pipenv](http://pipenv.org/) (or pip, of + course): + + ``` {.sourceCode .bash} + $ pipenv install requests + ✨🍰✨ + ``` + + Satisfaction guaranteed. + + Documentation + ------------- + + Fantastic documentation is available at + , for a limited time only. + + How to Contribute + ----------------- + + 1. Become more familiar with the project by reading our [Contributor's Guide](http://docs.python-requests.org/en/latest/dev/contributing/) and our [development philosophy](http://docs.python-requests.org/en/latest/dev/philosophy/). + 2. Check for open issues or open a fresh issue to start a discussion + around a feature idea or a bug. There is a [Contributor + Friendly](https://github.com/requests/requests/issues?direction=desc&labels=Contributor+Friendly&page=1&sort=updated&state=open) + tag for issues that should be ideal for people who are not very + familiar with the codebase yet. + 3. Fork [the repository](https://github.com/requests/requests) on + GitHub to start making your changes to the **master** branch (or + branch off of it). + 4. Write a test which shows that the bug was fixed or that the feature + works as expected. + 5. Send a pull request and bug the maintainer until it gets merged and + published. :) Make sure to add yourself to + [AUTHORS](https://github.com/requests/requests/blob/master/AUTHORS.rst). + + +Platform: UNKNOWN +Classifier: Development Status :: 5 - Production/Stable +Classifier: Intended Audience :: Developers +Classifier: Natural Language :: English +Classifier: License :: OSI Approved :: Apache Software License +Classifier: Programming Language :: Python +Classifier: Programming Language :: Python :: 2 +Classifier: Programming Language :: Python :: 2.7 +Classifier: Programming Language :: Python :: 3 +Classifier: Programming Language :: Python :: 3.5 +Classifier: Programming Language :: Python :: 3.6 +Classifier: Programming Language :: Python :: 3.7 +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Programming Language :: Python :: Implementation :: PyPy +Requires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.* +Description-Content-Type: text/markdown +Provides-Extra: security +Provides-Extra: socks \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/PKG-INFO-INVALID b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/PKG-INFO-INVALID new file mode 100644 index 0000000000000000000000000000000000000000..173d8c5126b25432fe1920a1229e043cef6b9d62 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/PKG-INFO-INVALID @@ -0,0 +1,69 @@ +Metadata-Version: 1.1 +Name: mxnet +Version: 1.8.0 +Summary: + + + + + + + + + + + + + + + + +MXNet Python Package +==================== +This directory and nested files contain MXNet Python package and language binding. + +## Installation +To install MXNet Python package, visit MXNet [Install Instruction](https://mxnet.apache.org/get_started) + + +## Running the unit tests + +For running unit tests, you will need the [nose PyPi package](https://pypi.python.org/pypi/nose). To install: +```bash +pip install --upgrade nose +``` + +Once ```nose``` is installed, run the following from MXNet root directory (please make sure the installation path of ```nosetests``` is included in your ```$PATH``` environment variable): +``` +nosetests tests/python/unittest +nosetests tests/python/train + +``` + +Home-page: https://github.com/apache/incubator-mxnet +Author: UNKNOWN +Author-email: UNKNOWN +License: UNKNOWN +Description: UNKNOWN +Platform: UNKNOWN +Classifier: Development Status :: 5 - Production/Stable +Classifier: Intended Audience :: Developers +Classifier: Intended Audience :: Education +Classifier: Intended Audience :: Science/Research +Classifier: License :: OSI Approved :: Apache Software License +Classifier: Programming Language :: C++ +Classifier: Programming Language :: Cython +Classifier: Programming Language :: Other +Classifier: Programming Language :: Perl +Classifier: Programming Language :: Python +Classifier: Programming Language :: Python :: 2.7 +Classifier: Programming Language :: Python :: 3.4 +Classifier: Programming Language :: Python :: 3.5 +Classifier: Programming Language :: Python :: 3.6 +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Topic :: Scientific/Engineering +Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence +Classifier: Topic :: Scientific/Engineering :: Mathematics +Classifier: Topic :: Software Development +Classifier: Topic :: Software Development :: Libraries +Classifier: Topic :: Software Development :: Libraries :: Python Modules diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/RECORD b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/RECORD new file mode 100644 index 0000000000000000000000000000000000000000..a2c2f97c353487e2bb91e1cac29f4e6056ab2057 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/RECORD @@ -0,0 +1,6 @@ +requests-2.22.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4 +requests/__init__.py,sha256=PnKCgjcTq44LaAMzB-7--B2FdewRrE8F_vjZeaG9NhA,3921 +requests/__pycache__/__version__.cpython-38.pyc,, +requests/__pycache__/utils.cpython-38.pyc,, +requests/__version__.py,sha256=Bm-GFstQaFezsFlnmEMrJDe8JNROz9n2XXYtODdvjjc,436 +requests/utils.py,sha256=LtPJ1db6mJff2TJSJWKi7rBpzjPS3mSOrjC9zRhoD3A,30049 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/top_level.txt b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/top_level.txt new file mode 100644 index 0000000000000000000000000000000000000000..663bd1f6a2ae02f29df59fb4963c17934034f731 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/egg-info/top_level.txt @@ -0,0 +1 @@ +requests \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/empty-1.0.0-py3.8.egg-info b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/empty-1.0.0-py3.8.egg-info new file mode 100644 index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/no-version-py3.8.egg-info b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/no-version-py3.8.egg-info new file mode 100644 index 0000000000000000000000000000000000000000..085ae6e87498030c5e409292b3a8602b1677eb9e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/no-version-py3.8.egg-info @@ -0,0 +1 @@ +Name: no-version diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/partial.dist-info/METADATA b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/partial.dist-info/METADATA new file mode 100644 index 0000000000000000000000000000000000000000..924780dfd45ab61f303185f3fa4d969ec2c336aa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/partial.dist-info/METADATA @@ -0,0 +1,47 @@ +Metadata-Version: 2.1 +Name: Pygments +Version: 2.6.1 +Summary: Pygments is a syntax highlighting package written in Python. +Home-page: https://pygments.org/ +Author: Georg Brandl +Author-email: georg@python.org +License: BSD License +Keywords: syntax highlighting +Platform: any +Classifier: License :: OSI Approved :: BSD License +Classifier: Intended Audience :: Developers +Classifier: Intended Audience :: End Users/Desktop +Classifier: Intended Audience :: System Administrators +Classifier: Development Status :: 6 - Mature +Classifier: Programming Language :: Python +Classifier: Programming Language :: Python :: 3 +Classifier: Programming Language :: Python :: 3.5 +Classifier: Programming Language :: Python :: 3.6 +Classifier: Programming Language :: Python :: 3.7 +Classifier: Programming Language :: Python :: 3.8 +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Programming Language :: Python :: Implementation :: PyPy +Classifier: Operating System :: OS Independent +Classifier: Topic :: Text Processing :: Filters +Classifier: Topic :: Utilities +Requires-Python: >=3.5 + + +Pygments +~~~~~~~~ + +Pygments is a syntax highlighting package written in Python. + +It is a generic syntax highlighter suitable for use in code hosting, forums, +wikis or other applications that need to prettify source code. Highlights +are: + +* a wide range of over 500 languages and other text formats is supported +* special attention is paid to details, increasing quality by a fair amount +* support for new languages and formats are added easily +* a number of output formats, presently HTML, LaTeX, RTF, SVG, all image formats that PIL supports and ANSI sequences +* it is usable as a command-line tool and as a library + +:copyright: Copyright 2006-2019 by the Pygments team, see AUTHORS. +:license: BSD, see LICENSE for details. + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/pipfile-lock/Pipfile.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/pipfile-lock/Pipfile.lock new file mode 100644 index 0000000000000000000000000000000000000000..78a6f10382ea605290b9eb9d706bdc32a758c4d1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/pipfile-lock/Pipfile.lock @@ -0,0 +1,69 @@ +{ + "_meta": { + "hash": { + "sha256": "a6b2dfd5367688bec81240eb04e7bde7f92b35491be5934fcb4e2e6ca9d275c0" + }, + "pipfile-spec": 6, + "requires": { + "python_version": "3.8" + }, + "sources": [ + { + "name": "pypi", + "url": "https://pypi.org/simple", + "verify_ssl": true + } + ] + }, + "default": { + "aio-pika": { + "hashes": [ + "sha256:1d4305a5f78af3857310b4fe48348cdcf6c097e0e275ea88c2cd08570531a369", + "sha256:e69afef8695f47c5d107bbdba21bdb845d5c249acb3be53ef5c2d497b02657c0" + ], + "index": "pypi", + "version": "==6.8.0" + }, + "aiodns": { + "hashes": [ + "sha256:815fdef4607474295d68da46978a54481dd1e7be153c7d60f9e72773cd38d77d", + "sha256:aaa5ac584f40fe778013df0aa6544bf157799bd3f608364b451840ed2c8688de" + ], + "index": "pypi", + "version": "==2.0.0" + }, + "aiohttp": { + "hashes": [ + "sha256:02f46fc0e3c5ac58b80d4d56eb0a7c7d97fcef69ace9326289fb9f1955e65cfe", + "sha256:0563c1b3826945eecd62186f3f5c7d31abb7391fedc893b7e2b26303b5a9f3fe" + ], + "index": "pypi", + "version": "==3.7.4.post0" + }, + "aiohttp-jinja2": { + "hashes": [ + "sha256:860da7582efa866744bad5883947557d0f82e457d69903ea65d666b66f8a69ca", + "sha256:9c22a0e48e3b277fc145c67dd8c3b8f609dab36bce9eb337f70dfe716663c9a0" + ], + "index": "pypi", + "version": "==1.4.2" + } + }, + "develop": { + "astroid": { + "hashes": [ + "sha256:6b0ed1af831570e500e2437625979eaa3b36011f66ddfc4ce930128610258ca9", + "sha256:cd80bf957c49765dce6d92c43163ff9d2abc43132ce64d4b1b47717c6d2522df" + ], + "version": "==2.5.2" + }, + "autopep8": { + "hashes": [ + "sha256:5454e6e9a3d02aae38f866eec0d9a7de4ab9f93c10a273fb0340f3d6d09f7514", + "sha256:f01b06a6808bc31698db907761e5890eb2295e287af53f6693b39ce55454034a" + ], + "index": "pypi", + "version": "==1.5.6" + } + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/poetry/poetry.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/poetry/poetry.lock new file mode 100644 index 0000000000000000000000000000000000000000..489f1df6d6dd385f79543abb4efbd0d09a55d589 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/poetry/poetry.lock @@ -0,0 +1,64 @@ +[[package]] +category = "dev" +description = "Sphinx \"added-value\" extension" +name = "added-value" +optional = false +python-versions = "*" +version = "0.14.2" + +[package.dependencies] +docutils = "*" +natsort = "*" +six = "*" +sphinx = "*" + +[package.extras] +deploy = ["bumpversion", "twine", "wheel"] +docs = ["sphinx", "sphinx-rtd-theme"] +test = ["pytest", "pytest-cov", "coveralls", "beautifulsoup4", "hypothesis"] + +[[package]] +category = "dev" +description = "A configurable sidebar-enabled Sphinx theme" +name = "alabaster" +optional = false +python-versions = "*" +version = "0.7.12" + +[[package]] +category = "dev" +description = "Disable App Nap on OS X 10.9" +marker = "python_version >= \"3.4\" and sys_platform == \"darwin\" or sys_platform == \"darwin\"" +name = "appnope" +optional = false +python-versions = "*" +version = "0.1.0" + +[[package]] +category = "dev" +description = "Draws ASCII trees." +name = "asciitree" +optional = false +python-versions = "*" +version = "0.3.3" + +[metadata] +content-hash = "6e35f765c2f01c635c2fb0d54a9d7dd68742350f04449ee24efad03e3c9eb0bb" +python-versions = "^3.6" + +[metadata.files] +added-value = [ + {file = "added-value-0.14.2.tar.gz", hash = "sha256:8c886aee74635cec15beb64c28a90ae664526f331c1a4941e4d6ab98af232028"}, + {file = "added_value-0.14.2-py2.py3-none-any.whl", hash = "sha256:b25fcb86f9bfad9a40adf4d344322690e312741556c7b75681bc948380a251e6"}, +] +alabaster = [ + {file = "alabaster-0.7.12-py2.py3-none-any.whl", hash = "sha256:446438bdcca0e05bd45ea2de1668c1d9b032e1a9154c2c259092d77031ddd359"}, + {file = "alabaster-0.7.12.tar.gz", hash = "sha256:a661d72d58e6ea8a57f7a86e37d86716863ee5e92788398526d58b26a4e4dc02"}, +] +appnope = [ + {file = "appnope-0.1.0-py2.py3-none-any.whl", hash = "sha256:5b26757dc6f79a3b7dc9fab95359328d5747fcb2409d331ea66d0272b90ab2a0"}, + {file = "appnope-0.1.0.tar.gz", hash = "sha256:8b995ffe925347a2138d7ac0fe77155e4311a0ea6d6da4f5128fe4b3cbe5ed71"}, +] +asciitree = [ + {file = "asciitree-0.3.3.tar.gz", hash = "sha256:4aa4b9b649f85e3fcb343363d97564aa1fb62e249677f2e18a96765145cc0f6e"}, +] diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/requires/requirements.txt b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/requires/requirements.txt new file mode 100644 index 0000000000000000000000000000000000000000..d66036398631edf3c33e6b1bc115e2d66164e281 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/requires/requirements.txt @@ -0,0 +1,12 @@ + flask == 4.0.0 +# a line that is ignored +sqlalchemy >= 1.0.0 + foo == 1.0.0 # a comment that needs to be ignored +-e https://github.com/pecan/pecan.git +-r other-requirements.txt +--requirements super-secretrequirements.txt +SomeProject ==5.4 ; python_version < '3.8' +coverage != 3.5 # Version Exclusion. Anything except version 3.5 +numpyNew; sys_platform == 'win32' +numpy >= 3.4.1; sys_platform == 'win32' +Mopidy-Dirble ~= 1.1 # Compatible release. Same as >= 1.1, == 1.* diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/setup/setup.py b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/setup/setup.py new file mode 100644 index 0000000000000000000000000000000000000000..266c8c0ff2f0a8a89ccad14ac5bfa277c6722cb5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/setup/setup.py @@ -0,0 +1,46 @@ +from setuptools import setup + +# Sample setup.py from the pytest project with added comments specific +# to the cataloger + +INSTALL_REQUIRES = [ + "py>=1.5.0", + "packaging", + "attrs>=17.4.0", + "more-itertools>=4.0.0", + 'atomicwrites>=1.0;sys_platform=="win32"', # sys_platform is ignored + 'pathlib2>=2.2.0;python_version=="3.6"', # python_version is ignored + 'pathlib3==2.2.0;python_version<"3.6"', # this is caught + 'colorama;sys_platform=="win32"', + "pluggy>=0.12,<1.0", + 'importlib-metadata>=0.12;python_version<"3.8"', + "wcwidth", +] + + +def main(): + setup( + use_scm_version={"write_to": "src/_pytest/_version.py"}, + setup_requires=["setuptools-scm", "setuptools>=40.0"], + package_dir={"": "src"}, + extras_require={ + "testing": [ + "argcomplete", + "hypothesis>=3.56", + "mock", + "nose", + "requests", + "xmlschema", + ], + "checkqa-mypy": [ + "mypy==v0.770", # this is caught + " mypy1==v0.770", # this is caught + " mypy2 == v0.770", ' mypy3== v0.770', # this is caught + ], + }, + install_requires=INSTALL_REQUIRES, + ) + + +if __name__ == "__main__": + main() diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/test.egg-info b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/test.egg-info new file mode 100644 index 0000000000000000000000000000000000000000..a73770668150c2bea1b4d7b807aeb058b18ebcc8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/python/test-fixtures/test.egg-info @@ -0,0 +1,134 @@ +Metadata-Version: 2.1 +Name: requests +Version: 2.22.0 +Summary: Python HTTP for Humans. +Home-page: http://python-requests.org +Author: Kenneth Reitz +Author-email: me@kennethreitz.org +License: Apache 2.0 +Description: Requests: HTTP for Humans™ + ========================== + + [![image](https://img.shields.io/pypi/v/requests.svg)](https://pypi.org/project/requests/) + [![image](https://img.shields.io/pypi/l/requests.svg)](https://pypi.org/project/requests/) + [![image](https://img.shields.io/pypi/pyversions/requests.svg)](https://pypi.org/project/requests/) + [![codecov.io](https://codecov.io/github/requests/requests/coverage.svg?branch=master)](https://codecov.io/github/requests/requests) + [![image](https://img.shields.io/github/contributors/requests/requests.svg)](https://github.com/requests/requests/graphs/contributors) + [![image](https://img.shields.io/badge/Say%20Thanks-!-1EAEDB.svg)](https://saythanks.io/to/kennethreitz) + + Requests is the only *Non-GMO* HTTP library for Python, safe for human + consumption. + + ![image](https://farm5.staticflickr.com/4317/35198386374_1939af3de6_k_d.jpg) + + Behold, the power of Requests: + + ``` {.sourceCode .python} + >>> import requests + >>> r = requests.get('https://api.github.com/user', auth=('user', 'pass')) + >>> r.status_code + 200 + >>> r.headers['content-type'] + 'application/json; charset=utf8' + >>> r.encoding + 'utf-8' + >>> r.text + u'{"type":"User"...' + >>> r.json() + {u'disk_usage': 368627, u'private_gists': 484, ...} + ``` + + See [the similar code, sans Requests](https://gist.github.com/973705). + + [![image](https://raw.githubusercontent.com/requests/requests/master/docs/_static/requests-logo-small.png)](http://docs.python-requests.org/) + + Requests allows you to send *organic, grass-fed* HTTP/1.1 requests, + without the need for manual labor. There's no need to manually add query + strings to your URLs, or to form-encode your POST data. Keep-alive and + HTTP connection pooling are 100% automatic, thanks to + [urllib3](https://github.com/shazow/urllib3). + + Besides, all the cool kids are doing it. Requests is one of the most + downloaded Python packages of all time, pulling in over 11,000,000 + downloads every month. You don't want to be left out! + + Feature Support + --------------- + + Requests is ready for today's web. + + - International Domains and URLs + - Keep-Alive & Connection Pooling + - Sessions with Cookie Persistence + - Browser-style SSL Verification + - Basic/Digest Authentication + - Elegant Key/Value Cookies + - Automatic Decompression + - Automatic Content Decoding + - Unicode Response Bodies + - Multipart File Uploads + - HTTP(S) Proxy Support + - Connection Timeouts + - Streaming Downloads + - `.netrc` Support + - Chunked Requests + + Requests officially supports Python 2.7 & 3.4–3.7, and runs great on + PyPy. + + Installation + ------------ + + To install Requests, simply use [pipenv](http://pipenv.org/) (or pip, of + course): + + ``` {.sourceCode .bash} + $ pipenv install requests + ✨🍰✨ + ``` + + Satisfaction guaranteed. + + Documentation + ------------- + + Fantastic documentation is available at + , for a limited time only. + + How to Contribute + ----------------- + + 1. Become more familiar with the project by reading our [Contributor's Guide](http://docs.python-requests.org/en/latest/dev/contributing/) and our [development philosophy](http://docs.python-requests.org/en/latest/dev/philosophy/). + 2. Check for open issues or open a fresh issue to start a discussion + around a feature idea or a bug. There is a [Contributor + Friendly](https://github.com/requests/requests/issues?direction=desc&labels=Contributor+Friendly&page=1&sort=updated&state=open) + tag for issues that should be ideal for people who are not very + familiar with the codebase yet. + 3. Fork [the repository](https://github.com/requests/requests) on + GitHub to start making your changes to the **master** branch (or + branch off of it). + 4. Write a test which shows that the bug was fixed or that the feature + works as expected. + 5. Send a pull request and bug the maintainer until it gets merged and + published. :) Make sure to add yourself to + [AUTHORS](https://github.com/requests/requests/blob/master/AUTHORS.rst). + + +Platform: UNKNOWN +Classifier: Development Status :: 5 - Production/Stable +Classifier: Intended Audience :: Developers +Classifier: Natural Language :: English +Classifier: License :: OSI Approved :: Apache Software License +Classifier: Programming Language :: Python +Classifier: Programming Language :: Python :: 2 +Classifier: Programming Language :: Python :: 2.7 +Classifier: Programming Language :: Python :: 3 +Classifier: Programming Language :: Python :: 3.5 +Classifier: Programming Language :: Python :: 3.6 +Classifier: Programming Language :: Python :: 3.7 +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Programming Language :: Python :: Implementation :: PyPy +Requires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.* +Description-Content-Type: text/markdown +Provides-Extra: security +Provides-Extra: socks \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/db_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/db_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..67169c4d88a4fa7f0255f7d921ec9ecc87e2f7e0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/db_cataloger.go @@ -0,0 +1,75 @@ +/* +Package rpm provides a concrete DBCataloger implementation for RPM "Package" DB files +and a FileCataloger for RPM files. +*/ +package rpm + +import ( + "fmt" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +const dbCatalogerName = "rpm-db-cataloger" + +type DBCataloger struct{} + +// NewRpmdbCataloger returns a new RPM DB cataloger object. +func NewRpmdbCataloger() *DBCataloger { + return &DBCataloger{} +} + +// Name returns a string that uniquely describes a cataloger +func (c *DBCataloger) Name() string { + return dbCatalogerName +} + +// Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing rpm db installation. +func (c *DBCataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + fileMatches, err := resolver.FilesByGlob(pkg.RpmDBGlob) + if err != nil { + return nil, nil, fmt.Errorf("failed to find rpmdb's by glob: %w", err) + } + + var pkgs []pkg.Package + for _, location := range fileMatches { + dbContentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + return nil, nil, err + } + + discoveredPkgs, err := parseRpmDB(resolver, location, dbContentReader) + internal.CloseAndLogError(dbContentReader, location.VirtualPath) + if err != nil { + return nil, nil, fmt.Errorf("unable to catalog rpmdb package=%+v: %w", location.RealPath, err) + } + + pkgs = append(pkgs, discoveredPkgs...) + } + + // Additionally look for RPM manifest files to detect packages in CBL-Mariner distroless images + manifestFileMatches, err := resolver.FilesByGlob(pkg.RpmManifestGlob) + if err != nil { + return nil, nil, fmt.Errorf("failed to find rpm manifests by glob: %w", err) + } + + for _, location := range manifestFileMatches { + reader, err := resolver.FileContentsByLocation(location) + if err != nil { + return nil, nil, err + } + + discoveredPkgs, err := parseRpmManifest(location, reader) + internal.CloseAndLogError(reader, location.VirtualPath) + if err != nil { + return nil, nil, fmt.Errorf("unable to catalog rpm manifest=%+v: %w", location.RealPath, err) + } + + pkgs = append(pkgs, discoveredPkgs...) + } + + return pkgs, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/file_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/file_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..6ae85de0d0a0587680fe3be0fb272e6ab46b8184 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/file_cataloger.go @@ -0,0 +1,136 @@ +package rpm + +import ( + "fmt" + "strconv" + "strings" + + rpmdb "github.com/knqyf263/go-rpmdb/pkg" + "github.com/sassoftware/go-rpmutils" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +type FileCataloger struct{} + +// NewFileCataloger returns a new RPM file cataloger object. +func NewFileCataloger() *FileCataloger { + return &FileCataloger{} +} + +// Name returns a string that uniquely describes a cataloger +func (c *FileCataloger) Name() string { + return "rpm-file-cataloger" +} + +// Catalog is given an object to resolve file references and content, this function returns any discovered Packages after analyzing rpm files +func (c *FileCataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + fileMatches, err := resolver.FilesByGlob("**/*.rpm") + if err != nil { + return nil, nil, fmt.Errorf("failed to find rpm files's by glob: %w", err) + } + + var pkgs []pkg.Package + for _, location := range fileMatches { + contentReader, err := resolver.FileContentsByLocation(location) + if err != nil { + return nil, nil, err + } + + rpm, err := rpmutils.ReadRpm(contentReader) + if err != nil { + return nil, nil, err + } + + nevra, err := rpm.Header.GetNEVRA() + if err != nil { + return nil, nil, err + } + + licenses, _ := rpm.Header.GetStrings(rpmutils.LICENSE) + sourceRpm, _ := rpm.Header.GetString(rpmutils.SOURCERPM) + vendor, _ := rpm.Header.GetString(rpmutils.VENDOR) + digestAlgorithm := getDigestAlgorithm(rpm.Header) + size, _ := rpm.Header.InstalledSize() + files, _ := rpm.Header.GetFiles() + + p := pkg.Package{ + Name: nevra.Name, + Version: nevra.Version, + FoundBy: c.Name(), + Licenses: licenses, + Locations: source.NewLocationSet(location), + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: pkg.RpmMetadata{ + Name: nevra.Name, + Version: nevra.Version, + Epoch: parseEpoch(nevra.Epoch), + Arch: nevra.Arch, + Release: nevra.Release, + SourceRpm: sourceRpm, + Vendor: vendor, + License: strings.Join(licenses, " AND "), + Size: int(size), + Files: mapFiles(files, digestAlgorithm), + }, + } + p.SetID() + pkgs = append(pkgs, p) + + internal.CloseAndLogError(contentReader, location.VirtualPath) + if err != nil { + return nil, nil, fmt.Errorf("unable to catalog rpm file=%+v: %w", location.RealPath, err) + } + } + + return pkgs, nil, nil +} + +func getDigestAlgorithm(header *rpmutils.RpmHeader) string { + digestAlgorithm, _ := header.GetString(rpmutils.FILEDIGESTALGO) + if digestAlgorithm != "" { + return digestAlgorithm + } + digestAlgorithms, _ := header.GetUint32s(rpmutils.FILEDIGESTALGO) + if len(digestAlgorithms) > 0 { + digestAlgo := int(digestAlgorithms[0]) + return rpmutils.GetFileAlgoName(digestAlgo) + } + return "" +} + +func mapFiles(files []rpmutils.FileInfo, digestAlgorithm string) []pkg.RpmdbFileRecord { + var out []pkg.RpmdbFileRecord + for _, f := range files { + digest := file.Digest{} + if f.Digest() != "" { + digest = file.Digest{ + Algorithm: digestAlgorithm, + Value: f.Digest(), + } + } + out = append(out, pkg.RpmdbFileRecord{ + Path: f.Name(), + Mode: pkg.RpmdbFileMode(f.Mode()), + Size: int(f.Size()), + Digest: digest, + UserName: f.UserName(), + GroupName: f.GroupName(), + Flags: rpmdb.FileFlags(f.Flags()).String(), + }) + } + return out +} + +func parseEpoch(epoch string) *int { + i, err := strconv.Atoi(epoch) + if err != nil { + return nil + } + return &i +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/file_cataloger_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/file_cataloger_test.go new file mode 100644 index 0000000000000000000000000000000000000000..da4752d5b921c9b3cb22b67cb21b5935bd1a9da6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/file_cataloger_test.go @@ -0,0 +1,106 @@ +package rpm + +import ( + "testing" + + "github.com/go-test/deep" + "github.com/stretchr/testify/require" + + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +func TestParseRpmFiles(t *testing.T) { + tests := []struct { + fixture string + expected map[string]pkg.Package + }{ + { + fixture: "test-fixtures/rpms", + expected: map[string]pkg.Package{ + "abc": { + Name: "abc", + Version: "1.01", + Locations: source.NewLocationSet(), + FoundBy: "rpm-file-cataloger", + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Licenses: []string{"MIT"}, + Metadata: pkg.RpmMetadata{ + Name: "abc", + Epoch: intRef(0), + Arch: "x86_64", + Release: "9.hg20160905.el7", + Version: "1.01", + SourceRpm: "abc-1.01-9.hg20160905.el7.src.rpm", + Size: 17396, + License: "MIT", + Vendor: "Fedora Project", + Files: []pkg.RpmdbFileRecord{ + {"/usr/bin/abc", 33261, 7120, file.Digest{"sha256", "8f8495a65c66762b60afa0c3949d81b275ca6fa0601696caba5af762f455d0b9"}, "root", "root", ""}, + {"/usr/share/doc/abc-1.01", 16877, 4096, file.Digest{}, "root", "root", ""}, + {"/usr/share/doc/abc-1.01/readme.md", 33188, 4984, file.Digest{"sha256", "808af8a28391e96ca0d91086789488dda3724fe7c8b2859efd464fb04b94b2d4"}, "root", "root", "d"}, + {"/usr/share/doc/abc-1.01/readmeaig", 33188, 3324, file.Digest{"sha256", "530ec6175cf7fbeb7b595cbe7a50994429c4e62cae6666fb3a1d5745f3127b19"}, "root", "root", "d"}, + {"/usr/share/man/man1/abc.1.gz", 33188, 1968, file.Digest{"sha256", "cf2cfe25b29087e60ffd5f31f974a0762172fc2f009704951f12ff750ea77ed6"}, "root", "root", "d"}, + }, + }, + }, + "zork": { + Name: "zork", + Version: "1.0.3", + Locations: source.NewLocationSet(), + FoundBy: "rpm-file-cataloger", + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Licenses: []string{"Public Domain"}, + Metadata: pkg.RpmMetadata{ + Name: "zork", + Epoch: intRef(0), + Arch: "x86_64", + Release: "1.el7", + Version: "1.0.3", + SourceRpm: "zork-1.0.3-1.el7.src.rpm", + Size: 262367, + License: "Public Domain", + Vendor: "Fedora Project", + Files: []pkg.RpmdbFileRecord{ + {"/usr/bin/zork", 33261, 115440, file.Digest{"sha256", "31b2ffc20b676a8fff795a45308f584273b9c47e8f7e196b4f36220b2734b472"}, "root", "root", ""}, + {"/usr/share/doc/zork-1.0.3", 16877, 38, file.Digest{}, "root", "root", ""}, + {"/usr/share/doc/zork-1.0.3/README.md", 33188, 5123, file.Digest{"sha256", "0013d67610a80c9f62d151a952f18d520b15b4c505b3ec2af34b96ab824654a4"}, "root", "root", "d"}, + {"/usr/share/doc/zork-1.0.3/history", 33188, 4816, file.Digest{"sha256", "6949044a65adefca6ac0132c18cfccc4ba8fdaec948424b6ccb60afd8a6ac82f"}, "root", "root", "d"}, + {"/usr/share/licenses/zork-1.0.3", 16877, 24, file.Digest{}, "root", "root", ""}, + {"/usr/share/licenses/zork-1.0.3/readme.txt", 33188, 146, file.Digest{"sha256", "9d6f7500555a2ecc3cb289dcca1e37fb96894dab1e4ba692b4d36fd6c3bdf939"}, "root", "root", "l"}, + {"/usr/share/man/man6/dungeon.6.gz", 33188, 3800, file.Digest{"sha256", "9b065d6a6f65b4d2d038fcca0af47a38e8723c32008d08659739ac34abe018da"}, "root", "root", "d"}, + {"/usr/share/man/man6/zork.6.gz", 33188, 34, file.Digest{"sha256", "18fbcb598bc40a25befe26256e29366984d2288dd154f877b8ac5fc138dd0884"}, "root", "root", "d"}, + {"/usr/share/zork/dtextc.dat", 33188, 133008, file.Digest{"sha256", "25ca42857c2b32054916d9258152293ead644023d5e03bec039ea92014e2ef91"}, "root", "root", ""}, + }, + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + s, err := source.NewFromDirectory(test.fixture) + require.NoError(t, err) + + r, err := s.FileResolver(source.SquashedScope) + require.NoError(t, err) + + packages, _, err := NewFileCataloger().Catalog(r) + require.NoError(t, err) + + for _, a := range packages { + e := test.expected[a.Name] + diffs := deep.Equal(e, a) + if len(diffs) > 0 { + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + } + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmdb.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmdb.go new file mode 100644 index 0000000000000000000000000000000000000000..5340c1258d7f7636c900cad0fbbf862853f3eca6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmdb.go @@ -0,0 +1,136 @@ +package rpm + +import ( + "fmt" + "io" + "io/ioutil" + "os" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + rpmdb "github.com/knqyf263/go-rpmdb/pkg" +) + +// parseRpmDb parses an "Packages" RPM DB and returns the Packages listed within it. +func parseRpmDB(resolver source.FilePathResolver, dbLocation source.Location, reader io.Reader) ([]pkg.Package, error) { + f, err := ioutil.TempFile("", internal.ApplicationName+"-rpmdb") + if err != nil { + return nil, fmt.Errorf("failed to create temp rpmdb file: %w", err) + } + + defer func() { + err = os.Remove(f.Name()) + if err != nil { + log.Errorf("failed to remove temp rpmdb file: %+v", err) + } + }() + + _, err = io.Copy(f, reader) + if err != nil { + return nil, fmt.Errorf("failed to copy rpmdb contents to temp file: %w", err) + } + + db, err := rpmdb.Open(f.Name()) + if err != nil { + return nil, err + } + + pkgList, err := db.ListPackages() + if err != nil { + return nil, err + } + + var allPkgs []pkg.Package + + for _, entry := range pkgList { + p := newPkg(resolver, dbLocation, entry) + + if !pkg.IsValid(&p) { + log.Warnf("ignoring invalid package found in RPM DB: location=%q name=%q version=%q", dbLocation, entry.Name, entry.Version) + continue + } + + p.SetID() + allPkgs = append(allPkgs, p) + } + + return allPkgs, nil +} + +func newPkg(resolver source.FilePathResolver, dbLocation source.Location, entry *rpmdb.PackageInfo) pkg.Package { + metadata := pkg.RpmMetadata{ + Name: entry.Name, + Version: entry.Version, + Epoch: entry.Epoch, + Arch: entry.Arch, + Release: entry.Release, + SourceRpm: entry.SourceRpm, + Vendor: entry.Vendor, + License: entry.License, + Size: entry.Size, + ModularityLabel: entry.Modularitylabel, + Files: extractRpmdbFileRecords(resolver, entry), + } + + p := pkg.Package{ + Name: entry.Name, + Version: toELVersion(metadata), + Locations: source.NewLocationSet(dbLocation), + FoundBy: dbCatalogerName, + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: metadata, + } + + if entry.License != "" { + p.Licenses = append(p.Licenses, entry.License) + } + + p.SetID() + return p +} + +// The RPM naming scheme is [name]-[version]-[release]-[arch], where version is implicitly expands to [epoch]:[version]. +// RPM version comparison depends on comparing at least the version and release fields together as a subset of the +// naming scheme. This toELVersion function takes a RPM DB package information and converts it into a minimally comparable +// version string, containing epoch (optional), version, and release information. Epoch is an optional field and can be +// assumed to be 0 when not provided for comparison purposes, however, if the underlying RPM DB entry does not have +// an epoch specified it would be slightly disingenuous to display a value of 0. +func toELVersion(metadata pkg.RpmMetadata) string { + if metadata.Epoch != nil { + return fmt.Sprintf("%d:%s-%s", *metadata.Epoch, metadata.Version, metadata.Release) + } + return fmt.Sprintf("%s-%s", metadata.Version, metadata.Release) +} + +func extractRpmdbFileRecords(resolver source.FilePathResolver, entry *rpmdb.PackageInfo) []pkg.RpmdbFileRecord { + var records = make([]pkg.RpmdbFileRecord, 0) + + files, err := entry.InstalledFiles() + if err != nil { + log.Warnf("unable to parse listing of installed files for RPM DB entry: %s", err.Error()) + return records + } + + for _, record := range files { + // only persist RPMDB file records which exist in the image/directory, otherwise ignore them + if resolver.HasPath(record.Path) { + records = append(records, pkg.RpmdbFileRecord{ + Path: record.Path, + Mode: pkg.RpmdbFileMode(record.Mode), + Size: int(record.Size), + Digest: file.Digest{ + Value: record.Digest, + Algorithm: entry.DigestAlgorithm.String(), + }, + UserName: record.Username, + GroupName: record.Groupname, + Flags: record.Flags.String(), + }) + } + } + return records +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmdb_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmdb_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4838c0d96d71b3a6b6ee2bbfaf18972dba64b443 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmdb_test.go @@ -0,0 +1,216 @@ +package rpm + +import ( + "fmt" + "os" + "testing" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/file" + + "github.com/anchore/syft/syft/source" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +type rpmdbTestFileResolverMock struct { + ignorePaths bool +} + +func newTestFileResolver(ignorePaths bool) *rpmdbTestFileResolverMock { + return &rpmdbTestFileResolverMock{ + ignorePaths: ignorePaths, + } +} + +func (r rpmdbTestFileResolverMock) HasPath(path string) bool { + return !r.ignorePaths +} + +func (r *rpmdbTestFileResolverMock) FilesByPath(paths ...string) ([]source.Location, error) { + if r.ignorePaths { + // act as if no paths exist + return nil, nil + } + // act as if all files exist + var locations = make([]source.Location, len(paths)) + for i, p := range paths { + locations[i] = source.NewLocation(p) + } + return locations, nil +} + +func (r *rpmdbTestFileResolverMock) FilesByGlob(...string) ([]source.Location, error) { + return nil, fmt.Errorf("not implemented") +} + +func (r *rpmdbTestFileResolverMock) RelativeFileByPath(source.Location, string) *source.Location { + panic(fmt.Errorf("not implemented")) + return nil +} + +func (r *rpmdbTestFileResolverMock) FilesByMIMEType(...string) ([]source.Location, error) { + return nil, fmt.Errorf("not implemented") +} + +func TestParseRpmDB(t *testing.T) { + dbLocation := source.NewLocation("test-path") + + tests := []struct { + fixture string + expected map[string]pkg.Package + ignorePaths bool + }{ + { + fixture: "test-fixtures/Packages", + // we only surface package paths for files that exist (here we DO NOT expect a path) + ignorePaths: true, + expected: map[string]pkg.Package{ + "dive": { + Name: "dive", + Version: "0.9.2-1", + Locations: source.NewLocationSet(dbLocation), + FoundBy: dbCatalogerName, + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Licenses: []string{"MIT"}, + Metadata: pkg.RpmMetadata{ + Name: "dive", + Epoch: nil, + Arch: "x86_64", + Release: "1", + Version: "0.9.2", + SourceRpm: "dive-0.9.2-1.src.rpm", + Size: 12406784, + License: "MIT", + Vendor: "", + Files: []pkg.RpmdbFileRecord{}, + }, + }, + }, + }, + { + fixture: "test-fixtures/Packages", + // we only surface package paths for files that exist (here we expect a path) + ignorePaths: false, + expected: map[string]pkg.Package{ + "dive": { + Name: "dive", + Version: "0.9.2-1", + Locations: source.NewLocationSet(dbLocation), + FoundBy: dbCatalogerName, + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Licenses: []string{"MIT"}, + Metadata: pkg.RpmMetadata{ + Name: "dive", + Epoch: nil, + Arch: "x86_64", + Release: "1", + Version: "0.9.2", + SourceRpm: "dive-0.9.2-1.src.rpm", + Size: 12406784, + License: "MIT", + Vendor: "", + Files: []pkg.RpmdbFileRecord{ + { + Path: "/usr/local/bin/dive", + Mode: 33261, + Size: 12406784, + Digest: file.Digest{ + Algorithm: "sha256", + Value: "81d29f327ba23096b3c52ff6fe1c425641e618bc87b5c05ee377edc650afaa55", + }, + // note: there is no username, groupname, or flags for this RPM + }, + }, + }, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + fixture, err := os.Open(test.fixture) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + fileResolver := newTestFileResolver(test.ignorePaths) + + actual, err := parseRpmDB(fileResolver, dbLocation, fixture) + if err != nil { + t.Fatalf("failed to parse rpmdb: %+v", err) + } + + if len(actual) != len(test.expected) { + for _, a := range actual { + t.Log(" ", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(test.expected)) + } + + for _, a := range actual { + e := test.expected[a.Name] + diffs := deep.Equal(a, e) + if len(diffs) > 0 { + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + } + } + }) + } + +} + +func TestToElVersion(t *testing.T) { + tests := []struct { + name string + entry pkg.RpmMetadata + expected string + }{ + { + name: "no epoch", + entry: pkg.RpmMetadata{ + Version: "1.2.3-4", + Release: "el7", + Arch: "x86-64", + }, + expected: "1.2.3-4-el7", + }, + { + name: "with 0 epoch", + entry: pkg.RpmMetadata{ + Version: "1.2.3-4", + Release: "el7", + Arch: "x86-64", + Epoch: intRef(0), + }, + expected: "0:1.2.3-4-el7", + }, + { + name: "with non-zero epoch", + entry: pkg.RpmMetadata{ + Version: "1.2.3-4", + Release: "el7", + Arch: "x86-64", + Epoch: intRef(12), + }, + expected: "12:1.2.3-4-el7", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, toELVersion(test.entry)) + }) + } +} + +func intRef(i int) *int { + return &i +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmmanifest.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmmanifest.go new file mode 100644 index 0000000000000000000000000000000000000000..e71dce90ecf95a8260a70eea14561b0f8365910a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmmanifest.go @@ -0,0 +1,104 @@ +package rpm + +import ( + "bufio" + "fmt" + "io" + "strconv" + "strings" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +// Parses an entry in an RPM manifest file as used in Mariner distroless containers +// Each line is the output of : +// rpm --query --all --query-format "%{NAME}\t%{VERSION}-%{RELEASE}\t%{INSTALLTIME}\t%{BUILDTIME}\t%{VENDOR}\t%{EPOCH}\t%{SIZE}\t%{ARCH}\t%{EPOCHNUM}\t%{SOURCERPM}\n" +// https://github.com/microsoft/CBL-Mariner/blob/3df18fac373aba13a54bd02466e64969574f13af/toolkit/docs/how_it_works/5_misc.md?plain=1#L150 +func parseRpmManifestEntry(entry string, location source.Location) (*pkg.Package, error) { + parts := strings.Split(entry, "\t") + if len(parts) < 10 { + return nil, fmt.Errorf("unexpected number of fields in line: %s", entry) + } + + versionParts := strings.Split(parts[1], "-") + if len(versionParts) != 2 { + return nil, fmt.Errorf("unexpected version field: %s", parts[1]) + } + version := versionParts[0] + release := versionParts[1] + + converted, err := strconv.Atoi(parts[8]) + var epoch *int + if err != nil || parts[5] == "(none)" { + epoch = nil + } else { + epoch = &converted + } + + converted, err = strconv.Atoi(parts[6]) + var size int + if err == nil { + size = converted + } + + metadata := pkg.RpmMetadata{ + Name: parts[0], + Version: version, + Epoch: epoch, + Arch: parts[7], + Release: release, + SourceRpm: parts[9], + Vendor: parts[4], + Size: size, + } + + p := pkg.Package{ + Name: parts[0], + Version: toELVersion(metadata), + Locations: source.NewLocationSet(location), + FoundBy: dbCatalogerName, + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: metadata, + } + + p.SetID() + return &p, nil +} + +// Parses an RPM manifest file, as used in Mariner distroless containers, and returns the Packages listed +func parseRpmManifest(dbLocation source.Location, reader io.Reader) ([]pkg.Package, error) { + r := bufio.NewReader(reader) + allPkgs := make([]pkg.Package, 0) + + for { + line, err := r.ReadString('\n') + if err != nil { + if err == io.EOF { + break + } + return nil, err + } + + if line == "" { + continue + } + + p, err := parseRpmManifestEntry(strings.TrimSuffix(line, "\n"), dbLocation) + if err != nil { + log.Warnf("unable to parse RPM manifest entry: %w", err) + continue + } + + if !pkg.IsValid(p) { + continue + } + + p.SetID() + allPkgs = append(allPkgs, *p) + } + + return allPkgs, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmmanifest_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmmanifest_test.go new file mode 100644 index 0000000000000000000000000000000000000000..a9b73df42712eed91458c07cc292fb33f61b4539 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/parse_rpmmanifest_test.go @@ -0,0 +1,117 @@ +package rpm + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" + "github.com/go-test/deep" +) + +func TestParseRpmManifest(t *testing.T) { + location := source.NewLocation("test-path") + + fixture_path := "test-fixtures/container-manifest-2" + expected := map[string]pkg.Package{ + "mariner-release": { + Name: "mariner-release", + Version: "2.0-12.cm2", + Locations: source.NewLocationSet(location), + FoundBy: dbCatalogerName, + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: pkg.RpmMetadata{ + Name: "mariner-release", + Epoch: nil, + Arch: "noarch", + Release: "12.cm2", + Version: "2.0", + SourceRpm: "mariner-release-2.0-12.cm2.src.rpm", + Size: 580, + Vendor: "Microsoft Corporation", + }, + }, + "filesystem": { + Name: "filesystem", + Version: "1.1-9.cm2", + Locations: source.NewLocationSet(location), + FoundBy: dbCatalogerName, + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: pkg.RpmMetadata{ + Name: "filesystem", + Epoch: nil, + Arch: "x86_64", + Release: "9.cm2", + Version: "1.1", + SourceRpm: "filesystem-1.1-9.cm2.src.rpm", + Size: 7596, + Vendor: "Microsoft Corporation", + }, + }, + "glibc": { + Name: "glibc", + Version: "2.35-2.cm2", + Locations: source.NewLocationSet(location), + FoundBy: dbCatalogerName, + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: pkg.RpmMetadata{ + Name: "glibc", + Epoch: nil, + Arch: "x86_64", + Release: "2.cm2", + Version: "2.35", + SourceRpm: "glibc-2.35-2.cm2.src.rpm", + Size: 10855265, + Vendor: "Microsoft Corporation", + }, + }, + "openssl-libs": { + Name: "openssl-libs", + Version: "1.1.1k-15.cm2", + Locations: source.NewLocationSet(location), + FoundBy: dbCatalogerName, + Type: pkg.RpmPkg, + MetadataType: pkg.RpmMetadataType, + Metadata: pkg.RpmMetadata{ + Name: "openssl-libs", + Epoch: nil, + Arch: "x86_64", + Release: "15.cm2", + Version: "1.1.1k", + SourceRpm: "openssl-1.1.1k-15.cm2.src.rpm", + Size: 4365048, + Vendor: "Microsoft Corporation", + }, + }, + } + + fixture, err := os.Open(fixture_path) + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + actual, err := parseRpmManifest(location, fixture) + if err != nil { + t.Fatalf("failed to parse rpm manifest: %+v", err) + } + + if len(actual) != 12 { + for _, a := range actual { + t.Log(" ", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(expected)) + } + + for _, a := range actual[0:4] { + e := expected[a.Name] + diffs := deep.Equal(a, e) + if len(diffs) > 0 { + for _, d := range diffs { + t.Errorf("diff: %+v", d) + } + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/.gitignore b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..5eae26881b9abcdb5faa3a3afa74fda74765b1fb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/.gitignore @@ -0,0 +1,2 @@ +/rpms/* +*.fingerprint diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/Makefile b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..e280d5e60e7b44c80175d836a9f81602f8da3ebb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/Makefile @@ -0,0 +1,21 @@ +RPMSDIR=rpms + +ifndef RPMSDIR + $(error RPMSDIR is not set) +endif + +all: rpms + +clean: + rm -rf $(RPMSDIR) + +rpms: + mkdir -p $(RPMSDIR) + cd $(RPMSDIR) && curl https://dl.fedoraproject.org/pub/epel/7/x86_64/Packages/a/abc-1.01-9.hg20160905.el7.x86_64.rpm -O + cd $(RPMSDIR) && curl https://dl.fedoraproject.org/pub/epel/7/x86_64/Packages/z/zork-1.0.3-1.el7.x86_64.rpm -O + +# we need a way to determine if CI should bust the test cache based on the source material +.PHONY: $(RPMSDIR).fingerprint +$(RPMSDIR).fingerprint: + find Makefile -type f -exec sha256sum {} \; | sort | tee /dev/stderr | tee $(RPMSDIR).fingerprint + sha256sum $(RPMSDIR).fingerprint diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/Packages b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/Packages new file mode 100644 index 0000000000000000000000000000000000000000..ef499f2f85f633f175fcee575c555222af4a7b79 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/Packages differ diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/container-manifest-2 b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/container-manifest-2 new file mode 100644 index 0000000000000000000000000000000000000000..576e121ac16d20c9706b902209f81ee65cdb291a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/container-manifest-2 @@ -0,0 +1,12 @@ +mariner-release 2.0-12.cm2 1653816591 1653753130 Microsoft Corporation (none) 580 noarch 0 mariner-release-2.0-12.cm2.src.rpm +filesystem 1.1-9.cm2 1653816591 1653628924 Microsoft Corporation (none) 7596 x86_64 0 filesystem-1.1-9.cm2.src.rpm +glibc 2.35-2.cm2 1653816591 1653628955 Microsoft Corporation (none) 10855265 x86_64 0 glibc-2.35-2.cm2.src.rpm +openssl-libs 1.1.1k-15.cm2 1653816591 1653631609 Microsoft Corporation (none) 4365048 x86_64 0 openssl-1.1.1k-15.cm2.src.rpm +libgcc 11.2.0-2.cm2 1653816591 1650702349 Microsoft Corporation (none) 103960 x86_64 0 gcc-11.2.0-2.cm2.src.rpm +openssl 1.1.1k-15.cm2 1653816591 1653631609 Microsoft Corporation (none) 1286337 x86_64 0 openssl-1.1.1k-15.cm2.src.rpm +glibc-iconv 2.35-2.cm2 1653816591 1653628955 Microsoft Corporation (none) 8397230 x86_64 0 glibc-2.35-2.cm2.src.rpm +iana-etc 20211115-1.cm2 1653816591 1650711959 Microsoft Corporation (none) 4380680 noarch 0 iana-etc-20211115-1.cm2.src.rpm +tzdata 2022a-1.cm2 1653816591 1653752882 Microsoft Corporation (none) 1535764 noarch 0 tzdata-2022a-1.cm2.src.rpm +prebuilt-ca-certificates-base 2.0.0-3.cm2 1653816591 1653771776 Microsoft Corporation (none) 65684 noarch 1 prebuilt-ca-certificates-base-2.0.0-3.cm2.src.rpm +distroless-packages-minimal 0.1-2.cm2 1653816591 1650712132 Microsoft Corporation (none) 0 x86_64 0 distroless-packages-0.1-2.cm2.src.rpm +distroless-packages-base 0.1-2.cm2 1653816591 1650712132 Microsoft Corporation (none) 0 x86_64 0 distroless-packages-0.1-2.cm2.src.rpm diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/generate-fixture.sh b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/generate-fixture.sh new file mode 100755 index 0000000000000000000000000000000000000000..908a82ad3930e13ba940f64c8bfce27f11a77676 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rpm/test-fixtures/generate-fixture.sh @@ -0,0 +1,29 @@ +#!/usr/bin/env bash +set -eux + +docker create --name generate-rpmdb-fixture centos:8 sh -c 'tail -f /dev/null' + +function cleanup { + docker kill generate-rpmdb-fixture + docker rm generate-rpmdb-fixture +} +trap cleanup EXIT + +docker start generate-rpmdb-fixture +docker exec -i --tty=false generate-rpmdb-fixture bash <<-EOF + mkdir -p /scratch + cd /scratch + rpm --initdb --dbpath /scratch + curl -sSLO https://github.com/wagoodman/dive/releases/download/v0.9.2/dive_0.9.2_linux_amd64.rpm + rpm --dbpath /scratch -ivh dive_0.9.2_linux_amd64.rpm + rm dive_0.9.2_linux_amd64.rpm + rpm --dbpath /scratch -qa +EOF + +docker cp generate-rpmdb-fixture:/scratch/Packages . + +docker build -o . - < 1 && line[0] != ' ' { + // start of section + currentSection = sanitizedLine + continue + } else if !sectionsOfInterest.Contains(currentSection) { + // skip this line, we're in the wrong section + continue + } + + if isDependencyLine(line) { + candidate := strings.Fields(sanitizedLine) + if len(candidate) != 2 { + continue + } + pkgs = append(pkgs, &pkg.Package{ + Name: candidate[0], + Version: strings.Trim(candidate[1], "()"), + Language: pkg.Ruby, + Type: pkg.GemPkg, + }) + } + } + if err := scanner.Err(); err != nil { + return nil, nil, err + } + return pkgs, nil, nil +} + +func isDependencyLine(line string) bool { + if len(line) < 5 { + return false + } + return strings.Count(line[:5], " ") == 4 +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemfile_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemfile_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..56cb5f277bb0b136d56bc95910a2913839a39a19 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemfile_lock_test.go @@ -0,0 +1,102 @@ +package ruby + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" +) + +func TestParseGemfileLockEntries(t *testing.T) { + + var expectedGems = map[string]string{ + "actionmailer": "4.1.1", + "actionpack": "4.1.1", + "actionview": "4.1.1", + "activemodel": "4.1.1", + "activerecord": "4.1.1", + "activesupport": "4.1.1", + "arel": "5.0.1.20140414130214", + "bootstrap-sass": "3.1.1.1", + "builder": "3.2.2", + "coffee-rails": "4.0.1", + "coffee-script": "2.2.0", + "coffee-script-source": "1.7.0", + "erubis": "2.7.0", + "execjs": "2.0.2", + "hike": "1.2.3", + "i18n": "0.6.9", + "jbuilder": "2.0.7", + "jquery-rails": "3.1.0", + "json": "1.8.1", + "kgio": "2.9.2", + "libv8": "3.16.14.3", + "mail": "2.5.4", + "mime-types": "1.25.1", + "minitest": "5.3.4", + "multi_json": "1.10.1", + "mysql2": "0.3.16", + "polyglot": "0.3.4", + "rack": "1.5.2", + "rack-test": "0.6.2", + "rails": "4.1.1", + "railties": "4.1.1", + "raindrops": "0.13.0", + "rake": "10.3.2", + "rdoc": "4.1.1", + "ref": "1.0.5", + "sass": "3.2.19", + "sass-rails": "4.0.3", + "sdoc": "0.4.0", + "spring": "1.1.3", + "sprockets": "2.11.0", + "sprockets-rails": "2.1.3", + "sqlite3": "1.3.9", + "therubyracer": "0.12.1", + "thor": "0.19.1", + "thread_safe": "0.3.3", + "tilt": "1.4.1", + "treetop": "1.4.15", + "turbolinks": "2.2.2", + "tzinfo": "1.2.0", + "uglifier": "2.5.0", + "unicorn": "4.8.3", + } + + fixture, err := os.Open("test-fixtures/Gemfile.lock") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseGemFileLockEntries(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse gemfile lock: %+v", err) + } + + if len(actual) != len(expectedGems) { + for _, a := range actual { + t.Log(" ", a) + } + t.Fatalf("unexpected package count: %d!=%d", len(actual), len(expectedGems)) + } + + for _, a := range actual { + expectedVersion, ok := expectedGems[a.Name] + if !ok { + t.Errorf("unexpected package found: %s", a.Name) + } + + if expectedVersion != a.Version { + t.Errorf("unexpected package version (pkg=%s): %s", a.Name, a.Version) + } + + if a.Language != pkg.Ruby { + t.Errorf("bad language (pkg=%+v): %+v", a.Name, a.Language) + } + + if a.Type != pkg.GemPkg { + t.Errorf("bad package type (pkg=%+v): %+v", a.Name, a.Type) + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemspec.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemspec.go new file mode 100644 index 0000000000000000000000000000000000000000..e175c417b876b2a10f388c181ea0b958e7844758 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemspec.go @@ -0,0 +1,126 @@ +package ruby + +import ( + "bufio" + "encoding/json" + "fmt" + "io" + "regexp" + "strings" + + "github.com/anchore/syft/internal" + + "github.com/mitchellh/mapstructure" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// integrity check +var _ common.ParserFn = parseGemFileLockEntries + +type postProcessor func(string) []string + +// match example: Al\u003Ex ---> 003E +var unicodePattern = regexp.MustCompile(`\\u(?P[0-9A-F]{4})`) + +var patterns = map[string]*regexp.Regexp{ + // match example: name = "railties".freeze ---> railties + "name": regexp.MustCompile(`.*\.name\s*=\s*["']{1}(?P.*)["']{1} *`), + + // match example: version = "1.0.4".freeze ---> 1.0.4 + "version": regexp.MustCompile(`.*\.version\s*=\s*["']{1}(?P.*)["']{1} *`), + + // match example: + // homepage = "https://github.com/anchore/syft".freeze ---> https://github.com/anchore/syft + "homepage": regexp.MustCompile(`.*\.homepage\s*=\s*["']{1}(?P.*)["']{1} *`), + + // match example: files = ["exe/bundle".freeze, "exe/bundler".freeze] ---> "exe/bundle".freeze, "exe/bundler".freeze + "files": regexp.MustCompile(`.*\.files\s*=\s*\[(?P.*)\] *`), + + // match example: authors = ["Andr\u00E9 Arko".freeze, "Samuel Giddins".freeze, "Colby Swandale".freeze, + // "Hiroshi Shibata".freeze, "David Rodr\u00EDguez".freeze, "Grey Baker".freeze...] + "authors": regexp.MustCompile(`.*\.authors\s*=\s*\[(?P.*)\] *`), + + // match example: licenses = ["MIT".freeze] ----> "MIT".freeze + "licenses": regexp.MustCompile(`.*\.licenses\s*=\s*\[(?P.*)\] *`), +} + +var postProcessors = map[string]postProcessor{ + "files": processList, + "authors": processList, + "licenses": processList, +} + +func processList(s string) []string { + var results []string + for _, item := range strings.Split(s, ",") { + results = append(results, strings.Trim(item, "\" ")) + } + return results +} + +func parseGemSpecEntries(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + var pkgs []*pkg.Package + var fields = make(map[string]interface{}) + scanner := bufio.NewScanner(reader) + + for scanner.Scan() { + line := scanner.Text() + + sanitizedLine := strings.TrimSpace(line) + sanitizedLine = strings.ReplaceAll(sanitizedLine, ".freeze", "") + sanitizedLine = renderUtf8(sanitizedLine) + + if sanitizedLine == "" { + continue + } + + for field, pattern := range patterns { + matchMap := internal.MatchNamedCaptureGroups(pattern, sanitizedLine) + if value := matchMap[field]; value != "" { + if postProcessor := postProcessors[field]; postProcessor != nil { + fields[field] = postProcessor(value) + } else { + fields[field] = value + } + // TODO: know that a line could actually match on multiple patterns, this is unlikely though + break + } + } + } + + if fields["name"] != "" && fields["version"] != "" { + var metadata pkg.GemMetadata + if err := mapstructure.Decode(fields, &metadata); err != nil { + return nil, nil, fmt.Errorf("unable to decode gem metadata: %w", err) + } + + pkgs = append(pkgs, &pkg.Package{ + Name: metadata.Name, + Version: metadata.Version, + Licenses: metadata.Licenses, + Language: pkg.Ruby, + Type: pkg.GemPkg, + MetadataType: pkg.GemMetadataType, + Metadata: metadata, + }) + } + + return pkgs, nil, nil +} + +// renderUtf8 takes any string escaped string sub-sections from the ruby string and replaces those sections with the UTF8 runes. +func renderUtf8(s string) string { + fullReplacement := unicodePattern.ReplaceAllStringFunc(s, func(unicodeSection string) string { + var replacement string + // note: the json parser already has support for interpreting hex-representations of unicode escaped strings as unicode runes. + // we can do this ourselves with strconv.Atoi, or leverage the existing json package. + if err := json.Unmarshal([]byte(`"`+unicodeSection+`"`), &replacement); err != nil { + return unicodeSection + } + return replacement + }) + return fullReplacement +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemspec_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemspec_test.go new file mode 100644 index 0000000000000000000000000000000000000000..75e3fa24ef2409c561fdca3ad11630737219f126 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/parse_gemspec_test.go @@ -0,0 +1,50 @@ +package ruby + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseGemspec(t *testing.T) { + var expectedPkg = pkg.Package{ + Name: "bundler", + Version: "2.1.4", + Type: pkg.GemPkg, + Licenses: []string{"MIT"}, + Language: pkg.Ruby, + MetadataType: pkg.GemMetadataType, + Metadata: pkg.GemMetadata{ + Name: "bundler", + Version: "2.1.4", + Files: []string{"exe/bundle", "exe/bundler"}, + Authors: []string{"André Arko", "Samuel Giddins", "Colby Swandale", "Hiroshi Shibata", "David Rodríguez", "Grey Baker", "Stephanie Morillo", "Chris Morris", "James Wen", "Tim Moore", "André Medeiros", "Jessica Lynn Suttles", "Terence Lee", "Carl Lerche", "Yehuda Katz"}, + Licenses: []string{"MIT"}, + Homepage: "https://bundler.io", + }, + } + + fixture, err := os.Open("test-fixtures/bundler.gemspec") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseGemSpecEntries(fixture.Name(), fixture) + if err != nil { + t.Fatalf("failed to parse gemspec: %+v", err) + } + + if len(actual) != 1 { + for _, a := range actual { + t.Log(" ", a) + } + t.Fatalf("unexpected package count: %d!=1", len(actual)) + } + + for _, d := range deep.Equal(actual[0], &expectedPkg) { + t.Errorf("diff: %+v", d) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/test-fixtures/Gemfile.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/test-fixtures/Gemfile.lock new file mode 100644 index 0000000000000000000000000000000000000000..b5aa45cbc106e6868ea10bb073c03fe4961cc82e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/test-fixtures/Gemfile.lock @@ -0,0 +1,149 @@ +GEM + remote: https://rubygems.org/ + specs: + actionmailer (4.1.1) + actionpack (= 4.1.1) + actionview (= 4.1.1) + mail (~> 2.5.4) + actionpack (4.1.1) + actionview (= 4.1.1) + activesupport (= 4.1.1) + rack (~> 1.5.2) + rack-test (~> 0.6.2) + actionview (4.1.1) + activesupport (= 4.1.1) + builder (~> 3.1) + erubis (~> 2.7.0) + activemodel (4.1.1) + activesupport (= 4.1.1) + builder (~> 3.1) + activerecord (4.1.1) + activemodel (= 4.1.1) + activesupport (= 4.1.1) + arel (~> 5.0.0) + activesupport (4.1.1) + i18n (~> 0.6, >= 0.6.9) + json (~> 1.7, >= 1.7.7) + minitest (~> 5.1) + thread_safe (~> 0.1) + tzinfo (~> 1.1) + arel (5.0.1.20140414130214) + bootstrap-sass (3.1.1.1) + sass (~> 3.2) + builder (3.2.2) + coffee-rails (4.0.1) + coffee-script (>= 2.2.0) + railties (>= 4.0.0, < 5.0) + coffee-script (2.2.0) + coffee-script-source + execjs + coffee-script-source (1.7.0) + erubis (2.7.0) + execjs (2.0.2) + hike (1.2.3) + i18n (0.6.9) + jbuilder (2.0.7) + activesupport (>= 3.0.0, < 5) + multi_json (~> 1.2) + jquery-rails (3.1.0) + railties (>= 3.0, < 5.0) + thor (>= 0.14, < 2.0) + json (1.8.1) + kgio (2.9.2) + libv8 (3.16.14.3) + mail (2.5.4) + mime-types (~> 1.16) + treetop (~> 1.4.8) + mime-types (1.25.1) + minitest (5.3.4) + multi_json (1.10.1) + mysql2 (0.3.16) + polyglot (0.3.4) + rack (1.5.2) + rack-test (0.6.2) + rack (>= 1.0) + rails (4.1.1) + actionmailer (= 4.1.1) + actionpack (= 4.1.1) + actionview (= 4.1.1) + activemodel (= 4.1.1) + activerecord (= 4.1.1) + activesupport (= 4.1.1) + bundler (>= 1.3.0, < 2.0) + railties (= 4.1.1) + sprockets-rails (~> 2.0) + railties (4.1.1) + actionpack (= 4.1.1) + activesupport (= 4.1.1) + rake (>= 0.8.7) + thor (>= 0.18.1, < 2.0) + raindrops (0.13.0) + rake (10.3.2) + rdoc (4.1.1) + json (~> 1.4) + ref (1.0.5) + sass (3.2.19) + sass-rails (4.0.3) + railties (>= 4.0.0, < 5.0) + sass (~> 3.2.0) + sprockets (~> 2.8, <= 2.11.0) + sprockets-rails (~> 2.0) + sdoc (0.4.0) + json (~> 1.8) + rdoc (~> 4.0, < 5.0) + spring (1.1.3) + sprockets (2.11.0) + hike (~> 1.2) + multi_json (~> 1.0) + rack (~> 1.0) + tilt (~> 1.1, != 1.3.0) + sprockets-rails (2.1.3) + actionpack (>= 3.0) + activesupport (>= 3.0) + sprockets (~> 2.8) + sqlite3 (1.3.9) + therubyracer (0.12.1) + libv8 (~> 3.16.14.0) + ref + thor (0.19.1) + thread_safe (0.3.3) + tilt (1.4.1) + treetop (1.4.15) + polyglot + polyglot (>= 0.3.1) + turbolinks (2.2.2) + coffee-rails + tzinfo (1.2.0) + thread_safe (~> 0.1) + uglifier (2.5.0) + execjs (>= 0.3.0) + json (>= 1.8.0) + unicorn (4.8.3) + kgio (~> 2.6) + rack + raindrops (~> 0.7) + +BAD-SECTION + bad-entry (5.5.5) + bad-kgio (~> 2.6) + bad-rack + bad-raindrops (~> 0.7) + +PLATFORMS + ruby + +DEPENDENCIES + bootstrap-sass + coffee-rails (~> 4.0.0) + jbuilder (~> 2.0) + jquery-rails + mysql2 (~> 0.3.16) + rails (= 4.1.1) + sass-rails (~> 4.0.3) + sdoc (~> 0.4.0) + spring + sqlite3 + therubyracer + turbolinks + uglifier (>= 1.3.0) + unicorn \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/test-fixtures/bundler.gemspec b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/test-fixtures/bundler.gemspec new file mode 100644 index 0000000000000000000000000000000000000000..a877840b3ae4352be1c59fd9c1d6687c8441fade --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/ruby/test-fixtures/bundler.gemspec @@ -0,0 +1,26 @@ +# frozen_string_literal: true +# -*- encoding: utf-8 -*- +# stub: bundler 2.1.4 ruby lib + +Gem::Specification.new do |s| + s.name = "bundler".freeze + s.version = "2.1.4" + + s.required_rubygems_version = Gem::Requirement.new(">= 2.5.2".freeze) if s.respond_to? :required_rubygems_version= + s.metadata = { "bug_tracker_uri" => "https://github.com/bundler/bundler/issues", "changelog_uri" => "https://github.com/bundler/bundler/blob/master/CHANGELOG.md", "homepage_uri" => "https://bundler.io/", "source_code_uri" => "https://github.com/bundler/bundler/" } if s.respond_to? :metadata= + s.require_paths = ["lib".freeze] + s.authors = ["Andr\u00E9 Arko".freeze, "Samuel Giddins".freeze, "Colby Swandale".freeze, "Hiroshi Shibata".freeze, "David Rodr\u00EDguez".freeze, "Grey Baker".freeze, "Stephanie Morillo".freeze, "Chris Morris".freeze, "James Wen".freeze, "Tim Moore".freeze, "Andr\u00E9 Medeiros".freeze, "Jessica Lynn Suttles".freeze, "Terence Lee".freeze, "Carl Lerche".freeze, "Yehuda Katz".freeze] + s.bindir = "exe".freeze + s.date = "2020-01-05" + s.description = "Bundler manages an application's dependencies through its entire life, across many machines, systematically and repeatably".freeze + s.email = ["team@bundler.io".freeze] + s.executables = ["bundle".freeze, "bundler".freeze] + s.files = ["exe/bundle".freeze, "exe/bundler".freeze] + s.homepage = "https://bundler.io".freeze + s.licenses = ["MIT".freeze] + s.required_ruby_version = Gem::Requirement.new(">= 2.3.0".freeze) + s.rubygems_version = "3.1.2".freeze + s.summary = "The best way to manage your application's dependencies".freeze + + s.installed_by_version = "3.1.2" if s.respond_to? :installed_by_version +end \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/audit_binary_cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/audit_binary_cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..eeab99cf1d28eb37bffbfaae38e13bc6845b5f4f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/audit_binary_cataloger.go @@ -0,0 +1,126 @@ +package rust + +import ( + "fmt" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/internal/unionreader" + "github.com/anchore/syft/syft/source" + rustaudit "github.com/microsoft/go-rustaudit" +) + +const catalogerName = "cargo-auditable-binary-cataloger" + +type Cataloger struct{} + +// NewRustAuditBinaryCataloger returns a new Rust auditable binary cataloger object that can detect dependencies +// in binaries produced with https://github.com/Shnatsel/rust-audit +func NewRustAuditBinaryCataloger() *Cataloger { + return &Cataloger{} +} + +// Name returns a string that uniquely describes a cataloger +func (c *Cataloger) Name() string { + return catalogerName +} + +// Catalog identifies executables then attempts to read Rust dependency information from them +func (c *Cataloger) Catalog(resolver source.FileResolver) ([]pkg.Package, []artifact.Relationship, error) { + var pkgs []pkg.Package + + fileMatches, err := resolver.FilesByMIMEType(internal.ExecutableMIMETypeSet.List()...) + if err != nil { + return pkgs, nil, fmt.Errorf("failed to find bin by mime types: %w", err) + } + + for _, location := range fileMatches { + readerCloser, err := resolver.FileContentsByLocation(location) + if err != nil { + log.Warnf("rust cataloger: opening file: %v", err) + continue + } + + reader, err := unionreader.GetUnionReader(readerCloser) + if err != nil { + return nil, nil, err + } + + versionInfos := scanFile(reader, location.RealPath) + internal.CloseAndLogError(readerCloser, location.RealPath) + + for _, versionInfo := range versionInfos { + pkgs = append(pkgs, buildRustPkgInfo(location, versionInfo)...) + } + } + + return pkgs, nil, nil +} + +// scanFile scans file to try to report the Rust crate dependencies +func scanFile(reader unionreader.UnionReader, filename string) []rustaudit.VersionInfo { + // NOTE: multiple readers are returned to cover universal binaries, which are files + // with more than one binary + readers, err := unionreader.GetReaders(reader) + if err != nil { + log.Warnf("rust cataloger: failed to open a binary: %v", err) + return nil + } + + var versionInfos []rustaudit.VersionInfo + for _, r := range readers { + versionInfo, err := rustaudit.GetDependencyInfo(r) + + if err != nil { + if err == rustaudit.ErrNoRustDepInfo { + // since the cataloger can only select executables and not distinguish if they are a Rust-compiled + // binary, we should not show warnings/logs in this case. + return nil + } + // Use an Info level log here like golang/scan_bin.go + log.Infof("rust cataloger: unable to read dependency information (file=%q): %v", filename, err) + return nil + } + + versionInfos = append(versionInfos, versionInfo) + } + + return versionInfos +} + +func buildRustPkgInfo(location source.Location, versionInfo rustaudit.VersionInfo) []pkg.Package { + var pkgs []pkg.Package + + for _, dep := range versionInfo.Packages { + dep := dep + p := newRustPackage(&dep, location) + if pkg.IsValid(&p) && dep.Kind == rustaudit.Runtime { + pkgs = append(pkgs, p) + } + } + + return pkgs +} + +func newRustPackage(dep *rustaudit.Package, location source.Location) pkg.Package { + p := pkg.Package{ + FoundBy: catalogerName, + Name: dep.Name, + Version: dep.Version, + Language: pkg.Rust, + Type: pkg.RustPkg, + Locations: source.NewLocationSet(location), + MetadataType: pkg.RustCargoPackageMetadataType, + Metadata: pkg.CargoPackageMetadata{ + Name: dep.Name, + Version: dep.Version, + Source: dep.Source, + }, + } + + p.SetID() + + return p +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..98785322bfb4f7d39f4a3fdaf4e0c7639d90226a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/cataloger.go @@ -0,0 +1,17 @@ +/* +Package rust provides a concrete Cataloger implementation for Cargo.lock files. +*/ +package rust + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewCargoLockCataloger returns a new Rust Cargo lock file cataloger object. +func NewCargoLockCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/Cargo.lock": parseCargoLock, + } + + return common.NewGenericCataloger(nil, globParsers, "rust-cargo-lock-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/parse_cargo_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/parse_cargo_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..8910a70dd1a0ad0324459677c363dddbc037067c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/parse_cargo_lock.go @@ -0,0 +1,30 @@ +package rust + +import ( + "fmt" + "io" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "github.com/pelletier/go-toml" +) + +// integrity check +var _ common.ParserFn = parseCargoLock + +// parseCargoLock is a parser function for Cargo.lock contents, returning all rust cargo crates discovered. +func parseCargoLock(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + tree, err := toml.LoadReader(reader) + if err != nil { + return nil, nil, fmt.Errorf("unable to load Cargo.lock for parsing: %v", err) + } + + metadata := pkg.CargoMetadata{} + err = tree.Unmarshal(&metadata) + if err != nil { + return nil, nil, fmt.Errorf("unable to parse Cargo.lock: %v", err) + } + + return metadata.Pkgs(), nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/parse_cargo_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/parse_cargo_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4bf2cd3e2274659d5ef788ce2683ebecd64d75b5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/parse_cargo_lock_test.go @@ -0,0 +1,190 @@ +package rust + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParseCargoLock(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "ansi_term", + Version: "0.12.1", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "ansi_term", + Version: "0.12.1", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "d52a9bb7ec0cf484c551830a7ce27bd20d67eac647e1befb56b0be4ee39a55d2", + Dependencies: []string{ + "winapi", + }, + }, + }, + { + Name: "matches", + Version: "0.1.8", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "matches", + Version: "0.1.8", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "7ffc5c5338469d4d3ea17d269fa8ea3512ad247247c30bd2df69e68309ed0a08", + Dependencies: []string{}, + }, + }, + { + Name: "memchr", + Version: "2.3.3", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "memchr", + Version: "2.3.3", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "3728d817d99e5ac407411fa471ff9800a778d88a24685968b36824eaf4bee400", + Dependencies: []string{}, + }, + }, + { + Name: "natord", + Version: "1.0.9", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "natord", + Version: "1.0.9", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "308d96db8debc727c3fd9744aac51751243420e46edf401010908da7f8d5e57c", + Dependencies: []string{}, + }, + }, + { + Name: "nom", + Version: "4.2.3", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "nom", + Version: "4.2.3", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "2ad2a91a8e869eeb30b9cb3119ae87773a8f4ae617f41b1eb9c154b2905f7bd6", + Dependencies: []string{ + "memchr", + "version_check", + }, + }, + }, + { + Name: "unicode-bidi", + Version: "0.3.4", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "unicode-bidi", + Version: "0.3.4", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "49f2bd0c6468a8230e1db229cff8029217cf623c767ea5d60bfbd42729ea54d5", + Dependencies: []string{ + "matches", + }, + }, + }, + { + Name: "version_check", + Version: "0.1.5", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "version_check", + Version: "0.1.5", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "914b1a6776c4c929a602fafd8bc742e06365d4bcbe48c30f9cca5824f70dc9dd", + Dependencies: []string{}, + }, + }, + { + Name: "winapi", + Version: "0.3.9", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "winapi", + Version: "0.3.9", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419", + Dependencies: []string{ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", + }, + }, + }, + { + Name: "winapi-i686-pc-windows-gnu", + Version: "0.4.0", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "winapi-i686-pc-windows-gnu", + Version: "0.4.0", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6", + Dependencies: []string{}, + }, + }, + { + Name: "winapi-x86_64-pc-windows-gnu", + Version: "0.4.0", + Language: pkg.Rust, + Type: pkg.RustPkg, + MetadataType: pkg.RustCargoPackageMetadataType, + Licenses: nil, + Metadata: pkg.CargoPackageMetadata{ + Name: "winapi-x86_64-pc-windows-gnu", + Version: "0.4.0", + Source: "registry+https://github.com/rust-lang/crates.io-index", + Checksum: "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f", + Dependencies: []string{}, + }, + }, + } + + fixture, err := os.Open("test-fixtures/Cargo.lock") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parseCargoLock(fixture.Name(), fixture) + if err != nil { + t.Error(err) + } + + differences := deep.Equal(expected, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/test-fixtures/Cargo.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/test-fixtures/Cargo.lock new file mode 100644 index 0000000000000000000000000000000000000000..5ee8fb7386fd4801e05d57ec7e2021721a8250c5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/rust/test-fixtures/Cargo.lock @@ -0,0 +1,76 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +[[package]] +name = "ansi_term" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d52a9bb7ec0cf484c551830a7ce27bd20d67eac647e1befb56b0be4ee39a55d2" +dependencies = [ + "winapi", +] + +[[package]] +name = "matches" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7ffc5c5338469d4d3ea17d269fa8ea3512ad247247c30bd2df69e68309ed0a08" + +[[package]] +name = "memchr" +version = "2.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3728d817d99e5ac407411fa471ff9800a778d88a24685968b36824eaf4bee400" + +[[package]] +name = "natord" +version = "1.0.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "308d96db8debc727c3fd9744aac51751243420e46edf401010908da7f8d5e57c" + +[[package]] +name = "nom" +version = "4.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2ad2a91a8e869eeb30b9cb3119ae87773a8f4ae617f41b1eb9c154b2905f7bd6" +dependencies = [ + "memchr", + "version_check", +] + +[[package]] +name = "unicode-bidi" +version = "0.3.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49f2bd0c6468a8230e1db229cff8029217cf623c767ea5d60bfbd42729ea54d5" +dependencies = [ + "matches", +] + +[[package]] +name = "version_check" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "914b1a6776c4c929a602fafd8bc742e06365d4bcbe48c30f9cca5824f70dc9dd" + +[[package]] +name = "winapi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" +dependencies = [ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", +] + +[[package]] +name = "winapi-i686-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" + +[[package]] +name = "winapi-x86_64-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" + diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/search_config.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/search_config.go new file mode 100644 index 0000000000000000000000000000000000000000..f92dc9928a94bd69d0977e38bbb4a84610a87b01 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/search_config.go @@ -0,0 +1,17 @@ +package cataloger + +import "github.com/anchore/syft/syft/source" + +type SearchConfig struct { + IncludeIndexedArchives bool + IncludeUnindexedArchives bool + Scope source.Scope +} + +func DefaultSearchConfig() SearchConfig { + return SearchConfig{ + IncludeIndexedArchives: true, + IncludeUnindexedArchives: false, + Scope: source.SquashedScope, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/cataloger.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/cataloger.go new file mode 100644 index 0000000000000000000000000000000000000000..d0c073408a41d056e234b2015767b898eb114367 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/cataloger.go @@ -0,0 +1,17 @@ +/* +Package swift provides a concrete Cataloger implementation for Podfile.lock files. +*/ +package swift + +import ( + "github.com/anchore/syft/syft/pkg/cataloger/common" +) + +// NewCocoapodsCataloger returns a new Swift Cocoapods lock file cataloger object. +func NewCocoapodsCataloger() *common.GenericCataloger { + globParsers := map[string]common.ParserFn{ + "**/Podfile.lock": parsePodfileLock, + } + + return common.NewGenericCataloger(nil, globParsers, "cocoapods-cataloger") +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/parse_podfile_lock.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/parse_podfile_lock.go new file mode 100644 index 0000000000000000000000000000000000000000..31819bef14e85f8be6fdf805bd587fd06126b471 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/parse_podfile_lock.go @@ -0,0 +1,76 @@ +package swift + +import ( + "fmt" + "io" + "io/ioutil" + "strings" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/pkg/cataloger/common" + "gopkg.in/yaml.v3" +) + +// integrity check +var _ common.ParserFn = parsePodfileLock + +// parsePodfileLock is a parser function for Podfile.lock contents, returning all cocoapods pods discovered. +func parsePodfileLock(_ string, reader io.Reader) ([]*pkg.Package, []artifact.Relationship, error) { + bytes, err := ioutil.ReadAll(reader) + if err != nil { + return nil, nil, fmt.Errorf("unable to read file: %w", err) + } + var podfile map[string]interface{} + if err = yaml.Unmarshal(bytes, &podfile); err != nil { + return nil, nil, fmt.Errorf("unable to parse yaml: %w", err) + } + + c, exists := podfile["SPEC CHECKSUMS"] + if !exists { + return nil, nil, fmt.Errorf("malformed podfile.lock: missing checksums") + } + checksums := c.(map[string]interface{}) + p, exists := podfile["PODS"] + if !exists { + return nil, nil, fmt.Errorf("malformed podfile.lock: missing checksums") + } + pods := p.([]interface{}) + + pkgs := []*pkg.Package{} + for _, podInterface := range pods { + var podBlob string + switch v := podInterface.(type) { + case map[string]interface{}: + for k := range v { + podBlob = k + } + case string: + podBlob = v + default: + return nil, nil, fmt.Errorf("malformed podfile.lock") + } + splits := strings.Split(podBlob, " ") + podName := splits[0] + podVersion := strings.TrimSuffix(strings.TrimPrefix(splits[1], "("), ")") + podRootPkg := strings.Split(podName, "/")[0] + pkgHash, exists := checksums[podRootPkg] + if !exists { + return nil, nil, fmt.Errorf("malformed podfile.lock: incomplete checksums") + } + pkgs = append(pkgs, &pkg.Package{ + Name: podName, + Version: podVersion, + Type: pkg.CocoapodsPkg, + Language: pkg.Swift, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: podName, + Version: podVersion, + PkgHash: pkgHash.(string), + }, + }) + } + + return pkgs, nil, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/parse_podfile_lock_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/parse_podfile_lock_test.go new file mode 100644 index 0000000000000000000000000000000000000000..8592eb4f82c23820fa5f8cff0557d4679200af10 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/parse_podfile_lock_test.go @@ -0,0 +1,306 @@ +package swift + +import ( + "os" + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/go-test/deep" +) + +func TestParsePodfileLock(t *testing.T) { + expected := []*pkg.Package{ + { + Name: "GlossButtonNode", + Version: "3.1.2", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "GlossButtonNode", + Version: "3.1.2", + PkgHash: "4ea1197a744f2fb5fb875fe31caf17ded4762e8f", + }, + }, + { + Name: "PINCache", + Version: "3.0.3", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "PINCache", + Version: "3.0.3", + PkgHash: "7a8fc1a691173d21dbddbf86cd515de6efa55086", + }, + }, + { + Name: "PINCache/Arc-exception-safe", + Version: "3.0.3", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "PINCache/Arc-exception-safe", + Version: "3.0.3", + PkgHash: "7a8fc1a691173d21dbddbf86cd515de6efa55086", + }, + }, + { + Name: "PINCache/Core", + Version: "3.0.3", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "PINCache/Core", + Version: "3.0.3", + PkgHash: "7a8fc1a691173d21dbddbf86cd515de6efa55086", + }, + }, + { + Name: "PINOperation", + Version: "1.2.1", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "PINOperation", + Version: "1.2.1", + PkgHash: "00c935935f1e8cf0d1e2d6b542e75b88fc3e5e20", + }, + }, + { + Name: "PINRemoteImage/Core", + Version: "3.0.3", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "PINRemoteImage/Core", + Version: "3.0.3", + PkgHash: "f1295b29f8c5e640e25335a1b2bd9d805171bd01", + }, + }, + { + Name: "PINRemoteImage/iOS", + Version: "3.0.3", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "PINRemoteImage/iOS", + Version: "3.0.3", + PkgHash: "f1295b29f8c5e640e25335a1b2bd9d805171bd01", + }, + }, + { + Name: "PINRemoteImage/PINCache", + Version: "3.0.3", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "PINRemoteImage/PINCache", + Version: "3.0.3", + PkgHash: "f1295b29f8c5e640e25335a1b2bd9d805171bd01", + }, + }, + { + Name: "Reveal-SDK", + Version: "33", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "Reveal-SDK", + Version: "33", + PkgHash: "effba1c940b8337195563c425a6b5862ec875caa", + }, + }, + { + Name: "SwiftGen", + Version: "6.5.1", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "SwiftGen", + Version: "6.5.1", + PkgHash: "a6d22010845f08fe18fbdf3a07a8e380fd22e0ea", + }, + }, + { + Name: "Texture", + Version: "3.1.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "Texture", + Version: "3.1.0", + PkgHash: "2e8ab2519452515f7f5a520f5a8f7e0a413abfa3", + }, + }, + { + Name: "Texture/AssetsLibrary", + Version: "3.1.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "Texture/AssetsLibrary", + Version: "3.1.0", + PkgHash: "2e8ab2519452515f7f5a520f5a8f7e0a413abfa3", + }, + }, + { + Name: "Texture/Core", + Version: "3.1.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "Texture/Core", + Version: "3.1.0", + PkgHash: "2e8ab2519452515f7f5a520f5a8f7e0a413abfa3", + }, + }, + { + Name: "Texture/MapKit", + Version: "3.1.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "Texture/MapKit", + Version: "3.1.0", + PkgHash: "2e8ab2519452515f7f5a520f5a8f7e0a413abfa3", + }, + }, + { + Name: "Texture/Photos", + Version: "3.1.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "Texture/Photos", + Version: "3.1.0", + PkgHash: "2e8ab2519452515f7f5a520f5a8f7e0a413abfa3", + }, + }, + { + Name: "Texture/PINRemoteImage", + Version: "3.1.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "Texture/PINRemoteImage", + Version: "3.1.0", + PkgHash: "2e8ab2519452515f7f5a520f5a8f7e0a413abfa3", + }, + }, + { + Name: "Texture/Video", + Version: "3.1.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "Texture/Video", + Version: "3.1.0", + PkgHash: "2e8ab2519452515f7f5a520f5a8f7e0a413abfa3", + }, + }, + { + Name: "TextureSwiftSupport", + Version: "3.13.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "TextureSwiftSupport", + Version: "3.13.0", + PkgHash: "c515c7927fab92d0d9485f49b885b8c5de34fbfb", + }, + }, + { + Name: "TextureSwiftSupport/Components", + Version: "3.13.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "TextureSwiftSupport/Components", + Version: "3.13.0", + PkgHash: "c515c7927fab92d0d9485f49b885b8c5de34fbfb", + }, + }, + { + Name: "TextureSwiftSupport/Experiments", + Version: "3.13.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "TextureSwiftSupport/Experiments", + Version: "3.13.0", + PkgHash: "c515c7927fab92d0d9485f49b885b8c5de34fbfb", + }, + }, + { + Name: "TextureSwiftSupport/Extensions", + Version: "3.13.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "TextureSwiftSupport/Extensions", + Version: "3.13.0", + PkgHash: "c515c7927fab92d0d9485f49b885b8c5de34fbfb", + }, + }, + { + Name: "TextureSwiftSupport/LayoutSpecBuilders", + Version: "3.13.0", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "TextureSwiftSupport/LayoutSpecBuilders", + Version: "3.13.0", + PkgHash: "c515c7927fab92d0d9485f49b885b8c5de34fbfb", + }, + }, + { + Name: "TinyConstraints", + Version: "4.0.2", + Language: pkg.Swift, + Type: pkg.CocoapodsPkg, + MetadataType: pkg.CocoapodsMetadataType, + Metadata: pkg.CocoapodsMetadata{ + Name: "TinyConstraints", + Version: "4.0.2", + PkgHash: "7b7ccc0c485bb3bb47082138ff28bc33cd49897f", + }, + }, + } + + fixture, err := os.Open("test-fixtures/Podfile.lock") + if err != nil { + t.Fatalf("failed to open fixture: %+v", err) + } + + // TODO: no relationships are under test yet + actual, _, err := parsePodfileLock(fixture.Name(), fixture) + if err != nil { + t.Error(err) + } + + differences := deep.Equal(expected, actual) + if differences != nil { + t.Errorf("returned package list differed from expectation: %+v", differences) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/test-fixtures/Podfile.lock b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/test-fixtures/Podfile.lock new file mode 100644 index 0000000000000000000000000000000000000000..4d82d8ef2d125220bf715a00051d5ae8536b0465 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cataloger/swift/test-fixtures/Podfile.lock @@ -0,0 +1,92 @@ +PODS: + - GlossButtonNode (3.1.2): + - Texture/Core (~> 3) + - TextureSwiftSupport (>= 3.10.0) + - PINCache (3.0.3): + - PINCache/Arc-exception-safe (= 3.0.3) + - PINCache/Core (= 3.0.3) + - PINCache/Arc-exception-safe (3.0.3): + - PINCache/Core + - PINCache/Core (3.0.3): + - PINOperation (~> 1.2.1) + - PINOperation (1.2.1) + - PINRemoteImage/Core (3.0.3): + - PINOperation + - PINRemoteImage/iOS (3.0.3): + - PINRemoteImage/Core + - PINRemoteImage/PINCache (3.0.3): + - PINCache (~> 3.0.3) + - PINRemoteImage/Core + - Reveal-SDK (33) + - SwiftGen (6.5.1) + - Texture (3.1.0): + - Texture/AssetsLibrary (= 3.1.0) + - Texture/Core (= 3.1.0) + - Texture/MapKit (= 3.1.0) + - Texture/Photos (= 3.1.0) + - Texture/PINRemoteImage (= 3.1.0) + - Texture/Video (= 3.1.0) + - Texture/AssetsLibrary (3.1.0): + - Texture/Core + - Texture/Core (3.1.0) + - Texture/MapKit (3.1.0): + - Texture/Core + - Texture/Photos (3.1.0): + - Texture/Core + - Texture/PINRemoteImage (3.1.0): + - PINRemoteImage/iOS (~> 3.0.0) + - PINRemoteImage/PINCache + - Texture/Core + - Texture/Video (3.1.0): + - Texture/Core + - TextureSwiftSupport (3.13.0): + - Texture/Core (>= 3) + - TextureSwiftSupport/Components (= 3.13.0) + - TextureSwiftSupport/Experiments (= 3.13.0) + - TextureSwiftSupport/Extensions (= 3.13.0) + - TextureSwiftSupport/LayoutSpecBuilders (= 3.13.0) + - TextureSwiftSupport/Components (3.13.0): + - Texture/Core (>= 3) + - TextureSwiftSupport/LayoutSpecBuilders + - TextureSwiftSupport/Experiments (3.13.0): + - Texture/Core (>= 3) + - TextureSwiftSupport/Extensions (3.13.0): + - Texture/Core (>= 3) + - TextureSwiftSupport/LayoutSpecBuilders (3.13.0): + - Texture/Core (>= 3) + - TinyConstraints (4.0.2) + +DEPENDENCIES: + - GlossButtonNode + - Reveal-SDK + - SwiftGen + - Texture + - TextureSwiftSupport + - TinyConstraints + +SPEC REPOS: + trunk: + - GlossButtonNode + - PINCache + - PINOperation + - PINRemoteImage + - Reveal-SDK + - SwiftGen + - Texture + - TextureSwiftSupport + - TinyConstraints + +SPEC CHECKSUMS: + GlossButtonNode: 4ea1197a744f2fb5fb875fe31caf17ded4762e8f + PINCache: 7a8fc1a691173d21dbddbf86cd515de6efa55086 + PINOperation: 00c935935f1e8cf0d1e2d6b542e75b88fc3e5e20 + PINRemoteImage: f1295b29f8c5e640e25335a1b2bd9d805171bd01 + Reveal-SDK: effba1c940b8337195563c425a6b5862ec875caa + SwiftGen: a6d22010845f08fe18fbdf3a07a8e380fd22e0ea + Texture: 2e8ab2519452515f7f5a520f5a8f7e0a413abfa3 + TextureSwiftSupport: c515c7927fab92d0d9485f49b885b8c5de34fbfb + TinyConstraints: 7b7ccc0c485bb3bb47082138ff28bc33cd49897f + +PODFILE CHECKSUM: 07aa55f54421f6e6d3a920c11716a89fc9243d1b + +COCOAPODS: 1.11.2 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cocoapods_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cocoapods_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..bad5708f7ee9868769c4293d5f33932864de3e47 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cocoapods_metadata.go @@ -0,0 +1,27 @@ +package pkg + +import ( + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +var _ urlIdentifier = (*CocoapodsMetadata)(nil) + +type CocoapodsMetadata struct { + Name string `mapstructure:"name" json:"name"` + Version string `mapstructure:"version" json:"version"` + PkgHash string `mapstructure:"pkgHash" json:"pkgHash"` +} + +func (m CocoapodsMetadata) PackageURL(_ *linux.Release) string { + var qualifiers packageurl.Qualifiers + + return packageurl.NewPackageURL( + packageurl.TypeCocoapods, + "", + m.Name, + m.Version, + qualifiers, + "", + ).ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/conan_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/conan_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..9717e8f3d8f67f03b357610a7b4c615caba4b2fa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/conan_metadata.go @@ -0,0 +1,24 @@ +package pkg + +import ( + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +type ConanMetadata struct { + Name string `mapstructure:"name" json:"name"` + Version string `mapstructure:"version" json:"version"` +} + +func (m ConanMetadata) PackageURL(_ *linux.Release) string { + var qualifiers packageurl.Qualifiers + + return packageurl.NewPackageURL( + packageurl.TypeConan, + "", + m.Name, + m.Version, + qualifiers, + "", + ).ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe.go new file mode 100644 index 0000000000000000000000000000000000000000..1d6402726958a8caf932ebaf86f3ce5784471dc0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe.go @@ -0,0 +1,154 @@ +package pkg + +import ( + "fmt" + "regexp" + "strings" + + "github.com/facebookincubator/nvdtools/wfn" +) + +type CPE = wfn.Attributes + +const ( + allowedCPEPunctuation = "-!\"#$%&'()+,./:;<=>@[]^`{|}~" +) + +// This regex string is taken from +// https://csrc.nist.gov/schema/cpe/2.3/cpe-naming_2.3.xsd which has the official cpe spec +// This first part matches CPE urls and the second part matches binding strings +const cpeRegexString = ((`^([c][pP][eE]:/[AHOaho]?(:[A-Za-z0-9\._\-~%]*){0,6})`) + + // Or match the CPE binding string + // Note that we had to replace '`' with '\x60' to escape the backticks + `|(cpe:2\.3:[aho\*\-](:(((\?*|\*?)([a-zA-Z0-9\-\._]|(\\[\\\*\?!"#$$%&'\(\)\+,/:;<=>@\[\]\^\x60\{\|}~]))+(\?*|\*?))|[\*\-])){5}(:(([a-zA-Z]{2,3}(-([a-zA-Z]{2}|[0-9]{3}))?)|[\*\-]))(:(((\?*|\*?)([a-zA-Z0-9\-\._]|(\\[\\\*\?!"#$$%&'\(\)\+,/:;<=>@\[\]\^\x60\{\|}~]))+(\?*|\*?))|[\*\-])){4})$`) + +var cpeRegex = regexp.MustCompile(cpeRegexString) + +// NewCPE will parse a formatted CPE string and return a CPE object. Some input, such as the existence of whitespace +// characters is allowed, however, a more strict validation is done after this sanitization process. +func NewCPE(cpeStr string) (CPE, error) { + // get a CPE object based on the given string --don't validate yet since it may be possible to escape select cases on the callers behalf + c, err := newCPEWithoutValidation(cpeStr) + if err != nil { + return CPE{}, fmt.Errorf("unable to parse CPE string: %w", err) + } + + // ensure that this CPE can be validated after being fully sanitized + if ValidateCPEString(CPEString(c)) != nil { + return CPE{}, err + } + + // we don't return the sanitized string, as this is a concern for later when creating CPE strings. In fact, since + // sanitization is lossy (whitespace is replaced, not escaped) it's important that the raw values are left as. + return c, nil +} + +func ValidateCPEString(cpeStr string) error { + // We should filter out all CPEs that do not match the official CPE regex + // The facebook nvdtools parser can sometimes incorrectly parse invalid CPE strings + if !cpeRegex.MatchString(cpeStr) { + return fmt.Errorf("failed to parse CPE=%q as it doesn't match the regex=%s", cpeStr, cpeRegexString) + } + return nil +} + +func newCPEWithoutValidation(cpeStr string) (CPE, error) { + value, err := wfn.Parse(cpeStr) + if err != nil { + return CPE{}, fmt.Errorf("failed to parse CPE=%q: %w", cpeStr, err) + } + + if value == nil { + return CPE{}, fmt.Errorf("failed to parse CPE=%q", cpeStr) + } + + // we need to compare the raw data since we are constructing CPEs in other locations + value.Vendor = normalizeCpeField(value.Vendor) + value.Product = normalizeCpeField(value.Product) + value.Language = normalizeCpeField(value.Language) + value.Version = normalizeCpeField(value.Version) + value.TargetSW = normalizeCpeField(value.TargetSW) + value.Part = normalizeCpeField(value.Part) + value.Edition = normalizeCpeField(value.Edition) + value.Other = normalizeCpeField(value.Other) + value.SWEdition = normalizeCpeField(value.SWEdition) + value.TargetHW = normalizeCpeField(value.TargetHW) + value.Update = normalizeCpeField(value.Update) + + return *value, nil +} + +func MustCPE(cpeStr string) CPE { + c, err := NewCPE(cpeStr) + if err != nil { + panic(err) + } + return c +} + +func normalizeCpeField(field string) string { + // replace spaces with underscores (per section 5.3.2 of the CPE spec v 2.3) + field = strings.ReplaceAll(field, " ", "_") + + // keep dashes and forward slashes unescaped + if field == "*" { + return wfn.Any + } + return stripSlashes(field) +} + +// stripSlashes is a reverse of the sanitize function below. +// It correctly removes slashes that are followed by allowed puncts. +// This is to allow for a correct round trip parsing of cpes with quoted characters. +func stripSlashes(s string) string { + sb := strings.Builder{} + for i, c := range s { + if c == '\\' && i+1 < len(s) && strings.ContainsRune(allowedCPEPunctuation, rune(s[i+1])) { + continue + } else { + sb.WriteRune(c) + } + } + return sb.String() +} + +func CPEString(c CPE) string { + output := CPE{} + output.Vendor = sanitize(c.Vendor) + output.Product = sanitize(c.Product) + output.Language = sanitize(c.Language) + output.Version = sanitize(c.Version) + output.TargetSW = sanitize(c.TargetSW) + output.Part = sanitize(c.Part) + output.Edition = sanitize(c.Edition) + output.Other = sanitize(c.Other) + output.SWEdition = sanitize(c.SWEdition) + output.TargetHW = sanitize(c.TargetHW) + output.Update = sanitize(c.Update) + return output.BindToFmtString() +} + +// sanitize is a modified version of WFNize function from nvdtools +// that quotes all the allowed punctation chars with a slash and replaces +// spaces with underscores. It differs from the upstream implmentation as +// it does not use the buggy nvdtools implementation, specifically the "addSlashesAt" part of the +// function which stops the loop as soon as it encounters ":" a valid +// character for a WFN attribute after quoting, but the way nvdtools +// handles it causes it to truncate strings that container ":". As a result +// strings like "prefix:1.2" which would have been quoted as "prefix\:1.2" +// end up becoming "prefix" instead causing loss of information and +// incorrect CPEs being generated. +func sanitize(s string) string { + // replace spaces with underscores + in := strings.ReplaceAll(s, " ", "_") + + // escape allowable punctuation per section 5.3.2 in the CPE 2.3 spec + sb := strings.Builder{} + for _, c := range in { + if strings.ContainsRune(allowedCPEPunctuation, c) { + sb.WriteRune('\\') + } + sb.WriteRune(c) + } + return sb.String() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_by_specificity.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_by_specificity.go new file mode 100644 index 0000000000000000000000000000000000000000..73cce8d04c11acccf98c109ea6d2b76a3085315a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_by_specificity.go @@ -0,0 +1,60 @@ +package pkg + +import ( + "sort" + + "github.com/facebookincubator/nvdtools/wfn" +) + +var _ sort.Interface = (*CPEBySpecificity)(nil) + +type CPEBySpecificity []wfn.Attributes + +func (c CPEBySpecificity) Len() int { return len(c) } + +func (c CPEBySpecificity) Swap(i, j int) { c[i], c[j] = c[j], c[i] } + +func (c CPEBySpecificity) Less(i, j int) bool { + iScore := weightedCountForSpecifiedFields(c[i]) + jScore := weightedCountForSpecifiedFields(c[j]) + + // check weighted sort first + if iScore != jScore { + return iScore > jScore + } + + // sort longer fields to top + if countFieldLength(c[i]) != countFieldLength(c[j]) { + return countFieldLength(c[i]) > countFieldLength(c[j]) + } + + // if score and length are equal then text sort + // note that we are not using CPEString from the syft pkg + // as we are not encoding/decoding this CPE string so we don't + // need the proper quoted version of the CPE. + return c[i].BindToFmtString() < c[j].BindToFmtString() +} + +func countFieldLength(cpe wfn.Attributes) int { + return len(cpe.Part + cpe.Vendor + cpe.Product + cpe.Version + cpe.TargetSW) +} + +func weightedCountForSpecifiedFields(cpe wfn.Attributes) int { + checksForSpecifiedField := []func(cpe wfn.Attributes) (bool, int){ + func(cpe wfn.Attributes) (bool, int) { return cpe.Part != "", 2 }, + func(cpe wfn.Attributes) (bool, int) { return cpe.Vendor != "", 3 }, + func(cpe wfn.Attributes) (bool, int) { return cpe.Product != "", 4 }, + func(cpe wfn.Attributes) (bool, int) { return cpe.Version != "", 1 }, + func(cpe wfn.Attributes) (bool, int) { return cpe.TargetSW != "", 1 }, + } + + weightedCount := 0 + for _, fieldIsSpecified := range checksForSpecifiedField { + isSpecified, weight := fieldIsSpecified(cpe) + if isSpecified { + weightedCount += weight + } + } + + return weightedCount +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_by_specificity_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_by_specificity_test.go new file mode 100644 index 0000000000000000000000000000000000000000..54f8e9f13087d9f56833c894da5696e3800d0e37 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_by_specificity_test.go @@ -0,0 +1,103 @@ +package pkg + +import ( + "sort" + "testing" + + "github.com/stretchr/testify/assert" +) + +func mustCPE(c string) CPE { + return must(NewCPE(c)) +} + +func TestCPESpecificity(t *testing.T) { + tests := []struct { + name string + input []CPE + expected []CPE + }{ + { + name: "sort strictly by wfn *", + input: []CPE{ + mustCPE("cpe:2.3:a:*:package:1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:some:package:1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:*:package:1:*:*:*:*:some:*:*"), + mustCPE("cpe:2.3:a:some:package:1:*:*:*:*:some:*:*"), + mustCPE("cpe:2.3:a:some:package:*:*:*:*:*:*:*:*"), + }, + expected: []CPE{ + mustCPE("cpe:2.3:a:some:package:1:*:*:*:*:some:*:*"), + mustCPE("cpe:2.3:a:some:package:1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:some:package:*:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:*:package:1:*:*:*:*:some:*:*"), + mustCPE("cpe:2.3:a:*:package:1:*:*:*:*:*:*:*"), + }, + }, + { + name: "sort strictly by field length", + input: []CPE{ + mustCPE("cpe:2.3:a:1:22:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:55555:1:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:1:333:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:666666:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:1:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:1:1:*:*:*:*:4444:*:*"), + }, + expected: []CPE{ + mustCPE("cpe:2.3:a:1:666666:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:55555:1:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:1:1:*:*:*:*:4444:*:*"), + mustCPE("cpe:2.3:a:1:1:333:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:22:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:1:1:*:*:*:*:1:*:*"), + }, + }, + { + name: "sort by mix of field length and specificity", + input: []CPE{ + mustCPE("cpe:2.3:a:1:666666:*:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:*:1:1:*:*:*:*:4444:*:*"), + mustCPE("cpe:2.3:a:1:*:333:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:1:1:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:22:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:55555:1:1:*:*:*:*:1:*:*"), + }, + expected: []CPE{ + mustCPE("cpe:2.3:a:55555:1:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:22:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:1:1:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:1:666666:*:*:*:*:*:1:*:*"), + mustCPE("cpe:2.3:a:*:1:1:*:*:*:*:4444:*:*"), + mustCPE("cpe:2.3:a:1:*:333:*:*:*:*:*:*:*"), + }, + }, + { + name: "sort by mix of field length, specificity, dash", + input: []CPE{ + mustCPE("cpe:2.3:a:alpine:alpine_keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine_keys:alpine_keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine-keys:alpine_keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine:alpine-keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine-keys:alpine-keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine_keys:alpine-keys:2.3-r1:*:*:*:*:*:*:*"), + }, + expected: []CPE{ + mustCPE("cpe:2.3:a:alpine-keys:alpine-keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine-keys:alpine_keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine_keys:alpine-keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine_keys:alpine_keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine:alpine-keys:2.3-r1:*:*:*:*:*:*:*"), + mustCPE("cpe:2.3:a:alpine:alpine_keys:2.3-r1:*:*:*:*:*:*:*"), + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + sort.Sort(CPEBySpecificity(test.input)) + assert.Equal(t, test.expected, test.input) + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_test.go new file mode 100644 index 0000000000000000000000000000000000000000..1f610541c47742cc7fe046848292dd7a59a9eec8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/cpe_test.go @@ -0,0 +1,234 @@ +package pkg + +import ( + "encoding/json" + "fmt" + "io/ioutil" + "strings" + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func must(c CPE, e error) CPE { + if e != nil { + panic(e) + } + return c +} + +func TestNewCPE(t *testing.T) { + tests := []struct { + name string + input string + expected CPE + }{ + { + name: "gocase", + input: `cpe:/a:10web:form_maker:1.0.0::~~~wordpress~~`, + expected: must(NewCPE(`cpe:2.3:a:10web:form_maker:1.0.0:*:*:*:*:wordpress:*:*`)), + }, + { + name: "dashes", + input: `cpe:/a:7-zip:7-zip:4.56:beta:~~~windows~~`, + expected: must(NewCPE(`cpe:2.3:a:7-zip:7-zip:4.56:beta:*:*:*:windows:*:*`)), + }, + { + name: "URL escape characters", + input: `cpe:/a:%240.99_kindle_books_project:%240.99_kindle_books:6::~~~android~~`, + expected: must(NewCPE(`cpe:2.3:a:\$0.99_kindle_books_project:\$0.99_kindle_books:6:*:*:*:*:android:*:*`)), + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual, err := NewCPE(test.input) + if err != nil { + t.Fatalf("got an error while creating CPE: %+v", err) + } + + if CPEString(actual) != CPEString(test.expected) { + t.Errorf("mismatched entries:\n\texpected:%+v\n\t actual:%+v\n", CPEString(test.expected), CPEString(actual)) + } + + }) + } +} + +func Test_normalizeCpeField(t *testing.T) { + + tests := []struct { + field string + expected string + }{ + { + field: "something", + expected: "something", + }, + { + field: "some\\thing", + expected: `some\thing`, + }, + { + field: "*", + expected: "", + }, + { + field: "", + expected: "", + }, + } + for _, test := range tests { + t.Run(test.field, func(t *testing.T) { + assert.Equal(t, test.expected, normalizeCpeField(test.field)) + }) + } +} + +func Test_CPEParser(t *testing.T) { + testCases := []struct { + CPEString string `json:"cpe-string"` + CPEUrl string `json:"cpe-url"` + WFN CPE `json:"wfn"` + }{} + out, err := ioutil.ReadFile("test-fixtures/cpe-data.json") + require.NoError(t, err) + require.NoError(t, json.Unmarshal(out, &testCases)) + + for _, test := range testCases { + t.Run(test.CPEString, func(t *testing.T) { + c1, err := NewCPE(test.CPEString) + assert.NoError(t, err) + c2, err := NewCPE(test.CPEUrl) + assert.NoError(t, err) + assert.Equal(t, c1, c2) + assert.Equal(t, c1, test.WFN) + assert.Equal(t, c2, test.WFN) + assert.Equal(t, CPEString(test.WFN), test.CPEString) + }) + } +} + +func Test_InvalidCPE(t *testing.T) { + type testcase struct { + name string + in string + expected string + expectedErr bool + } + + tests := []testcase{ + { + // 5.3.2: The underscore (x5f) MAY be used, and it SHOULD be used in place of whitespace characters (which SHALL NOT be used) + name: "translates spaces", + in: "cpe:2.3:a:some-vendor:name:1 2:*:*:*:*:*:*:*", + expected: "cpe:2.3:a:some-vendor:name:1_2:*:*:*:*:*:*:*", + }, + { + // it isn't easily possible in the string formatted string to detect improper escaping of : (it will fail parsing) + name: "unescaped ':' cannot be helped -- too many fields", + in: "cpe:2.3:a:some-vendor:name:::*:*:*:*:*:*:*", + expectedErr: true, + }, + { + name: "too few fields", + in: "cpe:2.3:a:some-vendor:name:*:*:*:*:*:*:*", + expected: "cpe:2.3:a:some-vendor:name:*:*:*:*:*:*:*:*", + }, + // Note: though the CPE spec does not allow for ? and * as escaped character input, these seem to be allowed in + // the NVD CPE validator for this reason these edge cases were removed + } + + // the wfn library does not account for escapes of . and - + exceptions := ".-" + // it isn't easily possible in the string formatted string to detect improper escaping of : (it will fail parsing) + skip := ":" + + // make escape exceptions for section 5.3.2 of the CPE spec (2.3) + for _, char := range allowedCPEPunctuation { + if strings.Contains(skip, string(char)) { + continue + } + + in := fmt.Sprintf("cpe:2.3:a:some-vendor:name:*:%s:*:*:*:*:*:*", string(char)) + exp := fmt.Sprintf(`cpe:2.3:a:some-vendor:name:*:\%s:*:*:*:*:*:*`, string(char)) + if strings.Contains(exceptions, string(char)) { + exp = in + } + + tests = append(tests, testcase{ + name: fmt.Sprintf("allowes future escape of character (%s)", string(char)), + in: in, + expected: exp, + expectedErr: false, + }) + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + c, err := NewCPE(test.in) + if test.expectedErr { + assert.Error(t, err) + if t.Failed() { + t.Logf("got CPE: %q details: %+v", CPEString(c), c) + } + return + } + require.NoError(t, err) + assert.Equal(t, test.expected, CPEString(c)) + }) + } +} + +func Test_RoundTrip(t *testing.T) { + tests := []struct { + name string + cpe string + parsedCPE CPE + }{ + { + name: "normal", + cpe: "cpe:2.3:a:some-vendor:name:3.2:*:*:*:*:*:*:*", + parsedCPE: CPE{ + Part: "a", + Vendor: "some-vendor", + Product: "name", + Version: "3.2", + }, + }, + { + name: "escaped colon", + cpe: "cpe:2.3:a:some-vendor:name:1\\:3.2:*:*:*:*:*:*:*", + parsedCPE: CPE{ + Part: "a", + Vendor: "some-vendor", + Product: "name", + Version: "1:3.2", + }, + }, + { + name: "escaped forward slash", + cpe: "cpe:2.3:a:test\\/some-vendor:name:3.2:*:*:*:*:*:*:*", + parsedCPE: CPE{ + Part: "a", + Vendor: "test/some-vendor", + Product: "name", + Version: "3.2", + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + // CPE string must be preserved through a round trip + assert.Equal(t, test.cpe, CPEString(MustCPE(test.cpe))) + // The parsed CPE must be the same after a round trip + assert.Equal(t, MustCPE(test.cpe), MustCPE(CPEString(MustCPE(test.cpe)))) + // The test case parsed CPE must be the same after parsing the input string + assert.Equal(t, test.parsedCPE, MustCPE(test.cpe)) + // The test case parsed CPE must produce the same string as the input cpe + assert.Equal(t, CPEString(test.parsedCPE), test.cpe) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/dart_pub_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/dart_pub_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..3c800877be27736a76ce21355e923bd122134873 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/dart_pub_metadata.go @@ -0,0 +1,38 @@ +package pkg + +import ( + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +type DartPubMetadata struct { + Name string `mapstructure:"name" json:"name"` + Version string `mapstructure:"version" json:"version"` + HostedURL string `mapstructure:"hosted_url" json:"hosted_url,omitempty"` + VcsURL string `mapstructure:"vcs_url" json:"vcs_url,omitempty"` +} + +func (m DartPubMetadata) PackageURL(_ *linux.Release) string { + var qualifiers packageurl.Qualifiers + + if m.HostedURL != "" { + qualifiers = append(qualifiers, packageurl.Qualifier{ + Key: "hosted_url", + Value: m.HostedURL, + }) + } else if m.VcsURL != "" { // Default to using Hosted if somehow both are provided + qualifiers = append(qualifiers, packageurl.Qualifier{ + Key: "vcs_url", + Value: m.VcsURL, + }) + } + + return packageurl.NewPackageURL( + packageurl.TypePub, + "", + m.Name, + m.Version, + qualifiers, + "", + ).ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/dotnet_deps_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/dotnet_deps_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..faac92839dadc658c414355cb5bfdeaa9bc09c00 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/dotnet_deps_metadata.go @@ -0,0 +1,27 @@ +package pkg + +import ( + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +type DotnetDepsMetadata struct { + Name string `mapstructure:"name" json:"name"` + Version string `mapstructure:"version" json:"version"` + Path string `mapstructure:"path" json:"path"` + Sha512 string `mapstructure:"sha512" json:"sha512"` + HashPath string `mapstructure:"hashPath" json:"hashPath"` +} + +func (m DotnetDepsMetadata) PackageURL(_ *linux.Release) string { + var qualifiers packageurl.Qualifiers + + return packageurl.NewPackageURL( + packageurl.TypeDotnet, + "", + m.Name, + m.Version, + qualifiers, + "", + ).ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/dpkg_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/dpkg_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..cc69a61732f01d40df8244f49f4162148b12b41d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/dpkg_metadata.go @@ -0,0 +1,86 @@ +package pkg + +import ( + "fmt" + "sort" + + "github.com/anchore/syft/syft/file" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" + "github.com/scylladb/go-set/strset" +) + +const DpkgDBGlob = "**/var/lib/dpkg/{status,status.d/**}" + +var ( + _ FileOwner = (*DpkgMetadata)(nil) + _ urlIdentifier = (*DpkgMetadata)(nil) +) + +// DpkgMetadata represents all captured data for a Debian package DB entry; available fields are described +// at http://manpages.ubuntu.com/manpages/xenial/man1/dpkg-query.1.html in the --showformat section. +type DpkgMetadata struct { + Package string `mapstructure:"Package" json:"package"` + Source string `mapstructure:"Source" json:"source" cyclonedx:"source"` + Version string `mapstructure:"Version" json:"version"` + SourceVersion string `mapstructure:"SourceVersion" json:"sourceVersion" cyclonedx:"sourceVersion"` + Architecture string `mapstructure:"Architecture" json:"architecture"` + Maintainer string `mapstructure:"Maintainer" json:"maintainer"` + InstalledSize int `mapstructure:"InstalledSize" json:"installedSize" cyclonedx:"installedSize"` + Description string `mapstructure:"Description" hash:"ignore" json:"-"` + Files []DpkgFileRecord `json:"files"` +} + +// DpkgFileRecord represents a single file attributed to a debian package. +type DpkgFileRecord struct { + Path string `json:"path"` + Digest *file.Digest `json:"digest,omitempty"` + IsConfigFile bool `json:"isConfigFile"` +} + +// PackageURL returns the PURL for the specific Debian package (see https://github.com/package-url/purl-spec) +func (m DpkgMetadata) PackageURL(distro *linux.Release) string { + var namespace string + if distro != nil { + namespace = distro.ID + } + + qualifiers := map[string]string{ + PURLQualifierArch: m.Architecture, + } + + if m.Source != "" { + if m.SourceVersion != "" { + qualifiers[PURLQualifierUpstream] = fmt.Sprintf("%s@%s", m.Source, m.SourceVersion) + } else { + qualifiers[PURLQualifierUpstream] = m.Source + } + } + + return packageurl.NewPackageURL( + // TODO: replace with `packageurl.TypeDebian` upon merge of https://github.com/package-url/packageurl-go/pull/21 + // TODO: or, since we're now using an Anchore fork of this module, we could do this sooner. + "deb", + namespace, + m.Package, + m.Version, + purlQualifiers( + qualifiers, + distro, + ), + "", + ).ToString() +} + +func (m DpkgMetadata) OwnedFiles() (result []string) { + s := strset.New() + for _, f := range m.Files { + if f.Path != "" { + s.Add(f.Path) + } + } + result = s.List() + sort.Strings(result) + return +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/dpkg_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/dpkg_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..145baf3087b398dba1e61e29fdffec6058d38cd6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/dpkg_metadata_test.go @@ -0,0 +1,132 @@ +package pkg + +import ( + "strings" + "testing" + + "github.com/go-test/deep" + + "github.com/anchore/syft/syft/linux" + "github.com/sergi/go-diff/diffmatchpatch" +) + +func TestDpkgMetadata_pURL(t *testing.T) { + tests := []struct { + name string + distro *linux.Release + metadata DpkgMetadata + expected string + }{ + { + name: "go case", + distro: &linux.Release{ + ID: "debian", + VersionID: "11", + }, + metadata: DpkgMetadata{ + Package: "p", + Version: "v", + }, + expected: "pkg:deb/debian/p@v?distro=debian-11", + }, + { + name: "with arch info", + distro: &linux.Release{ + ID: "ubuntu", + VersionID: "16.04", + }, + metadata: DpkgMetadata{ + Package: "p", + Version: "v", + Architecture: "a", + }, + expected: "pkg:deb/ubuntu/p@v?arch=a&distro=ubuntu-16.04", + }, + { + name: "missing distro", + metadata: DpkgMetadata{ + Package: "p", + Version: "v", + }, + expected: "pkg:deb/p@v", + }, + { + name: "with upstream qualifier with source pkg name info", + distro: &linux.Release{ + ID: "debian", + VersionID: "11", + }, + metadata: DpkgMetadata{ + Package: "p", + Source: "s", + Version: "v", + }, + expected: "pkg:deb/debian/p@v?upstream=s&distro=debian-11", + }, + { + name: "with upstream qualifier with source pkg name and version info", + distro: &linux.Release{ + ID: "debian", + VersionID: "11", + }, + metadata: DpkgMetadata{ + Package: "p", + Source: "s", + Version: "v", + SourceVersion: "2.3", + }, + expected: "pkg:deb/debian/p@v?upstream=s%402.3&distro=debian-11", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := test.metadata.PackageURL(test.distro) + if actual != test.expected { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.expected, actual, true) + t.Errorf("diff: %s", dmp.DiffPrettyText(diffs)) + } + }) + } +} + +func TestDpkgMetadata_FileOwner(t *testing.T) { + tests := []struct { + metadata DpkgMetadata + expected []string + }{ + { + metadata: DpkgMetadata{ + Files: []DpkgFileRecord{ + {Path: "/somewhere"}, + {Path: "/else"}, + }, + }, + expected: []string{ + "/else", + "/somewhere", + }, + }, + { + metadata: DpkgMetadata{ + Files: []DpkgFileRecord{ + {Path: "/somewhere"}, + {Path: ""}, + }, + }, + expected: []string{ + "/somewhere", + }, + }, + } + + for _, test := range tests { + t.Run(strings.Join(test.expected, ","), func(t *testing.T) { + actual := test.metadata.OwnedFiles() + for _, d := range deep.Equal(test.expected, actual) { + t.Errorf("diff: %+v", d) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/file_owner.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/file_owner.go new file mode 100644 index 0000000000000000000000000000000000000000..1e13cf6148f71d7f0a36df386ade0059e5feae08 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/file_owner.go @@ -0,0 +1,9 @@ +package pkg + +// FileOwner is the interface that wraps OwnedFiles method. +// +// OwnedFiles returns a list of files that a piece of +// package Metadata indicates are owned by the package. +type FileOwner interface { + OwnedFiles() []string +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/gem_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/gem_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..51a07a14880b77f4dc53bddf8e75db1c30b86b68 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/gem_metadata.go @@ -0,0 +1,11 @@ +package pkg + +// GemMetadata represents all metadata parsed from the gemspec file +type GemMetadata struct { + Name string `mapstructure:"name" json:"name"` + Version string `mapstructure:"version" json:"version"` + Files []string `mapstructure:"files" json:"files,omitempty"` + Authors []string `mapstructure:"authors" json:"authors,omitempty"` + Licenses []string `mapstructure:"licenses" json:"licenses,omitempty"` + Homepage string `mapstructure:"homepage" json:"homepage,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/golang_bin_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/golang_bin_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..c9c1d3e0a9c2de1ceede58ac2c471d18ed37f269 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/golang_bin_metadata.go @@ -0,0 +1,10 @@ +package pkg + +// GolangBinMetadata represents all captured data for a Golang Binary +type GolangBinMetadata struct { + BuildSettings map[string]string `json:"goBuildSettings,omitempty" cyclonedx:"goBuildSettings"` + GoCompiledVersion string `json:"goCompiledVersion" cyclonedx:"goCompiledVersion"` + Architecture string `json:"architecture" cyclonedx:"architecture"` + H1Digest string `json:"h1Digest,omitempty" cyclonedx:"h1Digest"` + MainModule string `json:"mainModule,omitempty" cyclonedx:"mainModule"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/hackage_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/hackage_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..0f8c38011954214e81c4e6d3857f94134bca08a3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/hackage_metadata.go @@ -0,0 +1,28 @@ +package pkg + +import ( + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +var _ urlIdentifier = (*HackageMetadata)(nil) + +type HackageMetadata struct { + Name string `mapstructure:"name" json:"name"` + Version string `mapstructure:"version" json:"version"` + PkgHash *string `mapstructure:"pkgHash" json:"pkgHash,omitempty"` + SnapshotURL *string `mapstructure:"snapshotURL" json:"snapshotURL,omitempty"` +} + +func (m HackageMetadata) PackageURL(_ *linux.Release) string { + var qualifiers packageurl.Qualifiers + + return packageurl.NewPackageURL( + packageurl.TypeHackage, + "", + m.Name, + m.Version, + qualifiers, + "", + ).ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/java_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/java_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..4e606a03d3fee42ae44c2645b6fd56d7e917237a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/java_metadata.go @@ -0,0 +1,80 @@ +package pkg + +import ( + "strings" + + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/linux" + + "github.com/anchore/syft/internal" +) + +var _ urlIdentifier = (*JavaMetadata)(nil) + +var jenkinsPluginPomPropertiesGroupIDs = []string{ + "io.jenkins.plugins", + "org.jenkins.plugins", + "org.jenkins-ci.plugins", + "io.jenkins-ci.plugins", + "com.cloudbees.jenkins.plugins", +} + +// JavaMetadata encapsulates all Java ecosystem metadata for a package as well as an (optional) parent relationship. +type JavaMetadata struct { + VirtualPath string `json:"virtualPath" cyclonedx:"virtualPath"` // we need to include the virtual path in cyclonedx documents to prevent deduplication of jars within jars + Manifest *JavaManifest `mapstructure:"Manifest" json:"manifest,omitempty"` + PomProperties *PomProperties `mapstructure:"PomProperties" json:"pomProperties,omitempty" cyclonedx:"-"` + PomProject *PomProject `mapstructure:"PomProject" json:"pomProject,omitempty"` + ArchiveDigests []file.Digest `hash:"ignore" json:"digest,omitempty"` + PURL string `hash:"ignore" json:"-"` // pURLs and CPEs are ignored for package IDs + Parent *Package `hash:"ignore" json:"-"` // note: the parent cannot be included in the minimal definition of uniqueness since this field is not reproducible in an encode-decode cycle (is lossy). +} + +// PomProperties represents the fields of interest extracted from a Java archive's pom.properties file. +type PomProperties struct { + Path string `mapstructure:"path" json:"path"` + Name string `mapstructure:"name" json:"name"` + GroupID string `mapstructure:"groupId" json:"groupId" cyclonedx:"groupID"` + ArtifactID string `mapstructure:"artifactId" json:"artifactId" cyclonedx:"artifactID"` + Version string `mapstructure:"version" json:"version"` + Extra map[string]string `mapstructure:",remain" json:"extraFields"` +} + +// PomProject represents fields of interest extracted from a Java archive's pom.xml file. See https://maven.apache.org/ref/3.6.3/maven-model/maven.html for more details. +type PomProject struct { + Path string `json:"path"` + Parent *PomParent `json:"parent,omitempty"` + GroupID string `json:"groupId"` + ArtifactID string `json:"artifactId"` + Version string `json:"version"` + Name string `json:"name"` + Description string `json:"description,omitempty"` + URL string `json:"url,omitempty"` +} + +// PomParent contains the fields within the tag in a pom.xml file +type PomParent struct { + GroupID string `json:"groupId"` + ArtifactID string `json:"artifactId"` + Version string `json:"version"` +} + +// PkgTypeIndicated returns the package Type indicated by the data contained in the PomProperties. +func (p PomProperties) PkgTypeIndicated() Type { + if internal.HasAnyOfPrefixes(p.GroupID, jenkinsPluginPomPropertiesGroupIDs...) || strings.Contains(p.GroupID, ".jenkins.plugin") { + return JenkinsPluginPkg + } + + return JavaPkg +} + +// JavaManifest represents the fields of interest extracted from a Java archive's META-INF/MANIFEST.MF file. +type JavaManifest struct { + Main map[string]string `json:"main,omitempty"` + NamedSections map[string]map[string]string `json:"namedSections,omitempty"` +} + +// PackageURL returns the PURL for the specific Maven package (see https://github.com/package-url/purl-spec) +func (m JavaMetadata) PackageURL(_ *linux.Release) string { + return m.PURL +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/java_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/java_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d538ee5a9d06e58179405cd75690a30b36dd0c25 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/java_metadata_test.go @@ -0,0 +1,111 @@ +package pkg + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestPomProperties_PkgTypeIndicated(t *testing.T) { + cases := []struct { + name string + pomProperties PomProperties + expectedType Type + }{ + { + name: "regular Java package", + pomProperties: PomProperties{ + Path: "some path", + Name: "some name", + GroupID: "some group ID", + ArtifactID: "some artifact ID", + Version: "1", + }, + expectedType: JavaPkg, + }, + { + name: "cloudbees jenkins plugin", + pomProperties: PomProperties{ + Path: "some path", + Name: "some name", + GroupID: "com.cloudbees.jenkins.plugins", + ArtifactID: "some artifact ID", + Version: "1", + }, + expectedType: JenkinsPluginPkg, + }, + { + name: "jenkins.io plugin", + pomProperties: PomProperties{ + Path: "some path", + Name: "some name", + GroupID: "io.jenkins.plugins", + ArtifactID: "some artifact ID", + Version: "1", + }, + expectedType: JenkinsPluginPkg, + }, + { + name: "jenkins-ci.io plugin", + pomProperties: PomProperties{ + Path: "some path", + Name: "some name", + GroupID: "io.jenkins-ci.plugins", + ArtifactID: "some artifact ID", + Version: "1", + }, + expectedType: JenkinsPluginPkg, + }, + { + name: "jenkins-ci.org plugin", + pomProperties: PomProperties{ + Path: "some path", + Name: "some name", + GroupID: "org.jenkins-ci.plugins", + ArtifactID: "some artifact ID", + Version: "1", + }, + expectedType: JenkinsPluginPkg, + }, + { + name: "jenkins.org plugin", + pomProperties: PomProperties{ + Path: "some path", + Name: "some name", + GroupID: "org.jenkins.plugins", + ArtifactID: "some artifact ID", + Version: "1", + }, + expectedType: JenkinsPluginPkg, + }, + { + name: "jenkins plugin prefix", + pomProperties: PomProperties{ + Path: "some path", + Name: "some name", + GroupID: "com.cloudbees.jenkins.plugins.bluesteel", + ArtifactID: "some artifact ID", + Version: "1", + }, + expectedType: JenkinsPluginPkg, + }, + { + name: "jenkins.plugin somewhere in group id", + pomProperties: PomProperties{ + Path: "some path", + Name: "some name", + GroupID: "org.wagoodman.jenkins.plugins.something", + ArtifactID: "some artifact ID", + Version: "1", + }, + expectedType: JenkinsPluginPkg, + }, + } + + for _, tc := range cases { + t.Run(tc.name, func(t *testing.T) { + actual := tc.pomProperties.PkgTypeIndicated() + assert.Equal(t, tc.expectedType, actual) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/kb_package_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/kb_package_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..e243712a6936d903be58b9fe4956008f77d28d99 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/kb_package_metadata.go @@ -0,0 +1,11 @@ +package pkg + +// KbPackageMetadata is slightly odd in how it is expected to map onto data. +// This is critical to grasp because there is no MSRC cataloger. The `ProductID` +// field is expected to be the MSRC Product ID, for example: +// "Windows 10 Version 1703 for 32-bit Systems". +// `Kb` is expected to be the actual KB number, for example "5001028" +type KbPackageMetadata struct { + ProductID string `toml:"product_id" json:"product_id"` + Kb string `toml:"kb" json:"kb"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/language.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/language.go new file mode 100644 index 0000000000000000000000000000000000000000..8e3d6193c6fb20559037a46213d3519925c99ff1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/language.go @@ -0,0 +1,88 @@ +package pkg + +import ( + "strings" + + "github.com/anchore/packageurl-go" +) + +// Language represents a single programming language. +type Language string + +const ( + // the full set of supported programming languages + UnknownLanguage Language = "" + Java Language = "java" + JavaScript Language = "javascript" + Python Language = "python" + PHP Language = "php" + Ruby Language = "ruby" + Go Language = "go" + Rust Language = "rust" + Dart Language = "dart" + Dotnet Language = "dotnet" + Swift Language = "swift" + CPP Language = "c++" + Haskell Language = "haskell" +) + +// AllLanguages is a set of all programming languages detected by syft. +var AllLanguages = []Language{ + Java, + JavaScript, + Python, + PHP, + Ruby, + Go, + Rust, + Dart, + Dotnet, + Swift, + CPP, + Haskell, +} + +// String returns the string representation of the language. +func (l Language) String() string { + return string(l) +} + +func LanguageFromPURL(p string) Language { + purl, err := packageurl.FromString(p) + if err != nil { + return UnknownLanguage + } + + return LanguageByName(purl.Type) +} + +func LanguageByName(name string) Language { + switch strings.ToLower(name) { + case packageurl.TypeMaven, string(purlGradlePkgType), string(JavaPkg), string(Java): + return Java + case packageurl.TypeComposer, string(PhpComposerPkg), string(PHP): + return PHP + case packageurl.TypeGolang, string(GoModulePkg), string(Go): + return Go + case packageurl.TypeNPM, string(JavaScript), "nodejs", "node.js": + return JavaScript + case packageurl.TypePyPi, string(Python): + return Python + case packageurl.TypeGem, string(Ruby): + return Ruby + case purlCargoPkgType, string(RustPkg), string(Rust): + return Rust + case packageurl.TypePub, string(DartPubPkg), string(Dart): + return Dart + case packageurl.TypeDotnet: + return Dotnet + case packageurl.TypeCocoapods, packageurl.TypeSwift, string(CocoapodsPkg): + return Swift + case packageurl.TypeConan, string(CPP): + return CPP + case packageurl.TypeHackage, string(Haskell): + return Haskell + default: + return UnknownLanguage + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/language_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/language_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4acf8c379963f0b24862c4ed0ea0f7b1ca82bbde --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/language_test.go @@ -0,0 +1,231 @@ +package pkg + +import ( + "testing" + + "github.com/scylladb/go-set/strset" + "github.com/stretchr/testify/assert" +) + +func TestLanguageFromPURL(t *testing.T) { + + tests := []struct { + purl string + want Language + }{ + + { + purl: "pkg:npm/util@2.32", + want: JavaScript, + }, + { + purl: "pkg:pypi/util-linux@2.32.1-27.el8", + want: Python, + }, + { + purl: "pkg:gem/ruby-advisory-db-check@0.12.4", + want: Ruby, + }, + { + purl: "pkg:golang/github.com/gorilla/context@234fd47e07d1004f0aed9c", + want: Go, + }, + { + purl: "pkg:pub/util@1.2.34", + want: Dart, + }, + { + purl: "pkg:dotnet/Microsoft.CodeAnalysis.Razor@2.2.0", + want: Dotnet, + }, + { + purl: "pkg:cargo/clap@2.33.0", + want: Rust, + }, + { + purl: "pkg:composer/laravel/laravel@5.5.0", + want: PHP, + }, + { + purl: "pkg:maven/org.apache.xmlgraphics/batik-anim@1.9.1?type=zip&classifier=dist", + want: Java, + }, + { + purl: "pkg:cocoapods/GlossButtonNode@3.1.2", + want: Swift, + }, + { + purl: "pkg:conan/catch2@2.13.8", + want: CPP, + }, + { + purl: "pkg:hackage/HTTP@4000.3.16", + want: Haskell, + }, + } + + var languages []string + var expectedLanguages = strset.New() + for _, ty := range AllLanguages { + expectedLanguages.Add(string(ty)) + } + + for _, tt := range tests { + t.Run(tt.purl, func(t *testing.T) { + actual := LanguageFromPURL(tt.purl) + + if actual != "" { + languages = append(languages, string(actual)) + } + + assert.Equalf(t, tt.want, actual, "LanguageFromPURL(%v)", tt.purl) + }) + } + + assert.ElementsMatch(t, expectedLanguages.List(), languages, "missing one or more languages to test against (maybe a package type was added?)") + +} + +func TestLanguageByName(t *testing.T) { + tests := []struct { + name string + language Language + }{ + { + name: "maven", + language: Java, + }, + { + name: "java", + language: Java, + }, + { + name: "java-archive", + language: Java, + }, + { + name: "java", + language: Java, + }, + { + name: "composer", + language: PHP, + }, + { + name: "php-composer", + language: PHP, + }, + { + name: "php", + language: PHP, + }, + { + name: "go", + language: Go, + }, + { + name: "golang", + language: Go, + }, + { + name: "go-module", + language: Go, + }, + { + name: "npm", + language: JavaScript, + }, + { + name: "javascript", + language: JavaScript, + }, + { + name: "node.js", + language: JavaScript, + }, + { + name: "nodejs", + language: JavaScript, + }, + { + name: "pypi", + language: Python, + }, + { + name: "python", + language: Python, + }, + { + name: "gem", + language: Ruby, + }, + { + name: "ruby", + language: Ruby, + }, + { + name: "rust", + language: Rust, + }, + { + name: "rust-crate", + language: Rust, + }, + { + name: "cargo", + language: Rust, + }, + { + name: "dart", + language: Dart, + }, + { + name: "dart-pub", + language: Dart, + }, + { + name: "pub", + language: Dart, + }, + { + name: "dotnet", + language: Dotnet, + }, + { + name: "swift", + language: Swift, + }, + { + name: "pod", + language: Swift, + }, + { + name: "cocoapods", + language: Swift, + }, + { + name: "unknown", + language: UnknownLanguage, + }, + { + name: "conan", + language: CPP, + }, + { + name: "c++", + language: CPP, + }, + { + name: "hackage", + language: Haskell, + }, + { + name: "haskell", + language: Haskell, + }, + } + + for _, test := range tests { + assert.Equal(t, LanguageByName(test.name), test.language) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/merge_cpes.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/merge_cpes.go new file mode 100644 index 0000000000000000000000000000000000000000..cb766a72feda057dbb8e6a0e5d1d40dab994a1e7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/merge_cpes.go @@ -0,0 +1,25 @@ +package pkg + +import ( + "sort" +) + +func mergeCPEs(a, b []CPE) (result []CPE) { + aCPEs := make(map[string]CPE) + + // keep all CPEs from a and create a quick string-based lookup + for _, aCPE := range a { + aCPEs[aCPE.BindToFmtString()] = aCPE + result = append(result, aCPE) + } + + // keep all unique CPEs from b + for _, bCPE := range b { + if _, exists := aCPEs[bCPE.BindToFmtString()]; !exists { + result = append(result, bCPE) + } + } + + sort.Sort(CPEBySpecificity(result)) + return result +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..99e8d0839fa2b4c2d93f5ee27652c4ed328eadac --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/metadata.go @@ -0,0 +1,81 @@ +package pkg + +import ( + "reflect" +) + +// MetadataType represents the data shape stored within pkg.Package.Metadata. +type MetadataType string + +const ( + // this is the full set of data shapes that can be represented within the pkg.Package.Metadata field + + UnknownMetadataType MetadataType = "UnknownMetadata" + ApkMetadataType MetadataType = "ApkMetadata" + AlpmMetadataType MetadataType = "AlpmMetadata" + DpkgMetadataType MetadataType = "DpkgMetadata" + GemMetadataType MetadataType = "GemMetadata" + JavaMetadataType MetadataType = "JavaMetadata" + NpmPackageJSONMetadataType MetadataType = "NpmPackageJsonMetadata" + RpmMetadataType MetadataType = "RpmMetadata" + DartPubMetadataType MetadataType = "DartPubMetadata" + DotnetDepsMetadataType MetadataType = "DotnetDepsMetadata" + PythonPackageMetadataType MetadataType = "PythonPackageMetadata" + RustCargoPackageMetadataType MetadataType = "RustCargoPackageMetadata" + KbPackageMetadataType MetadataType = "KbPackageMetadata" + GolangBinMetadataType MetadataType = "GolangBinMetadata" + PhpComposerJSONMetadataType MetadataType = "PhpComposerJsonMetadata" + CocoapodsMetadataType MetadataType = "CocoapodsMetadataType" + ConanaMetadataType MetadataType = "ConanaMetadataType" + PortageMetadataType MetadataType = "PortageMetadata" + HackageMetadataType MetadataType = "HackageMetadataType" +) + +var AllMetadataTypes = []MetadataType{ + ApkMetadataType, + AlpmMetadataType, + DpkgMetadataType, + GemMetadataType, + JavaMetadataType, + NpmPackageJSONMetadataType, + RpmMetadataType, + DartPubMetadataType, + DotnetDepsMetadataType, + PythonPackageMetadataType, + RustCargoPackageMetadataType, + KbPackageMetadataType, + GolangBinMetadataType, + PhpComposerJSONMetadataType, + CocoapodsMetadataType, + ConanaMetadataType, + PortageMetadataType, + HackageMetadataType, +} + +var MetadataTypeByName = map[MetadataType]reflect.Type{ + ApkMetadataType: reflect.TypeOf(ApkMetadata{}), + AlpmMetadataType: reflect.TypeOf(AlpmMetadata{}), + DpkgMetadataType: reflect.TypeOf(DpkgMetadata{}), + GemMetadataType: reflect.TypeOf(GemMetadata{}), + JavaMetadataType: reflect.TypeOf(JavaMetadata{}), + NpmPackageJSONMetadataType: reflect.TypeOf(NpmPackageJSONMetadata{}), + RpmMetadataType: reflect.TypeOf(RpmMetadata{}), + DartPubMetadataType: reflect.TypeOf(DartPubMetadata{}), + DotnetDepsMetadataType: reflect.TypeOf(DotnetDepsMetadata{}), + PythonPackageMetadataType: reflect.TypeOf(PythonPackageMetadata{}), + RustCargoPackageMetadataType: reflect.TypeOf(CargoMetadata{}), + KbPackageMetadataType: reflect.TypeOf(KbPackageMetadata{}), + GolangBinMetadataType: reflect.TypeOf(GolangBinMetadata{}), + PhpComposerJSONMetadataType: reflect.TypeOf(PhpComposerJSONMetadata{}), + CocoapodsMetadataType: reflect.TypeOf(CocoapodsMetadata{}), + ConanaMetadataType: reflect.TypeOf(ConanMetadata{}), + PortageMetadataType: reflect.TypeOf(PortageMetadata{}), + HackageMetadataType: reflect.TypeOf(HackageMetadata{}), +} + +func CleanMetadataType(typ MetadataType) MetadataType { + if typ == "RpmdbMetadata" { + return RpmMetadataType + } + return typ +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/npm_package_json_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/npm_package_json_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..3fe51bffec8d87603404ea4da67ccf72bed49322 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/npm_package_json_metadata.go @@ -0,0 +1,44 @@ +package pkg + +import ( + "strings" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +var _ urlIdentifier = (*NpmPackageJSONMetadata)(nil) + +// NpmPackageJSONMetadata holds extra information that is used in pkg.Package +type NpmPackageJSONMetadata struct { + Name string `mapstructure:"name" json:"name"` + Version string `mapstructure:"version" json:"version"` + Files []string `mapstructure:"files" json:"files,omitempty"` + Author string `mapstructure:"author" json:"author"` + Licenses []string `mapstructure:"licenses" json:"licenses"` + Homepage string `mapstructure:"homepage" json:"homepage"` + Description string `mapstructure:"description" json:"description"` + URL string `mapstructure:"url" json:"url"` + Private bool `mapstructure:"private" json:"private"` +} + +// PackageURL returns the PURL for the specific NPM package (see https://github.com/package-url/purl-spec) +func (p NpmPackageJSONMetadata) PackageURL(_ *linux.Release) string { + var namespace string + name := p.Name + + fields := strings.SplitN(p.Name, "/", 2) + if len(fields) > 1 { + namespace = fields[0] + name = fields[1] + } + + return packageurl.NewPackageURL( + packageurl.TypeNPM, + namespace, + name, + p.Version, + nil, + "", + ).ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/npm_package_json_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/npm_package_json_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..ff5e5f0e661ab0d27392a583197500b130900ce4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/npm_package_json_metadata_test.go @@ -0,0 +1,62 @@ +package pkg + +import ( + "fmt" + "testing" + + "github.com/anchore/packageurl-go" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func TestNpmPackageJSONMetadata_PackageURL(t *testing.T) { + + tests := []struct { + name string + metadata NpmPackageJSONMetadata + expected string + namespace string + }{ + { + name: "no namespace", + metadata: NpmPackageJSONMetadata{ + Name: "arborist", + Version: "2.6.2", + }, + expected: "pkg:npm/arborist@2.6.2", + }, + { + name: "split by namespace", + metadata: NpmPackageJSONMetadata{ + Name: "npmcli/arborist", + Version: "2.6.2", + }, + expected: "pkg:npm/npmcli/arborist@2.6.2", + namespace: "npmcli", + }, + { + name: "encoding @ symobl", + metadata: NpmPackageJSONMetadata{ + Name: "@npmcli/arborist", + Version: "2.6.2", + }, + expected: "pkg:npm/%40npmcli/arborist@2.6.2", + namespace: "@npmcli", + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + actual := tt.metadata.PackageURL(nil) + assert.Equal(t, tt.expected, actual) + decoded, err := packageurl.FromString(actual) + require.NoError(t, err) + assert.Equal(t, tt.namespace, decoded.Namespace) + if decoded.Namespace != "" { + assert.Equal(t, tt.metadata.Name, fmt.Sprintf("%s/%s", decoded.Namespace, decoded.Name)) + } else { + assert.Equal(t, tt.metadata.Name, decoded.Name) + } + assert.Equal(t, tt.metadata.Version, decoded.Version) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/package.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/package.go new file mode 100644 index 0000000000000000000000000000000000000000..ccfbbb01f488739c8f2981aceec6d871048dc859 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/package.go @@ -0,0 +1,81 @@ +/* +Package pkg provides the data structures for a package, a package catalog, package types, and domain-specific metadata. +*/ +package pkg + +import ( + "fmt" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/source" +) + +// Package represents an application or library that has been bundled into a distributable format. +// TODO: if we ignore FoundBy for ID generation should we merge the field to show it was found in two places? +type Package struct { + id artifact.ID `hash:"ignore"` + Name string // the package name + Version string // the version of the package + FoundBy string `cyclonedx:"foundBy"` // the specific cataloger that discovered this package + Locations source.LocationSet // the locations that lead to the discovery of this package (note: this is not necessarily the locations that make up this package) + Licenses []string // licenses discovered with the package metadata + Language Language `cyclonedx:"language"` // the language ecosystem this package belongs to (e.g. JavaScript, Python, etc) + Type Type `cyclonedx:"type"` // the package type (e.g. Npm, Yarn, Python, Rpm, Deb, etc) + CPEs []CPE `hash:"ignore"` // all possible Common Platform Enumerators (note: this is NOT included in the definition of the ID since all fields on a CPE are derived from other fields) + PURL string `hash:"ignore"` // the Package URL (see https://github.com/package-url/purl-spec) + MetadataType MetadataType `cyclonedx:"metadataType"` // the shape of the additional data in the "metadata" field + Metadata interface{} // additional data found while parsing the package source +} + +func (p *Package) OverrideID(id artifact.ID) { + p.id = id +} + +func (p *Package) SetID() { + id, err := artifact.IDByHash(p) + if err != nil { + // TODO: what to do in this case? + log.Warnf("unable to get fingerprint of package=%s@%s: %+v", p.Name, p.Version, err) + return + } + p.id = id +} + +func (p Package) ID() artifact.ID { + return p.id +} + +// Stringer to represent a package. +func (p Package) String() string { + return fmt.Sprintf("Pkg(name=%q version=%q type=%q id=%q)", p.Name, p.Version, p.Type, p.id) +} + +func (p *Package) merge(other Package) error { + if p.id != other.id { + return fmt.Errorf("cannot merge packages with different IDs: %q vs %q", p.id, other.id) + } + if p.PURL != other.PURL { + log.Warnf("merging packages have with different pURLs: %q=%q vs %q=%q", p.id, p.PURL, other.id, other.PURL) + } + + p.Locations.Add(other.Locations.ToSlice()...) + + p.CPEs = mergeCPEs(p.CPEs, other.CPEs) + + if p.PURL == "" { + p.PURL = other.PURL + } + return nil +} + +// IsValid checks whether a package has the minimum necessary info +// which is a non-empty name. +// The nil-check was added as a helper as often, in this code base, packages +// move between callers as pointers. +// CycloneDX and SPDX define Name as the minimum required info for a valid package: +// * https://spdx.github.io/spdx-spec/package-information/#73-package-version-field +// * https://cyclonedx.org/docs/1.4/json/#components_items_name +func IsValid(p *Package) bool { + return p != nil && p.Name != "" +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/package_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/package_test.go new file mode 100644 index 0000000000000000000000000000000000000000..6e95e38968946564aa750326826c44cc93b8efb4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/package_test.go @@ -0,0 +1,472 @@ +package pkg + +import ( + "testing" + + "github.com/anchore/stereoscope/pkg/file" + "github.com/anchore/syft/syft/source" + "github.com/google/go-cmp/cmp" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func TestIDUniqueness(t *testing.T) { + originalLocation := source.Location{ + Coordinates: source.Coordinates{ + RealPath: "39.0742° N, 21.8243° E", + FileSystemID: "Earth", + }, + VirtualPath: "/Ancient-Greece", + } + originalPkg := Package{ + Name: "pi", + Version: "3.14", + FoundBy: "Archimedes", + Locations: source.NewLocationSet( + originalLocation, + ), + Licenses: []string{ + "cc0-1.0", + "MIT", + }, + Language: "math", + Type: PythonPkg, + CPEs: []CPE{ + must(NewCPE(`cpe:2.3:a:Archimedes:pi:3.14:*:*:*:*:math:*:*`)), + }, + PURL: "pkg:pypi/pi@3.14", + MetadataType: PythonPackageMetadataType, + Metadata: PythonPackageMetadata{ + Name: "pi", + Version: "3.14", + License: "cc0-1.0", + Author: "Archimedes", + AuthorEmail: "Archimedes@circles.io", + Platform: "universe", + SitePackagesRootPath: "Pi", + }, + } + + // this is a set of differential tests, ensuring that select mutations are reflected in the fingerprint (or not) + tests := []struct { + name string + transform func(pkg Package) Package + expectedIDComparison assert.ComparisonAssertionFunc + }{ + { + name: "go case (no transform)", + transform: func(pkg Package) Package { + // do nothing! + return pkg + }, + expectedIDComparison: assert.Equal, + }, + { + name: "same metadata is ignored", + transform: func(pkg Package) Package { + // note: this is the same as the original values, just a new allocation + pkg.Metadata = PythonPackageMetadata{ + Name: "pi", + Version: "3.14", + License: "cc0-1.0", + Author: "Archimedes", + AuthorEmail: "Archimedes@circles.io", + Platform: "universe", + SitePackagesRootPath: "Pi", + } + return pkg + }, + expectedIDComparison: assert.Equal, + }, + { + name: "licenses order is ignored", + transform: func(pkg Package) Package { + // note: same as the original package, only a different order + pkg.Licenses = []string{ + "MIT", + "cc0-1.0", + } + return pkg + }, + expectedIDComparison: assert.Equal, + }, + { + name: "name is reflected", + transform: func(pkg Package) Package { + pkg.Name = "new!" + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "location is reflected", + transform: func(pkg Package) Package { + locations := source.NewLocationSet(pkg.Locations.ToSlice()...) + locations.Add(source.NewLocation("/somewhere/new")) + pkg.Locations = locations + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "same path for different filesystem is NOT reflected", + transform: func(pkg Package) Package { + newLocation := originalLocation + newLocation.FileSystemID = "Mars" + + pkg.Locations = source.NewLocationSet(newLocation) + return pkg + }, + expectedIDComparison: assert.Equal, + }, + { + name: "multiple equivalent paths for different filesystem is NOT reflected", + transform: func(pkg Package) Package { + newLocation := originalLocation + newLocation.FileSystemID = "Mars" + + locations := source.NewLocationSet(pkg.Locations.ToSlice()...) + locations.Add(newLocation, originalLocation) + + pkg.Locations = locations + return pkg + }, + expectedIDComparison: assert.Equal, + }, + { + name: "version is reflected", + transform: func(pkg Package) Package { + pkg.Version = "new!" + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "licenses is reflected", + transform: func(pkg Package) Package { + pkg.Licenses = []string{"new!"} + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "type is reflected", + transform: func(pkg Package) Package { + pkg.Type = RustPkg + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "metadata type is reflected", + transform: func(pkg Package) Package { + pkg.MetadataType = RustCargoPackageMetadataType + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "CPEs is ignored", + transform: func(pkg Package) Package { + pkg.CPEs = []CPE{} + return pkg + }, + expectedIDComparison: assert.Equal, + }, + { + name: "pURL is ignored", + transform: func(pkg Package) Package { + pkg.PURL = "new!" + return pkg + }, + expectedIDComparison: assert.Equal, + }, + { + name: "language is reflected", + transform: func(pkg Package) Package { + pkg.Language = Rust + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "foundBy is reflected", + transform: func(pkg Package) Package { + pkg.FoundBy = "new!" + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "metadata mutation is reflected", + transform: func(pkg Package) Package { + metadata := pkg.Metadata.(PythonPackageMetadata) + metadata.Name = "new!" + pkg.Metadata = metadata + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "new metadata is reflected", + transform: func(pkg Package) Package { + pkg.Metadata = PythonPackageMetadata{ + Name: "new!", + } + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + { + name: "nil metadata is reflected", + transform: func(pkg Package) Package { + pkg.Metadata = nil + return pkg + }, + expectedIDComparison: assert.NotEqual, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + originalPkg.SetID() + transformedPkg := test.transform(originalPkg) + transformedPkg.SetID() + + originalFingerprint := originalPkg.ID() + assert.NotEmpty(t, originalFingerprint) + transformedFingerprint := transformedPkg.ID() + assert.NotEmpty(t, transformedFingerprint) + + test.expectedIDComparison(t, originalFingerprint, transformedFingerprint) + }) + } +} + +func TestPackage_Merge(t *testing.T) { + originalLocation := source.Location{ + Coordinates: source.Coordinates{ + RealPath: "39.0742° N, 21.8243° E", + FileSystemID: "Earth", + }, + VirtualPath: "/Ancient-Greece", + } + + similarLocation := originalLocation + similarLocation.FileSystemID = "Mars" + + tests := []struct { + name string + subject Package + other Package + expected *Package + }{ + { + name: "merge two packages (different cpes + locations)", + subject: Package{ + Name: "pi", + Version: "3.14", + FoundBy: "Archimedes", + Locations: source.NewLocationSet( + originalLocation, + ), + Licenses: []string{ + "cc0-1.0", + "MIT", + }, + Language: "math", + Type: PythonPkg, + CPEs: []CPE{ + must(NewCPE(`cpe:2.3:a:Archimedes:pi:3.14:*:*:*:*:math:*:*`)), + }, + PURL: "pkg:pypi/pi@3.14", + MetadataType: PythonPackageMetadataType, + Metadata: PythonPackageMetadata{ + Name: "pi", + Version: "3.14", + License: "cc0-1.0", + Author: "Archimedes", + AuthorEmail: "Archimedes@circles.io", + Platform: "universe", + SitePackagesRootPath: "Pi", + }, + }, + other: Package{ + Name: "pi", + Version: "3.14", + FoundBy: "Archimedes", + Locations: source.NewLocationSet( + similarLocation, // NOTE: difference; we have a different layer but the same path + ), + Licenses: []string{ + "cc0-1.0", + "MIT", + }, + Language: "math", + Type: PythonPkg, + CPEs: []CPE{ + must(NewCPE(`cpe:2.3:a:DIFFERENT:pi:3.14:*:*:*:*:math:*:*`)), // NOTE: difference + }, + PURL: "pkg:pypi/pi@3.14", + MetadataType: PythonPackageMetadataType, + Metadata: PythonPackageMetadata{ + Name: "pi", + Version: "3.14", + License: "cc0-1.0", + Author: "Archimedes", + AuthorEmail: "Archimedes@circles.io", + Platform: "universe", + SitePackagesRootPath: "Pi", + }, + }, + expected: &Package{ + Name: "pi", + Version: "3.14", + FoundBy: "Archimedes", + Locations: source.NewLocationSet( + originalLocation, + similarLocation, // NOTE: merge! + ), + Licenses: []string{ + "cc0-1.0", + "MIT", + }, + Language: "math", + Type: PythonPkg, + CPEs: []CPE{ + must(NewCPE(`cpe:2.3:a:Archimedes:pi:3.14:*:*:*:*:math:*:*`)), + must(NewCPE(`cpe:2.3:a:DIFFERENT:pi:3.14:*:*:*:*:math:*:*`)), // NOTE: merge! + }, + PURL: "pkg:pypi/pi@3.14", + MetadataType: PythonPackageMetadataType, + Metadata: PythonPackageMetadata{ + Name: "pi", + Version: "3.14", + License: "cc0-1.0", + Author: "Archimedes", + AuthorEmail: "Archimedes@circles.io", + Platform: "universe", + SitePackagesRootPath: "Pi", + }, + }, + }, + { + name: "error when there are different IDs", + subject: Package{ + Name: "pi", + Version: "3.14", + FoundBy: "Archimedes", + Locations: source.NewLocationSet( + originalLocation, + ), + Licenses: []string{ + "cc0-1.0", + "MIT", + }, + Language: "math", + Type: PythonPkg, + CPEs: []CPE{ + must(NewCPE(`cpe:2.3:a:Archimedes:pi:3.14:*:*:*:*:math:*:*`)), + }, + PURL: "pkg:pypi/pi@3.14", + MetadataType: PythonPackageMetadataType, + Metadata: PythonPackageMetadata{ + Name: "pi", + Version: "3.14", + License: "cc0-1.0", + Author: "Archimedes", + AuthorEmail: "Archimedes@circles.io", + Platform: "universe", + SitePackagesRootPath: "Pi", + }, + }, + other: Package{ + Name: "pi-DIFFERENT", // difference + Version: "3.14", + FoundBy: "Archimedes", + Locations: source.NewLocationSet( + originalLocation, + ), + Licenses: []string{ + "cc0-1.0", + "MIT", + }, + Language: "math", + Type: PythonPkg, + CPEs: []CPE{ + must(NewCPE(`cpe:2.3:a:Archimedes:pi:3.14:*:*:*:*:math:*:*`)), + }, + PURL: "pkg:pypi/pi@3.14", + MetadataType: PythonPackageMetadataType, + Metadata: PythonPackageMetadata{ + Name: "pi", + Version: "3.14", + License: "cc0-1.0", + Author: "Archimedes", + AuthorEmail: "Archimedes@circles.io", + Platform: "universe", + SitePackagesRootPath: "Pi", + }, + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + tt.subject.SetID() + tt.other.SetID() + + err := tt.subject.merge(tt.other) + if tt.expected == nil { + require.Error(t, err) + return + } + require.NoError(t, err) + + tt.expected.SetID() + require.Equal(t, tt.expected.id, tt.subject.id) + + if diff := cmp.Diff(*tt.expected, tt.subject, + cmp.AllowUnexported(Package{}), + cmp.Comparer( + func(x, y source.LocationSet) bool { + return cmp.Equal( + x.ToSlice(), y.ToSlice(), + cmp.AllowUnexported(source.Location{}), + cmp.AllowUnexported(file.Reference{}), + ) + }, + ), + ); diff != "" { + t.Errorf("unexpected result from parsing (-expected +actual)\n%s", diff) + } + }) + } +} + +func TestIsValid(t *testing.T) { + cases := []struct { + name string + given *Package + want bool + }{ + { + name: "nil", + given: nil, + want: false, + }, + { + name: "has-name", + given: &Package{Name: "paul"}, + want: true, + }, + { + name: "has-no-name", + given: &Package{}, + want: false, + }, + } + + for _, c := range cases { + require.Equal(t, c.want, IsValid(c.given), "when package: %s", c.name) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/php_composer_json_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/php_composer_json_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..11b529d2b44fcb139b8a88be7e36346a2c72d092 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/php_composer_json_metadata.go @@ -0,0 +1,70 @@ +package pkg + +import ( + "strings" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +var _ urlIdentifier = (*PhpComposerJSONMetadata)(nil) + +// PhpComposerJSONMetadata represents information found from composer v1/v2 "installed.json" files as well as composer.lock files +type PhpComposerJSONMetadata struct { + Name string `json:"name"` + Version string `json:"version"` + Source PhpComposerExternalReference `json:"source"` + Dist PhpComposerExternalReference `json:"dist"` + Require map[string]string `json:"require,omitempty"` + Provide map[string]string `json:"provide,omitempty"` + RequireDev map[string]string `json:"require-dev,omitempty"` + Suggest map[string]string `json:"suggest,omitempty"` + Type string `json:"type,omitempty"` + NotificationURL string `json:"notification-url,omitempty"` + Bin []string `json:"bin,omitempty"` + License []string `json:"license,omitempty"` + Authors []PhpComposerAuthors `json:"authors,omitempty"` + Description string `json:"description,omitempty"` + Homepage string `json:"homepage,omitempty"` + Keywords []string `json:"keywords,omitempty"` + Time string `json:"time,omitempty"` +} + +type PhpComposerExternalReference struct { + Type string `json:"type"` + URL string `json:"url"` + Reference string `json:"reference"` + Shasum string `json:"shasum,omitempty"` +} + +type PhpComposerAuthors struct { + Name string `json:"name"` + Email string `json:"email,omitempty"` + Homepage string `json:"homepage,omitempty"` +} + +func (m PhpComposerJSONMetadata) PackageURL(_ *linux.Release) string { + var name, vendor string + fields := strings.Split(m.Name, "/") + switch len(fields) { + case 0: + return "" + case 1: + name = m.Name + case 2: + vendor = fields[0] + name = fields[1] + default: + vendor = fields[0] + name = strings.Join(fields[1:], "-") + } + + pURL := packageurl.NewPackageURL( + packageurl.TypeComposer, + vendor, + name, + m.Version, + nil, + "") + return pURL.ToString() +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/php_composer_json_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/php_composer_json_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..81453a7d02e086eb0548bac91e7a6992a6248f61 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/php_composer_json_metadata_test.go @@ -0,0 +1,64 @@ +package pkg + +import ( + "github.com/anchore/syft/syft/linux" + "github.com/sergi/go-diff/diffmatchpatch" + "testing" +) + +func TestPhpComposerJsonMetadata_pURL(t *testing.T) { + tests := []struct { + name string + distro *linux.Release + metadata PhpComposerJSONMetadata + expected string + }{ + { + name: "with extractable vendor", + metadata: PhpComposerJSONMetadata{ + Name: "ven/name", + Version: "1.0.1", + }, + expected: "pkg:composer/ven/name@1.0.1", + }, + { + name: "name with slashes (invalid)", + metadata: PhpComposerJSONMetadata{ + Name: "ven/name/component", + Version: "1.0.1", + }, + expected: "pkg:composer/ven/name-component@1.0.1", + }, + { + name: "unknown vendor", + metadata: PhpComposerJSONMetadata{ + Name: "name", + Version: "1.0.1", + }, + expected: "pkg:composer/name@1.0.1", + }, + { + name: "ignores distro", + distro: &linux.Release{ + ID: "rhel", + VersionID: "8.4", + }, + metadata: PhpComposerJSONMetadata{ + Name: "ven/name", + Version: "1.0.1", + }, + expected: "pkg:composer/ven/name@1.0.1", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := test.metadata.PackageURL(test.distro) + if actual != test.expected { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.expected, actual, true) + t.Errorf("diff: %s", dmp.DiffPrettyText(diffs)) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/portage_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/portage_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..97ae36772dd68ae9793a0579a0829ce66bd6f9b1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/portage_metadata.go @@ -0,0 +1,21 @@ +package pkg + +import ( + "github.com/anchore/syft/syft/file" +) + +const PortageDBGlob = "**/var/db/pkg/*/*/CONTENTS" + +// PortageMetadata represents all captured data for a Package package DB entry. +type PortageMetadata struct { + Package string `mapstructure:"Package" json:"package"` + Version string `mapstructure:"Version" json:"version"` + InstalledSize int `mapstructure:"InstalledSize" json:"installedSize" cyclonedx:"installedSize"` + Files []PortageFileRecord `json:"files"` +} + +// PortageFileRecord represents a single file attributed to a portage package. +type PortageFileRecord struct { + Path string `json:"path"` + Digest *file.Digest `json:"digest,omitempty"` +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/python_package_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/python_package_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..de5664d48c4dcd99a0be2f98b5d10c7a03a80863 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/python_package_metadata.go @@ -0,0 +1,112 @@ +package pkg + +import ( + "fmt" + "sort" + + "github.com/anchore/syft/syft/linux" + + "github.com/anchore/packageurl-go" + "github.com/scylladb/go-set/strset" +) + +var ( + _ FileOwner = (*PythonPackageMetadata)(nil) + _ urlIdentifier = (*PythonPackageMetadata)(nil) +) + +// PythonFileDigest represents the file metadata for a single file attributed to a python package. +type PythonFileDigest struct { + Algorithm string `json:"algorithm"` + Value string `json:"value"` +} + +// PythonFileRecord represents a single entry within a RECORD file for a python wheel or egg package +type PythonFileRecord struct { + Path string `json:"path"` + Digest *PythonFileDigest `json:"digest,omitempty"` + Size string `json:"size,omitempty"` +} + +type PythonDirectURLOriginInfo struct { + URL string `json:"url"` + CommitID string `json:"commitId,omitempty"` + VCS string `json:"vcs,omitempty"` +} + +// PythonPackageMetadata represents all captured data for a python egg or wheel package. +type PythonPackageMetadata struct { + Name string `json:"name" mapstruct:"Name"` + Version string `json:"version" mapstruct:"Version"` + License string `json:"license" mapstruct:"License"` + Author string `json:"author" mapstruct:"Author"` + AuthorEmail string `json:"authorEmail" mapstruct:"Authoremail"` + Platform string `json:"platform" mapstruct:"Platform"` + Files []PythonFileRecord `json:"files,omitempty"` + SitePackagesRootPath string `json:"sitePackagesRootPath"` + TopLevelPackages []string `json:"topLevelPackages,omitempty"` + DirectURLOrigin *PythonDirectURLOriginInfo `json:"directUrlOrigin,omitempty"` +} + +type DirectURLOrigin struct { + URL string `json:"url"` + VCSInfo VCSInfo `json:"vcs_info"` + ArchiveInfo ArchiveInfo `json:"archive_info"` + DirInfo DirInfo `json:"dir_info"` +} + +type DirInfo struct { + Editable bool `json:"editable"` +} + +type ArchiveInfo struct { + Hash string `json:"hash"` +} + +type VCSInfo struct { + CommitID string `json:"commit_id"` + VCS string `json:"vcs"` + RequestedRevision string `json:"requested_revision"` +} + +func (m PythonPackageMetadata) OwnedFiles() (result []string) { + s := strset.New() + for _, f := range m.Files { + if f.Path != "" { + s.Add(f.Path) + } + } + result = s.List() + sort.Strings(result) + return result +} + +func (m PythonPackageMetadata) PackageURL(_ *linux.Release) string { + // generate a purl from the package data + pURL := packageurl.NewPackageURL( + packageurl.TypePyPi, + "", + m.Name, + m.Version, + m.purlQualifiers(), + "") + + return pURL.ToString() +} + +func (m PythonPackageMetadata) purlQualifiers() packageurl.Qualifiers { + q := packageurl.Qualifiers{} + if m.DirectURLOrigin != nil { + q = append(q, m.DirectURLOrigin.vcsURLQualifier()...) + } + return q +} + +func (p PythonDirectURLOriginInfo) vcsURLQualifier() packageurl.Qualifiers { + if p.VCS != "" { + // Taken from https://github.com/package-url/purl-spec/blob/master/PURL-SPECIFICATION.rst#known-qualifiers-keyvalue-pairs + // packageurl-go still doesn't support all qualifier names + return packageurl.Qualifiers{{Key: PURLQualifierVCSURL, Value: fmt.Sprintf("%s+%s@%s", p.VCS, p.URL, p.CommitID)}} + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/python_package_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/python_package_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..f4e61b05d14f83c9e0fed1ccc69f40c176630c1c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/python_package_metadata_test.go @@ -0,0 +1,96 @@ +package pkg + +import ( + "github.com/anchore/syft/syft/linux" + "github.com/sergi/go-diff/diffmatchpatch" + "strings" + "testing" + + "github.com/go-test/deep" +) + +func TestPythonPackageMetadata_pURL(t *testing.T) { + tests := []struct { + name string + distro *linux.Release + metadata PythonPackageMetadata + expected string + }{ + { + name: "with vcs info", + metadata: PythonPackageMetadata{ + Name: "name", + Version: "v0.1.0", + DirectURLOrigin: &PythonDirectURLOriginInfo{ + VCS: "git", + URL: "https://github.com/test/test.git", + CommitID: "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa", + }, + }, + expected: "pkg:pypi/name@v0.1.0?vcs_url=git+https://github.com/test/test.git%40aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa", + }, + { + name: "should not respond to release info", + distro: &linux.Release{ + ID: "rhel", + VersionID: "8.4", + }, + metadata: PythonPackageMetadata{ + Name: "name", + Version: "v0.1.0", + }, + expected: "pkg:pypi/name@v0.1.0", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := test.metadata.PackageURL(test.distro) + if actual != test.expected { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.expected, actual, true) + t.Errorf("diff: %s", dmp.DiffPrettyText(diffs)) + } + }) + } +} + +func TestPythonMetadata_FileOwner(t *testing.T) { + tests := []struct { + metadata PythonPackageMetadata + expected []string + }{ + { + metadata: PythonPackageMetadata{ + Files: []PythonFileRecord{ + {Path: "/somewhere"}, + {Path: "/else"}, + }, + }, + expected: []string{ + "/else", + "/somewhere", + }, + }, + { + metadata: PythonPackageMetadata{ + Files: []PythonFileRecord{ + {Path: "/somewhere"}, + {Path: ""}, + }, + }, + expected: []string{ + "/somewhere", + }, + }, + } + + for _, test := range tests { + t.Run(strings.Join(test.expected, ","), func(t *testing.T) { + actual := test.metadata.OwnedFiles() + for _, d := range deep.Equal(test.expected, actual) { + t.Errorf("diff: %+v", d) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships.go new file mode 100644 index 0000000000000000000000000000000000000000..fe73c1b0f7bc7c495659bfd66ff74bc5351be724 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships.go @@ -0,0 +1,8 @@ +package pkg + +import "github.com/anchore/syft/syft/artifact" + +// TODO: as more relationships are added, this function signature will probably accommodate selection +func NewRelationships(catalog *Catalog) []artifact.Relationship { + return RelationshipsByFileOwnership(catalog) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships_by_file_ownership.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships_by_file_ownership.go new file mode 100644 index 0000000000000000000000000000000000000000..5738b85c107624f283bffea679d556049881f4ab --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships_by_file_ownership.go @@ -0,0 +1,114 @@ +package pkg + +import ( + "sort" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" + "github.com/bmatcuk/doublestar/v4" + "github.com/scylladb/go-set/strset" +) + +// AltRpmDBGlob allows db matches against new locations introduced in fedora:{36,37} +// See https://github.com/anchore/syft/issues/1077 for larger context +const AltRpmDBGlob = "**/rpm/{Packages,Packages.db,rpmdb.sqlite}" + +var globsForbiddenFromBeingOwned = []string{ + // any OS DBs should automatically be ignored to prevent cyclic issues (e.g. the "rpm" RPM owns the path to the + // RPM DB, so if not ignored that package would own all other packages on the system). + ApkDBGlob, + DpkgDBGlob, + RpmDBGlob, + AltRpmDBGlob, + // DEB packages share common copyright info between, this does not mean that sharing these paths implies ownership. + "/usr/share/doc/**/copyright", +} + +type ownershipByFilesMetadata struct { + Files []string `json:"files"` +} + +// RelationshipsByFileOwnership creates a package-to-package relationship based on discovering which packages have +// evidence locations that overlap with ownership claim from another package's package manager metadata. +func RelationshipsByFileOwnership(catalog *Catalog) []artifact.Relationship { + var relationships = findOwnershipByFilesRelationships(catalog) + + var edges []artifact.Relationship + for parentID, children := range relationships { + for childID, files := range children { + fs := files.List() + sort.Strings(fs) + edges = append(edges, artifact.Relationship{ + From: catalog.byID[parentID], + To: catalog.byID[childID], + Type: artifact.OwnershipByFileOverlapRelationship, + Data: ownershipByFilesMetadata{ + Files: fs, + }, + }) + } + } + + return edges +} + +// findOwnershipByFilesRelationships find overlaps in file ownership with a file that defines another package. Specifically, a .Location.Path of +// a package is found to be owned by another (from the owner's .Metadata.Files[]). +func findOwnershipByFilesRelationships(catalog *Catalog) map[artifact.ID]map[artifact.ID]*strset.Set { + var relationships = make(map[artifact.ID]map[artifact.ID]*strset.Set) + + if catalog == nil { + return relationships + } + + for _, candidateOwnerPkg := range catalog.Sorted() { + id := candidateOwnerPkg.ID() + if candidateOwnerPkg.Metadata == nil { + continue + } + + // check to see if this is a file owner + pkgFileOwner, ok := candidateOwnerPkg.Metadata.(FileOwner) + if !ok { + continue + } + for _, ownedFilePath := range pkgFileOwner.OwnedFiles() { + if matchesAny(ownedFilePath, globsForbiddenFromBeingOwned) { + // we skip over known exceptions to file ownership, such as the RPM package owning + // the RPM DB path, otherwise the RPM package would "own" all RPMs, which is not intended + continue + } + + // look for package(s) in the catalog that may be owned by this package and mark the relationship + for _, subPackage := range catalog.PackagesByPath(ownedFilePath) { + subID := subPackage.ID() + if subID == id { + continue + } + if _, exists := relationships[id]; !exists { + relationships[id] = make(map[artifact.ID]*strset.Set) + } + + if _, exists := relationships[id][subID]; !exists { + relationships[id][subID] = strset.New() + } + relationships[id][subID].Add(ownedFilePath) + } + } + } + + return relationships +} + +func matchesAny(s string, globs []string) bool { + for _, g := range globs { + matches, err := doublestar.Match(g, s) + if err != nil { + log.Errorf("failed to match glob=%q : %+v", g, err) + } + if matches { + return true + } + } + return false +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships_by_file_ownership_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships_by_file_ownership_test.go new file mode 100644 index 0000000000000000000000000000000000000000..ff0f71f9e6099b7e4d4e99dcfabd2e9946eecdad --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/relationships_by_file_ownership_test.go @@ -0,0 +1,154 @@ +package pkg + +import ( + "testing" + + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" +) + +func TestOwnershipByFilesRelationship(t *testing.T) { + + tests := []struct { + name string + setup func(t testing.TB) ([]Package, []artifact.Relationship) + }{ + { + name: "owns-by-real-path", + setup: func(t testing.TB) ([]Package, []artifact.Relationship) { + parent := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/a/path", "/another/path"), + source.NewVirtualLocation("/b/path", "/bee/path"), + ), + Type: RpmPkg, + MetadataType: RpmMetadataType, + Metadata: RpmMetadata{ + Files: []RpmdbFileRecord{ + {Path: "/owning/path/1"}, + {Path: "/owning/path/2"}, + {Path: "/d/path"}, + }, + }, + } + parent.SetID() + + child := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/c/path", "/another/path"), + source.NewVirtualLocation("/d/path", "/another/path"), + ), + Type: NpmPkg, + } + child.SetID() + + relationship := artifact.Relationship{ + From: parent, + To: child, + Type: artifact.OwnershipByFileOverlapRelationship, + Data: ownershipByFilesMetadata{ + Files: []string{ + "/d/path", + }, + }, + } + + return []Package{parent, child}, []artifact.Relationship{relationship} + }, + }, + { + name: "owns-by-virtual-path", + setup: func(t testing.TB) ([]Package, []artifact.Relationship) { + parent := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/a/path", "/some/other/path"), + source.NewVirtualLocation("/b/path", "/bee/path"), + ), + Type: RpmPkg, + MetadataType: RpmMetadataType, + Metadata: RpmMetadata{ + Files: []RpmdbFileRecord{ + {Path: "/owning/path/1"}, + {Path: "/owning/path/2"}, + {Path: "/another/path"}, + }, + }, + } + parent.SetID() + + child := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/c/path", "/another/path"), + source.NewLocation("/d/path"), + ), + Type: NpmPkg, + } + child.SetID() + + relationship := artifact.Relationship{ + From: parent, + To: child, + Type: artifact.OwnershipByFileOverlapRelationship, + Data: ownershipByFilesMetadata{ + Files: []string{ + "/another/path", + }, + }, + } + return []Package{parent, child}, []artifact.Relationship{relationship} + }, + }, + { + name: "ignore-empty-path", + setup: func(t testing.TB) ([]Package, []artifact.Relationship) { + parent := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/a/path", "/some/other/path"), + source.NewVirtualLocation("/b/path", "/bee/path"), + ), + Type: RpmPkg, + MetadataType: RpmMetadataType, + Metadata: RpmMetadata{ + Files: []RpmdbFileRecord{ + {Path: "/owning/path/1"}, + {Path: "/owning/path/2"}, + {Path: ""}, + }, + }, + } + + parent.SetID() + + child := Package{ + Locations: source.NewLocationSet( + source.NewVirtualLocation("/c/path", "/another/path"), + source.NewLocation("/d/path"), + ), + Type: NpmPkg, + } + + child.SetID() + + return []Package{parent, child}, nil + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + pkgs, expectedRelations := test.setup(t) + c := NewCatalog(pkgs...) + relationships := RelationshipsByFileOwnership(c) + + assert.Len(t, relationships, len(expectedRelations)) + for idx, expectedRelationship := range expectedRelations { + actualRelationship := relationships[idx] + assert.Equal(t, expectedRelationship.From.ID(), actualRelationship.From.ID()) + assert.Equal(t, expectedRelationship.To.ID(), actualRelationship.To.ID()) + assert.Equal(t, expectedRelationship.Type, actualRelationship.Type) + assert.Equal(t, expectedRelationship.Data, actualRelationship.Data) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/rpm_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/rpm_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..684de377c580bbdb96499cd150cd3a5e1c8e3aff --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/rpm_metadata.go @@ -0,0 +1,100 @@ +package pkg + +import ( + "fmt" + "sort" + "strconv" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/linux" + "github.com/scylladb/go-set/strset" +) + +// Packages is the legacy Berkely db based format +// Packages.db is the "ndb" format used in SUSE +// rpmdb.sqlite is the sqlite format used in fedora + derivates +const RpmDBGlob = "**/var/lib/rpm/{Packages,Packages.db,rpmdb.sqlite}" + +// Used in CBL-Mariner distroless images +const RpmManifestGlob = "**/var/lib/rpmmanifest/container-manifest-2" + +var ( + _ FileOwner = (*RpmMetadata)(nil) + _ urlIdentifier = (*RpmMetadata)(nil) +) + +// RpmMetadata represents all captured data for a RPM DB package entry. +type RpmMetadata struct { + Name string `json:"name"` + Version string `json:"version"` + Epoch *int `json:"epoch" cyclonedx:"epoch" jsonschema:"nullable"` + Arch string `json:"architecture"` + Release string `json:"release" cyclonedx:"release"` + SourceRpm string `json:"sourceRpm" cyclonedx:"sourceRpm"` + Size int `json:"size" cyclonedx:"size"` + License string `json:"license"` + Vendor string `json:"vendor"` + ModularityLabel string `json:"modularityLabel"` + Files []RpmdbFileRecord `json:"files"` +} + +// RpmdbFileRecord represents the file metadata for a single file attributed to a RPM package. +type RpmdbFileRecord struct { + Path string `json:"path"` + Mode RpmdbFileMode `json:"mode"` + Size int `json:"size"` + Digest file.Digest `json:"digest"` + UserName string `json:"userName"` + GroupName string `json:"groupName"` + Flags string `json:"flags"` +} + +// RpmdbFileMode is the raw file mode for a single file. This can be interpreted as the linux stat.h mode (see https://pubs.opengroup.org/onlinepubs/007908799/xsh/sysstat.h.html) +type RpmdbFileMode uint16 + +// PackageURL returns the PURL for the specific RHEL package (see https://github.com/package-url/purl-spec) +func (m RpmMetadata) PackageURL(distro *linux.Release) string { + var namespace string + if distro != nil { + namespace = distro.ID + } + + qualifiers := map[string]string{ + PURLQualifierArch: m.Arch, + } + + if m.Epoch != nil { + qualifiers[PURLQualifierEpoch] = strconv.Itoa(*m.Epoch) + } + + if m.SourceRpm != "" { + qualifiers[PURLQualifierUpstream] = m.SourceRpm + } + + return packageurl.NewPackageURL( + packageurl.TypeRPM, + namespace, + m.Name, + // for purl the epoch is a qualifier, not part of the version + // see https://github.com/package-url/purl-spec/blob/master/PURL-TYPES.rst under the RPM section + fmt.Sprintf("%s-%s", m.Version, m.Release), + purlQualifiers( + qualifiers, + distro, + ), + "", + ).ToString() +} + +func (m RpmMetadata) OwnedFiles() (result []string) { + s := strset.New() + for _, f := range m.Files { + if f.Path != "" { + s.Add(f.Path) + } + } + result = s.List() + sort.Strings(result) + return result +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/rpm_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/rpm_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..85f36212edb5b5acb6b49d4b9fd14ccd449636d0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/rpm_metadata_test.go @@ -0,0 +1,129 @@ +package pkg + +import ( + "strings" + "testing" + + "github.com/go-test/deep" + + "github.com/anchore/syft/syft/linux" + "github.com/sergi/go-diff/diffmatchpatch" +) + +func TestRpmMetadata_pURL(t *testing.T) { + tests := []struct { + name string + distro *linux.Release + metadata RpmMetadata + expected string + }{ + { + name: "go case", + distro: &linux.Release{ + ID: "rhel", + VersionID: "8.4", + }, + metadata: RpmMetadata{ + Name: "p", + Version: "v", + Release: "r", + Epoch: nil, + }, + expected: "pkg:rpm/rhel/p@v-r?distro=rhel-8.4", + }, + { + name: "with arch and epoch", + distro: &linux.Release{ + ID: "centos", + VersionID: "7", + }, + metadata: RpmMetadata{ + Name: "p", + Version: "v", + Arch: "a", + Release: "r", + Epoch: intRef(1), + }, + expected: "pkg:rpm/centos/p@v-r?arch=a&epoch=1&distro=centos-7", + }, + { + name: "missing distro", + metadata: RpmMetadata{ + Name: "p", + Version: "v", + Release: "r", + Epoch: nil, + }, + expected: "pkg:rpm/p@v-r", + }, + { + name: "with upstream source rpm info", + distro: &linux.Release{ + ID: "rhel", + VersionID: "8.4", + }, + metadata: RpmMetadata{ + Name: "p", + Version: "v", + Release: "r", + SourceRpm: "sourcerpm", + }, + expected: "pkg:rpm/rhel/p@v-r?upstream=sourcerpm&distro=rhel-8.4", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + actual := test.metadata.PackageURL(test.distro) + if actual != test.expected { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.expected, actual, true) + t.Errorf("diff: %s", dmp.DiffPrettyText(diffs)) + } + }) + } +} + +func TestRpmMetadata_FileOwner(t *testing.T) { + tests := []struct { + metadata RpmMetadata + expected []string + }{ + { + metadata: RpmMetadata{ + Files: []RpmdbFileRecord{ + {Path: "/somewhere"}, + {Path: "/else"}, + }, + }, + expected: []string{ + "/else", + "/somewhere", + }, + }, + { + metadata: RpmMetadata{ + Files: []RpmdbFileRecord{ + {Path: "/somewhere"}, + {Path: ""}, + }, + }, + expected: []string{ + "/somewhere", + }, + }, + } + + for _, test := range tests { + t.Run(strings.Join(test.expected, ","), func(t *testing.T) { + actual := test.metadata.OwnedFiles() + for _, d := range deep.Equal(test.expected, actual) { + t.Errorf("diff: %+v", d) + } + }) + } +} + +func intRef(i int) *int { + return &i +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/test-fixtures/cpe-data.json b/ci/tools/openeuler-purl/syft-dev/syft/pkg/test-fixtures/cpe-data.json new file mode 100644 index 0000000000000000000000000000000000000000..a1ce425880b72eddd25baf644429db451a777c06 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/test-fixtures/cpe-data.json @@ -0,0 +1,16934 @@ +[ + { + "cpe-string": "cpe:2.3:h:supermicro:x9drff-7\\/i\\(t\\)g\\+:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:supermicro:x9drff-7%2fi%28t%29g%2b:-", + "wfn": { + "Part": "h", + "Vendor": "supermicro", + "Product": "x9drff-7/i(t)g+", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:thimpress:learnpress:3.0.0:closebeta.2:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:thimpress:learnpress:3.0.0:closebeta.2:~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "thimpress", + "Product": "learnpress", + "Version": "3.0.0", + "Update": "closebeta.2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fortinet:fortisiem:3.2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:fortinet:fortisiem:3.2.1", + "wfn": { + "Part": "a", + "Vendor": "fortinet", + "Product": "fortisiem", + "Version": "3.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:uglifyjs_project:uglifyjs:2.8.12:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:uglifyjs_project:uglifyjs:2.8.12::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "uglifyjs_project", + "Product": "uglifyjs", + "Version": "2.8.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:drogon:drogon:1.0.0:beta10:*:*:*:*:*:*", + "cpe-url": "cpe:/a:drogon:drogon:1.0.0:beta10", + "wfn": { + "Part": "a", + "Vendor": "drogon", + "Product": "drogon", + "Version": "1.0.0", + "Update": "beta10", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gtranslate:gtranslate:1.0.4:*:*:*:enterprise:wordpress:*:*", + "cpe-url": "cpe:/a:gtranslate:gtranslate:1.0.4::~~enterprise~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "gtranslate", + "Product": "gtranslate", + "Version": "1.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "enterprise", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:abb:800xa_system:5.1:feature_pack_4_revision_d:*:*:*:*:*:*", + "cpe-url": "cpe:/a:abb:800xa_system:5.1:feature_pack_4_revision_d", + "wfn": { + "Part": "a", + "Vendor": "abb", + "Product": "800xa_system", + "Version": "5.1", + "Update": "feature_pack_4_revision_d", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:totvs:fluig_mobile:1.17.13:*:*:*:*:iphone_os:*:*", + "cpe-url": "cpe:/a:totvs:fluig_mobile:1.17.13::~~~iphone_os~~", + "wfn": { + "Part": "a", + "Vendor": "totvs", + "Product": "fluig_mobile", + "Version": "1.17.13", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "iphone_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:diesel:diesel:1.4.2:*:*:*:*:rust:*:*", + "cpe-url": "cpe:/a:diesel:diesel:1.4.2::~~~rust~~", + "wfn": { + "Part": "a", + "Vendor": "diesel", + "Product": "diesel", + "Version": "1.4.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "rust", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:mitsubishielectric:r16mtcpu_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:mitsubishielectric:r16mtcpu_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "mitsubishielectric", + "Product": "r16mtcpu_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:communigate:communigate_pro:5.4.8:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:communigate:communigate_pro:5.4.8", + "wfn": { + "Part": "a", + "Vendor": "communigate", + "Product": "communigate_pro", + "Version": "5.4.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:smartertools:smartermail:7.0.3845:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:smartertools:smartermail:7.0.3845", + "wfn": { + "Part": "a", + "Vendor": "smartertools", + "Product": "smartermail", + "Version": "7.0.3845", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bluetrace:opentrace:1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bluetrace:opentrace:1.0", + "wfn": { + "Part": "a", + "Vendor": "bluetrace", + "Product": "opentrace", + "Version": "1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:crocoblock:jetwidgets_for_elementor:1.0.8:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:crocoblock:jetwidgets_for_elementor:1.0.8::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "crocoblock", + "Product": "jetwidgets_for_elementor", + "Version": "1.0.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:on_demand_services_sdk:0.14.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:on_demand_services_sdk:0.14.1", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "on_demand_services_sdk", + "Version": "0.14.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:horde:wicked:2.0.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:horde:wicked:2.0.0:-", + "wfn": { + "Part": "a", + "Vendor": "horde", + "Product": "wicked", + "Version": "2.0.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kopano:groupware_core:8.7.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:kopano:groupware_core:8.7.9", + "wfn": { + "Part": "a", + "Vendor": "kopano", + "Product": "groupware_core", + "Version": "8.7.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nasm:netwide_assembler:2.14.0:rc14:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nasm:netwide_assembler:2.14.0:rc14", + "wfn": { + "Part": "a", + "Vendor": "nasm", + "Product": "netwide_assembler", + "Version": "2.14.0", + "Update": "rc14", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:components_for_wp_bakery_page_builder_project:components_for_wp_bakery_page_builder:4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:components_for_wp_bakery_page_builder_project:components_for_wp_bakery_page_builder:4.0", + "wfn": { + "Part": "a", + "Vendor": "components_for_wp_bakery_page_builder_project", + "Product": "components_for_wp_bakery_page_builder", + "Version": "4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:dollar_bank:dollar_bank_mobile:2.4.2:*:*:*:*:iphone_os:*:*", + "cpe-url": "cpe:/a:dollar_bank:dollar_bank_mobile:2.4.2::~~~iphone_os~~", + "wfn": { + "Part": "a", + "Vendor": "dollar_bank", + "Product": "dollar_bank_mobile", + "Version": "2.4.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "iphone_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:adm-zip_project:adm-zip:0.1.4:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:adm-zip_project:adm-zip:0.1.4::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "adm-zip_project", + "Product": "adm-zip", + "Version": "0.1.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vega_project:vega:5.0.0:rc3:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:vega_project:vega:5.0.0:rc3:~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "vega_project", + "Product": "vega", + "Version": "5.0.0", + "Update": "rc3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:citrix:gateway:12.1-62.25:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:citrix:gateway:12.1-62.25", + "wfn": { + "Part": "a", + "Vendor": "citrix", + "Product": "gateway", + "Version": "12.1-62.25", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nystudio107:seomatic:3.1.38:*:*:*:*:craft_cms:*:*", + "cpe-url": "cpe:/a:nystudio107:seomatic:3.1.38::~~~craft_cms~~", + "wfn": { + "Part": "a", + "Vendor": "nystudio107", + "Product": "seomatic", + "Version": "3.1.38", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "craft_cms", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:lucene:2.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:lucene:2.4.0", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "lucene", + "Version": "2.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:spinnaker:orca:1.307.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:spinnaker:orca:1.307.0", + "wfn": { + "Part": "a", + "Vendor": "spinnaker", + "Product": "orca", + "Version": "1.307.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:apple:iphone:1.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:apple:iphone:1.0.1", + "wfn": { + "Part": "h", + "Vendor": "apple", + "Product": "iphone", + "Version": "1.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:scapy:scapy:0.9.17.33:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:scapy:scapy:0.9.17.33", + "wfn": { + "Part": "a", + "Vendor": "scapy", + "Product": "scapy", + "Version": "0.9.17.33", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:metabox:meta_box:3.1.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:metabox:meta_box:3.1.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "metabox", + "Product": "meta_box", + "Version": "3.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:segue_project:segue:2.2.8.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:segue_project:segue:2.2.8.1", + "wfn": { + "Part": "a", + "Vendor": "segue_project", + "Product": "segue", + "Version": "2.2.8.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:idreamsoft:icms:7.0.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:idreamsoft:icms:7.0.7", + "wfn": { + "Part": "a", + "Vendor": "idreamsoft", + "Product": "icms", + "Version": "7.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:spreecommerce:spree:0.30.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:spreecommerce:spree:0.30.0:-", + "wfn": { + "Part": "a", + "Vendor": "spreecommerce", + "Product": "spree", + "Version": "0.30.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ruby-lang:ruby:1.8.7:p357:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ruby-lang:ruby:1.8.7:p357", + "wfn": { + "Part": "a", + "Vendor": "ruby-lang", + "Product": "ruby", + "Version": "1.8.7", + "Update": "p357", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:lucene:3.6.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:lucene:3.6.2", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "lucene", + "Version": "3.6.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:socket.io-file_project:socket.io-file:1.0.41:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:socket.io-file_project:socket.io-file:1.0.41::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "socket.io-file_project", + "Product": "socket.io-file", + "Version": "1.0.41", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mintty_project:mintty:2.2.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mintty_project:mintty:2.2.4", + "wfn": { + "Part": "a", + "Vendor": "mintty_project", + "Product": "mintty", + "Version": "2.2.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:netgear:gs110tp:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:netgear:gs110tp:-", + "wfn": { + "Part": "h", + "Vendor": "netgear", + "Product": "gs110tp", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rsvpmaker_project:rsvpmaker:4.5.6:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:rsvpmaker_project:rsvpmaker:4.5.6::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "rsvpmaker_project", + "Product": "rsvpmaker", + "Version": "4.5.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:security_qradar_analyst_workflow:1.18.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:security_qradar_analyst_workflow:1.18.0", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "security_qradar_analyst_workflow", + "Version": "1.18.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:docker:docker:2.1.0.2:*:*:*:community:*:*:*", + "cpe-url": "cpe:/a:docker:docker:2.1.0.2::~~community~~~", + "wfn": { + "Part": "a", + "Vendor": "docker", + "Product": "docker", + "Version": "2.1.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "community", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloudfoundry:cf-deployment:4.3.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cloudfoundry:cf-deployment:4.3.0", + "wfn": { + "Part": "a", + "Vendor": "cloudfoundry", + "Product": "cf-deployment", + "Version": "4.3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:procurve_switch:jg247a:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:procurve_switch:jg247a", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "procurve_switch", + "Version": "jg247a", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:microsoft:ms-dos:4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:microsoft:ms-dos:4.0", + "wfn": { + "Part": "o", + "Vendor": "microsoft", + "Product": "ms-dos", + "Version": "4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:horde:horde_translation:1.0.0:alpha1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:horde:horde_translation:1.0.0:alpha1", + "wfn": { + "Part": "a", + "Vendor": "horde", + "Product": "horde_translation", + "Version": "1.0.0", + "Update": "alpha1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:saltos:saltos:3.7:8870:*:*:*:*:*:*", + "cpe-url": "cpe:/a:saltos:saltos:3.7:8870", + "wfn": { + "Part": "a", + "Vendor": "saltos", + "Product": "saltos", + "Version": "3.7", + "Update": "8870", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:mikrotik:routeros:6.43.7:*:*:*:-:*:*:*", + "cpe-url": "cpe:/o:mikrotik:routeros:6.43.7::~~-~~~", + "wfn": { + "Part": "o", + "Vendor": "mikrotik", + "Product": "routeros", + "Version": "6.43.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "-", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.3.364:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.3.364", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.3.364", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:telegram:telegram_desktop:0.8.46:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:telegram:telegram_desktop:0.8.46", + "wfn": { + "Part": "a", + "Vendor": "telegram", + "Product": "telegram_desktop", + "Version": "0.8.46", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hiawatha-webserver:hiawatha:5.8.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hiawatha-webserver:hiawatha:5.8.0", + "wfn": { + "Part": "a", + "Vendor": "hiawatha-webserver", + "Product": "hiawatha", + "Version": "5.8.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cpe17:autorun_killer:1.8.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cpe17:autorun_killer:1.8.6", + "wfn": { + "Part": "a", + "Vendor": "cpe17", + "Product": "autorun_killer", + "Version": "1.8.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:intel:tri-band_wireless-ac_17265:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:intel:tri-band_wireless-ac_17265:-", + "wfn": { + "Part": "h", + "Vendor": "intel", + "Product": "tri-band_wireless-ac_17265", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:goodiware:goodreader:2.5:-:*:*:*:iphone_os:*:*", + "cpe-url": "cpe:/a:goodiware:goodreader:2.5:-:~~~iphone_os~~", + "wfn": { + "Part": "a", + "Vendor": "goodiware", + "Product": "goodreader", + "Version": "2.5", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "iphone_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:brainstormforce:astra:1.7.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:brainstormforce:astra:1.7.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "brainstormforce", + "Product": "astra", + "Version": "1.7.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pyrocms:pyrocms:3.4.14:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pyrocms:pyrocms:3.4.14", + "wfn": { + "Part": "a", + "Vendor": "pyrocms", + "Product": "pyrocms", + "Version": "3.4.14", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:iij:seil_b1_firmware:4.61:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:iij:seil_b1_firmware:4.61", + "wfn": { + "Part": "o", + "Vendor": "iij", + "Product": "seil_b1_firmware", + "Version": "4.61", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:imagemagick:imagemagick:6.7.3-5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:imagemagick:imagemagick:6.7.3-5", + "wfn": { + "Part": "a", + "Vendor": "imagemagick", + "Product": "imagemagick", + "Version": "6.7.3-5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:doctrine-project:object_relational_mapper:2.5.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:doctrine-project:object_relational_mapper:2.5.0:-", + "wfn": { + "Part": "a", + "Vendor": "doctrine-project", + "Product": "object_relational_mapper", + "Version": "2.5.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:typo3:typo3:6.2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:typo3:typo3:6.2.1", + "wfn": { + "Part": "a", + "Vendor": "typo3", + "Product": "typo3", + "Version": "6.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnome:libgee:0.8.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnome:libgee:0.8.1", + "wfn": { + "Part": "a", + "Vendor": "gnome", + "Product": "libgee", + "Version": "0.8.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:horde:internet_mail_program:6.0.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:horde:internet_mail_program:6.0.2", + "wfn": { + "Part": "a", + "Vendor": "horde", + "Product": "internet_mail_program", + "Version": "6.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:arubanetworks:aruba_instant:6.4.4.8-4.2.4.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:arubanetworks:aruba_instant:6.4.4.8-4.2.4.6", + "wfn": { + "Part": "a", + "Vendor": "arubanetworks", + "Product": "aruba_instant", + "Version": "6.4.4.8-4.2.4.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:racket-lang:racket:6.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:racket-lang:racket:6.2", + "wfn": { + "Part": "a", + "Vendor": "racket-lang", + "Product": "racket", + "Version": "6.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nlnetlabs:name_server_daemon:4.1.16:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nlnetlabs:name_server_daemon:4.1.16:rc1", + "wfn": { + "Part": "a", + "Vendor": "nlnetlabs", + "Product": "name_server_daemon", + "Version": "4.1.16", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:scilab:scilab:5.1.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:scilab:scilab:5.1.1", + "wfn": { + "Part": "a", + "Vendor": "scilab", + "Product": "scilab", + "Version": "5.1.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:ibm:mcs-7815i-2.0:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:ibm:mcs-7815i-2.0:-", + "wfn": { + "Part": "h", + "Vendor": "ibm", + "Product": "mcs-7815i-2.0", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:plainware:locatoraid:3.2.4:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:plainware:locatoraid:3.2.4::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "plainware", + "Product": "locatoraid", + "Version": "3.2.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:httplib2_project:httplib2:0.10.1:*:*:*:*:python:*:*", + "cpe-url": "cpe:/a:httplib2_project:httplib2:0.10.1::~~~python~~", + "wfn": { + "Part": "a", + "Vendor": "httplib2_project", + "Product": "httplib2", + "Version": "0.10.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "python", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:virtuemart:virtuemart:3.0.0:*:*:*:*:joomla\\!:*:*", + "cpe-url": "cpe:/a:virtuemart:virtuemart:3.0.0::~~~joomla%21~~", + "wfn": { + "Part": "a", + "Vendor": "virtuemart", + "Product": "virtuemart", + "Version": "3.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "joomla!", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:microsoft:.net_core:5.0:preview2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:microsoft:.net_core:5.0:preview2", + "wfn": { + "Part": "a", + "Vendor": "microsoft", + "Product": ".net_core", + "Version": "5.0", + "Update": "preview2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlassian:jira:6.0.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:atlassian:jira:6.0.5", + "wfn": { + "Part": "a", + "Vendor": "atlassian", + "Product": "jira", + "Version": "6.0.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:linuxcontainers:lxc:1.1.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:linuxcontainers:lxc:1.1.2", + "wfn": { + "Part": "a", + "Vendor": "linuxcontainers", + "Product": "lxc", + "Version": "1.1.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pear:html_ajax:0.3.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pear:html_ajax:0.3.4", + "wfn": { + "Part": "a", + "Vendor": "pear", + "Product": "html_ajax", + "Version": "0.3.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:evo:evolution_cms:1.4.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:evo:evolution_cms:1.4.11", + "wfn": { + "Part": "a", + "Vendor": "evo", + "Product": "evolution_cms", + "Version": "1.4.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:abb:cp676-web_firmware:1.76:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:abb:cp676-web_firmware:1.76", + "wfn": { + "Part": "o", + "Vendor": "abb", + "Product": "cp676-web_firmware", + "Version": "1.76", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:fortinet:fortios:4.0.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:fortinet:fortios:4.0.4", + "wfn": { + "Part": "o", + "Vendor": "fortinet", + "Product": "fortios", + "Version": "4.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openwhyd:openwhyd:1.26.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openwhyd:openwhyd:1.26.0", + "wfn": { + "Part": "a", + "Vendor": "openwhyd", + "Product": "openwhyd", + "Version": "1.26.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:axis:mpeg-2_video_server:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:axis:mpeg-2_video_server:-", + "wfn": { + "Part": "h", + "Vendor": "axis", + "Product": "mpeg-2_video_server", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:intel:d845bg_motherboard:p02-0015:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:intel:d845bg_motherboard:p02-0015", + "wfn": { + "Part": "h", + "Vendor": "intel", + "Product": "d845bg_motherboard", + "Version": "p02-0015", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redis:redis:2.8.10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redis:redis:2.8.10", + "wfn": { + "Part": "a", + "Vendor": "redis", + "Product": "redis", + "Version": "2.8.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:db2:9.7.0.3:*:*:*:express:*:*:*", + "cpe-url": "cpe:/a:ibm:db2:9.7.0.3::~~express~~~", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "db2", + "Version": "9.7.0.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "express", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ninjaforms:ninja_forms:3.0.21:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:ninjaforms:ninja_forms:3.0.21::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "ninjaforms", + "Product": "ninja_forms", + "Version": "3.0.21", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim_project:vim:0.15.4:*:*:*:*:visual_studio_code:*:*", + "cpe-url": "cpe:/a:vim_project:vim:0.15.4::~~~visual_studio_code~~", + "wfn": { + "Part": "a", + "Vendor": "vim_project", + "Product": "vim", + "Version": "0.15.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "visual_studio_code", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jekyllrb:jekyll:1.4.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:jekyllrb:jekyll:1.4.3", + "wfn": { + "Part": "a", + "Vendor": "jekyllrb", + "Product": "jekyll", + "Version": "1.4.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:eclipse:keti:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:eclipse:keti:-", + "wfn": { + "Part": "a", + "Vendor": "eclipse", + "Product": "keti", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:softvelum:nimble_streamer:3.4.0-4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:softvelum:nimble_streamer:3.4.0-4", + "wfn": { + "Part": "a", + "Vendor": "softvelum", + "Product": "nimble_streamer", + "Version": "3.4.0-4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:netgear:r7850:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:netgear:r7850:-", + "wfn": { + "Part": "h", + "Vendor": "netgear", + "Product": "r7850", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:proftpd:proftpd:1.2.2:rc3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:proftpd:proftpd:1.2.2:rc3", + "wfn": { + "Part": "a", + "Vendor": "proftpd", + "Product": "proftpd", + "Version": "1.2.2", + "Update": "rc3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rocomotion:pplog:2.32:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:rocomotion:pplog:2.32", + "wfn": { + "Part": "a", + "Vendor": "rocomotion", + "Product": "pplog", + "Version": "2.32", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sysstat_project:sysstat:9.1.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sysstat_project:sysstat:9.1.5", + "wfn": { + "Part": "a", + "Vendor": "sysstat_project", + "Product": "sysstat", + "Version": "9.1.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redhat:beaker:0.8.0-11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redhat:beaker:0.8.0-11", + "wfn": { + "Part": "a", + "Vendor": "redhat", + "Product": "beaker", + "Version": "0.8.0-11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:percona:percona_server:5.6.44-85.0-1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:percona:percona_server:5.6.44-85.0-1", + "wfn": { + "Part": "a", + "Vendor": "percona", + "Product": "percona_server", + "Version": "5.6.44-85.0-1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:omniauth:omniauth:1.1.3:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:omniauth:omniauth:1.1.3::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "omniauth", + "Product": "omniauth", + "Version": "1.1.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:videojs:video.js:6.1.0:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:videojs:video.js:6.1.0::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "videojs", + "Product": "video.js", + "Version": "6.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:httpie:httpie:0.1.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:httpie:httpie:0.1.5", + "wfn": { + "Part": "a", + "Vendor": "httpie", + "Product": "httpie", + "Version": "0.1.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fortinet:fortimanager:5.0.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:fortinet:fortimanager:5.0.4", + "wfn": { + "Part": "a", + "Vendor": "fortinet", + "Product": "fortimanager", + "Version": "5.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:check_mk_project:check_mk:1.4.0:p25:*:*:*:*:*:*", + "cpe-url": "cpe:/a:check_mk_project:check_mk:1.4.0:p25", + "wfn": { + "Part": "a", + "Vendor": "check_mk_project", + "Product": "check_mk", + "Version": "1.4.0", + "Update": "p25", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wp-livechat:live_chat_support:2.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wp-livechat:live_chat_support:2.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wp-livechat", + "Product": "live_chat_support", + "Version": "2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:signal:signal:2.25.0.10:*:*:*:*:iphone_os:*:*", + "cpe-url": "cpe:/a:signal:signal:2.25.0.10::~~~iphone_os~~", + "wfn": { + "Part": "a", + "Vendor": "signal", + "Product": "signal", + "Version": "2.25.0.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "iphone_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:telerik:ui_for_asp.net_core:2018.2.620:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:telerik:ui_for_asp.net_core:2018.2.620", + "wfn": { + "Part": "a", + "Vendor": "telerik", + "Product": "ui_for_asp.net_core", + "Version": "2018.2.620", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kde:paste_applet:4.6.90:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:kde:paste_applet:4.6.90", + "wfn": { + "Part": "a", + "Vendor": "kde", + "Product": "paste_applet", + "Version": "4.6.90", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:chrome:5.0.382.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:chrome:5.0.382.3", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "chrome", + "Version": "5.0.382.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:fronius:primo_5.0-1_firmware:3.14.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:fronius:primo_5.0-1_firmware:3.14.1", + "wfn": { + "Part": "o", + "Vendor": "fronius", + "Product": "primo_5.0-1_firmware", + "Version": "3.14.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:videolan:vlc_media_player:2.0.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:videolan:vlc_media_player:2.0.0", + "wfn": { + "Part": "a", + "Vendor": "videolan", + "Product": "vlc_media_player", + "Version": "2.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:woocommerce:woocommerce:3.5.7:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:woocommerce:woocommerce:3.5.7::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "woocommerce", + "Product": "woocommerce", + "Version": "3.5.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:yajl-ruby_project:yajl-ruby:1.2.3:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:yajl-ruby_project:yajl-ruby:1.2.3::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "yajl-ruby_project", + "Product": "yajl-ruby", + "Version": "1.2.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gitlab:gitlab:8.2.4:*:*:*:community:*:*:*", + "cpe-url": "cpe:/a:gitlab:gitlab:8.2.4::~~community~~~", + "wfn": { + "Part": "a", + "Vendor": "gitlab", + "Product": "gitlab", + "Version": "8.2.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "community", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:b3log:symphony:3.4.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:b3log:symphony:3.4.7", + "wfn": { + "Part": "a", + "Vendor": "b3log", + "Product": "symphony", + "Version": "3.4.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gajim:gajim:1.3.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gajim:gajim:1.3.0:-", + "wfn": { + "Part": "a", + "Vendor": "gajim", + "Product": "gajim", + "Version": "1.3.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rope_project:rope:0.15.0:*:*:*:*:python:*:*", + "cpe-url": "cpe:/a:rope_project:rope:0.15.0::~~~python~~", + "wfn": { + "Part": "a", + "Vendor": "rope_project", + "Product": "rope", + "Version": "0.15.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "python", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:microsoft:sql_srv:7.0:sp3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:microsoft:sql_srv:7.0:sp3", + "wfn": { + "Part": "a", + "Vendor": "microsoft", + "Product": "sql_srv", + "Version": "7.0", + "Update": "sp3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openconext:openconext_engineblock:1.17.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openconext:openconext_engineblock:1.17.0", + "wfn": { + "Part": "a", + "Vendor": "openconext", + "Product": "openconext_engineblock", + "Version": "1.17.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nmap:nmap:7.30:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nmap:nmap:7.30", + "wfn": { + "Part": "a", + "Vendor": "nmap", + "Product": "nmap", + "Version": "7.30", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:openmeetings:3.3.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:openmeetings:3.3.1", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "openmeetings", + "Version": "3.3.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:owasp_dependency-track:3.1.0:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:owasp_dependency-track:3.1.0::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "owasp_dependency-track", + "Version": "3.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpsymposiumpro:wp_symposium:13.08.01:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpsymposiumpro:wp_symposium:13.08.01::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpsymposiumpro", + "Product": "wp_symposium", + "Version": "13.08.01", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:chrome:4.0.249.51:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:chrome:4.0.249.51", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "chrome", + "Version": "4.0.249.51", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:feehi:feehi_cms:2.1.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:feehi:feehi_cms:2.1.1", + "wfn": { + "Part": "a", + "Vendor": "feehi", + "Product": "feehi_cms", + "Version": "2.1.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:altiris:network_discovery_language_pack:6.0.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:altiris:network_discovery_language_pack:6.0.4", + "wfn": { + "Part": "a", + "Vendor": "altiris", + "Product": "network_discovery_language_pack", + "Version": "6.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:python:python:3.9.0:alpha6:*:*:*:*:*:*", + "cpe-url": "cpe:/a:python:python:3.9.0:alpha6", + "wfn": { + "Part": "a", + "Vendor": "python", + "Product": "python", + "Version": "3.9.0", + "Update": "alpha6", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:app_engine_python_sdk:1.9.71:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:app_engine_python_sdk:1.9.71", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "app_engine_python_sdk", + "Version": "1.9.71", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:web_security_appliance:7.1.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:web_security_appliance:7.1.2", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "web_security_appliance", + "Version": "7.1.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:html-pdf_project:html-pdf:-:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:html-pdf_project:html-pdf:-::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "html-pdf_project", + "Product": "html-pdf", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:htmlsanitizer_project:htmlsanitizer:3.3.125:beta:*:*:*:*:*:*", + "cpe-url": "cpe:/a:htmlsanitizer_project:htmlsanitizer:3.3.125:beta", + "wfn": { + "Part": "a", + "Vendor": "htmlsanitizer_project", + "Product": "htmlsanitizer", + "Version": "3.3.125", + "Update": "beta", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:neliosoftware:nelio_ab_testing:4.4.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:neliosoftware:nelio_ab_testing:4.4.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "neliosoftware", + "Product": "nelio_ab_testing", + "Version": "4.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redhat:jbpm:7.12.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redhat:jbpm:7.12.0", + "wfn": { + "Part": "a", + "Vendor": "redhat", + "Product": "jbpm", + "Version": "7.12.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sap:businessobjects_business_intelligence:4.1:support_package1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sap:businessobjects_business_intelligence:4.1:support_package1", + "wfn": { + "Part": "a", + "Vendor": "sap", + "Product": "businessobjects_business_intelligence", + "Version": "4.1", + "Update": "support_package1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:cordova:5.2.2:*:*:*:*:android:*:*", + "cpe-url": "cpe:/a:apache:cordova:5.2.2::~~~android~~", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "cordova", + "Version": "5.2.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "android", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:nx-os:12.0\\(1q\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:nx-os:12.0%281q%29", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "nx-os", + "Version": "12.0(1q)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:solarwinds:serv-u:15.2.2:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:solarwinds:serv-u:15.2.2:-", + "wfn": { + "Part": "a", + "Vendor": "solarwinds", + "Product": "serv-u", + "Version": "15.2.2", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpdeveloper:essential_addons_for_elementor:2.8.7:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpdeveloper:essential_addons_for_elementor:2.8.7::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpdeveloper", + "Product": "essential_addons_for_elementor", + "Version": "2.8.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlassian:sourcetree:1.0.7:*:*:*:*:macos:*:*", + "cpe-url": "cpe:/a:atlassian:sourcetree:1.0.7::~~~macos~~", + "wfn": { + "Part": "a", + "Vendor": "atlassian", + "Product": "sourcetree", + "Version": "1.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "macos", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:infinispan:infinispan-server-runtime:11.0.0:alpha1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:infinispan:infinispan-server-runtime:11.0.0:alpha1", + "wfn": { + "Part": "a", + "Vendor": "infinispan", + "Product": "infinispan-server-runtime", + "Version": "11.0.0", + "Update": "alpha1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.3.485:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.3.485", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.3.485", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bytecodealliance:cranelift-codegen:0.17.0:alpha:*:*:*:rust:*:*", + "cpe-url": "cpe:/a:bytecodealliance:cranelift-codegen:0.17.0:alpha:~~~rust~~", + "wfn": { + "Part": "a", + "Vendor": "bytecodealliance", + "Product": "cranelift-codegen", + "Version": "0.17.0", + "Update": "alpha", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "rust", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zeit:next.js:9.2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:zeit:next.js:9.2.1", + "wfn": { + "Part": "a", + "Vendor": "zeit", + "Product": "next.js", + "Version": "9.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ansible-vault_project:ansible-vault:1.2.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ansible-vault_project:ansible-vault:1.2.0", + "wfn": { + "Part": "a", + "Vendor": "ansible-vault_project", + "Product": "ansible-vault", + "Version": "1.2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:sg300-28p_firmware:1.4.8.06:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:sg300-28p_firmware:1.4.8.06", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "sg300-28p_firmware", + "Version": "1.4.8.06", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:digium:asterisk:1.4.40:rc3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:digium:asterisk:1.4.40:rc3", + "wfn": { + "Part": "a", + "Vendor": "digium", + "Product": "asterisk", + "Version": "1.4.40", + "Update": "rc3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:idrive:remotepc:7.6.26:*:*:*:*:macos:*:*", + "cpe-url": "cpe:/a:idrive:remotepc:7.6.26::~~~macos~~", + "wfn": { + "Part": "a", + "Vendor": "idrive", + "Product": "remotepc", + "Version": "7.6.26", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "macos", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:oracle:ireceivables:12.2.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:oracle:ireceivables:12.2.3", + "wfn": { + "Part": "a", + "Vendor": "oracle", + "Product": "ireceivables", + "Version": "12.2.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloud_foundry:bits_service:2.25.0:dev7:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cloud_foundry:bits_service:2.25.0:dev7", + "wfn": { + "Part": "a", + "Vendor": "cloud_foundry", + "Product": "bits_service", + "Version": "2.25.0", + "Update": "dev7", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zeromq:zeromq:0.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:zeromq:zeromq:0.5", + "wfn": { + "Part": "a", + "Vendor": "zeromq", + "Product": "zeromq", + "Version": "0.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mobyproject:moby:0.1.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mobyproject:moby:0.1.6", + "wfn": { + "Part": "a", + "Vendor": "mobyproject", + "Product": "moby", + "Version": "0.1.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlassian:jira:3.7:*:enterprise:*:*:*:*:*", + "cpe-url": "cpe:/a:atlassian:jira:3.7::enterprise", + "wfn": { + "Part": "a", + "Vendor": "atlassian", + "Product": "jira", + "Version": "3.7", + "Update": "", + "Edition": "enterprise", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:intel:ac_9462_firmware:22.40:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:intel:ac_9462_firmware:22.40", + "wfn": { + "Part": "o", + "Vendor": "intel", + "Product": "ac_9462_firmware", + "Version": "22.40", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:lenovo:thinkpad_usb_3.0_ethernet_adapter:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:lenovo:thinkpad_usb_3.0_ethernet_adapter:-", + "wfn": { + "Part": "h", + "Vendor": "lenovo", + "Product": "thinkpad_usb_3.0_ethernet_adapter", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:ui:unifi_dream_machine_pro_firmware:1.8.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:ui:unifi_dream_machine_pro_firmware:1.8.4", + "wfn": { + "Part": "o", + "Vendor": "ui", + "Product": "unifi_dream_machine_pro_firmware", + "Version": "1.8.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:php:php:3.0.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:php:php:3.0.7", + "wfn": { + "Part": "a", + "Vendor": "php", + "Product": "php", + "Version": "3.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:handsontable:handsontable:0.32.0:beta2:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:handsontable:handsontable:0.32.0:beta2:~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "handsontable", + "Product": "handsontable", + "Version": "0.32.0", + "Update": "beta2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:charlesproxy:charles:3.8:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:charlesproxy:charles:3.8", + "wfn": { + "Part": "a", + "Vendor": "charlesproxy", + "Product": "charles", + "Version": "3.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:f5:big-ip_analytics:13.1.1.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:f5:big-ip_analytics:13.1.1.3", + "wfn": { + "Part": "a", + "Vendor": "f5", + "Product": "big-ip_analytics", + "Version": "13.1.1.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:jenkins:1.437:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:jenkins:jenkins:1.437", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "jenkins", + "Version": "1.437", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:shout_project:shout:0.32.5:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:shout_project:shout:0.32.5::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "shout_project", + "Product": "shout", + "Version": "0.32.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openenergymonitor:emoncms:10.1.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openenergymonitor:emoncms:10.1.5", + "wfn": { + "Part": "a", + "Vendor": "openenergymonitor", + "Product": "emoncms", + "Version": "10.1.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:advancedcustomfields:advanced_custom_fields:5.5.7:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:advancedcustomfields:advanced_custom_fields:5.5.7::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "advancedcustomfields", + "Product": "advanced_custom_fields", + "Version": "5.5.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cpanel:cpanel:11.38.0.19:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cpanel:cpanel:11.38.0.19", + "wfn": { + "Part": "a", + "Vendor": "cpanel", + "Product": "cpanel", + "Version": "11.38.0.19", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ovirt:ovirt:4.2.4.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ovirt:ovirt:4.2.4.5", + "wfn": { + "Part": "a", + "Vendor": "ovirt", + "Product": "ovirt", + "Version": "4.2.4.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ruamel.yaml_project:ruamel.yaml:0.15.13:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ruamel.yaml_project:ruamel.yaml:0.15.13", + "wfn": { + "Part": "a", + "Vendor": "ruamel.yaml_project", + "Product": "ruamel.yaml", + "Version": "0.15.13", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:cisco:firepower_1020:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:cisco:firepower_1020:-", + "wfn": { + "Part": "h", + "Vendor": "cisco", + "Product": "firepower_1020", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnome:libsoup:2.34.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnome:libsoup:2.34.0", + "wfn": { + "Part": "a", + "Vendor": "gnome", + "Product": "libsoup", + "Version": "2.34.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:python:setuptools:36.2.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:python:setuptools:36.2.4", + "wfn": { + "Part": "a", + "Vendor": "python", + "Product": "setuptools", + "Version": "36.2.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sonarsource:sonarqube_docker_image:6.7.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sonarsource:sonarqube_docker_image:6.7.3", + "wfn": { + "Part": "a", + "Vendor": "sonarsource", + "Product": "sonarqube_docker_image", + "Version": "6.7.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gatsbyjs:gatsby-source-wordpress:3.1.70:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:gatsbyjs:gatsby-source-wordpress:3.1.70::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "gatsbyjs", + "Product": "gatsby-source-wordpress", + "Version": "3.1.70", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redhat:jboss-ejb-client:4.0.0:cr6:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redhat:jboss-ejb-client:4.0.0:cr6", + "wfn": { + "Part": "a", + "Vendor": "redhat", + "Product": "jboss-ejb-client", + "Version": "4.0.0", + "Update": "cr6", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:octopus:tentacle:6.1.1016:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:octopus:tentacle:6.1.1016", + "wfn": { + "Part": "a", + "Vendor": "octopus", + "Product": "tentacle", + "Version": "6.1.1016", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:dpl:product_feed_on_woocommerce_for_google\\,_awin\\,_shareasale\\,_bing\\,_and_more:3.0.0.2:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:dpl:product_feed_on_woocommerce_for_google%2c_awin%2c_shareasale%2c_bing%2c_and_more:3.0.0.2::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "dpl", + "Product": "product_feed_on_woocommerce_for_google,_awin,_shareasale,_bing,_and_more", + "Version": "3.0.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:intel:xeon_e5-1428l_v3_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:intel:xeon_e5-1428l_v3_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "intel", + "Product": "xeon_e5-1428l_v3_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:netgear:r7000p_firmware:v1.0.11.100_10.2.100:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:netgear:r7000p_firmware:v1.0.11.100_10.2.100", + "wfn": { + "Part": "o", + "Vendor": "netgear", + "Product": "r7000p_firmware", + "Version": "v1.0.11.100_10.2.100", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:lynxtechnology:twonky_server:7.3.1-3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:lynxtechnology:twonky_server:7.3.1-3", + "wfn": { + "Part": "a", + "Vendor": "lynxtechnology", + "Product": "twonky_server", + "Version": "7.3.1-3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:shareaholic:shareaholic:7.0.4.7:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:shareaholic:shareaholic:7.0.4.7::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "shareaholic", + "Product": "shareaholic", + "Version": "7.0.4.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ios:12.2\\(31\\)sga9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ios:12.2%2831%29sga9", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ios", + "Version": "12.2(31)sga9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:veronalabs:wp_statistics:8.6:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:veronalabs:wp_statistics:8.6::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "veronalabs", + "Product": "wp_statistics", + "Version": "8.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zom:zom:1.0.17:*:*:*:*:iphone_os:*:*", + "cpe-url": "cpe:/a:zom:zom:1.0.17::~~~iphone_os~~", + "wfn": { + "Part": "a", + "Vendor": "zom", + "Product": "zom", + "Version": "1.0.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "iphone_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:codepeople:appointment_booking_calendar:1.2.44:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:codepeople:appointment_booking_calendar:1.2.44::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "codepeople", + "Product": "appointment_booking_calendar", + "Version": "1.2.44", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:linuxcontainers:lxd:2.0.10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:linuxcontainers:lxd:2.0.10", + "wfn": { + "Part": "a", + "Vendor": "linuxcontainers", + "Product": "lxd", + "Version": "2.0.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bochs_project:bochs:2.0:pre1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bochs_project:bochs:2.0:pre1", + "wfn": { + "Part": "a", + "Vendor": "bochs_project", + "Product": "bochs", + "Version": "2.0", + "Update": "pre1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:qualcomm:smb1394_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:qualcomm:smb1394_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "qualcomm", + "Product": "smb1394_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.4a.015:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.4a.015", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.4a.015", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:superantispyware:superantispyware:4.26.1002:*:*:*:professional:*:*:*", + "cpe-url": "cpe:/a:superantispyware:superantispyware:4.26.1002::~~professional~~~", + "wfn": { + "Part": "a", + "Vendor": "superantispyware", + "Product": "superantispyware", + "Version": "4.26.1002", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "professional", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:silverstripe:silverstripe:2.4.4:rc2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:silverstripe:silverstripe:2.4.4:rc2", + "wfn": { + "Part": "a", + "Vendor": "silverstripe", + "Product": "silverstripe", + "Version": "2.4.4", + "Update": "rc2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:advantech:webaccess:7.0-2010.05.10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:advantech:webaccess:7.0-2010.05.10", + "wfn": { + "Part": "a", + "Vendor": "advantech", + "Product": "webaccess", + "Version": "7.0-2010.05.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tinyxml2_project:tinyxml2:5.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tinyxml2_project:tinyxml2:5.0.1", + "wfn": { + "Part": "a", + "Vendor": "tinyxml2_project", + "Product": "tinyxml2", + "Version": "5.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:eclipse:jetty:4.2.23:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:eclipse:jetty:4.2.23:-", + "wfn": { + "Part": "a", + "Vendor": "eclipse", + "Product": "jetty", + "Version": "4.2.23", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:property-expr_project:property-expr:1.0.0:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:property-expr_project:property-expr:1.0.0::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "property-expr_project", + "Product": "property-expr", + "Version": "1.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:netgear:srs60_firmware:2.5.2.104:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:netgear:srs60_firmware:2.5.2.104", + "wfn": { + "Part": "o", + "Vendor": "netgear", + "Product": "srs60_firmware", + "Version": "2.5.2.104", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:spinnaker:orca:6.77.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:spinnaker:orca:6.77.5", + "wfn": { + "Part": "a", + "Vendor": "spinnaker", + "Product": "orca", + "Version": "6.77.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:protobufjs_project:protobufjs:1.0.0:beta5:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:protobufjs_project:protobufjs:1.0.0:beta5:~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "protobufjs_project", + "Product": "protobufjs", + "Version": "1.0.0", + "Update": "beta5", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:imagemagick:imagemagick:6.4.5-9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:imagemagick:imagemagick:6.4.5-9", + "wfn": { + "Part": "a", + "Vendor": "imagemagick", + "Product": "imagemagick", + "Version": "6.4.5-9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnome:evolution-ews:3.8.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnome:evolution-ews:3.8.1", + "wfn": { + "Part": "a", + "Vendor": "gnome", + "Product": "evolution-ews", + "Version": "3.8.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openstack:horizon:18.3.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openstack:horizon:18.3.3", + "wfn": { + "Part": "a", + "Vendor": "openstack", + "Product": "horizon", + "Version": "18.3.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:advanced_access_manager_project:advanced_access_manager:6.3.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:advanced_access_manager_project:advanced_access_manager:6.3.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "advanced_access_manager_project", + "Product": "advanced_access_manager", + "Version": "6.3.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rails_admin_project:rails_admin:0.6.8:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:rails_admin_project:rails_admin:0.6.8::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "rails_admin_project", + "Product": "rails_admin", + "Version": "0.6.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:moxa:nport_ia5150a_firmware:1.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:moxa:nport_ia5150a_firmware:1.4", + "wfn": { + "Part": "o", + "Vendor": "moxa", + "Product": "nport_ia5150a_firmware", + "Version": "1.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jkeenan:file-path_module:2.09:*:*:*:*:perl:*:*", + "cpe-url": "cpe:/a:jkeenan:file-path_module:2.09::~~~perl~~", + "wfn": { + "Part": "a", + "Vendor": "jkeenan", + "Product": "file-path_module", + "Version": "2.09", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "perl", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:corusent:global_tv:4.3.1:*:*:*:*:iphone_os:*:*", + "cpe-url": "cpe:/a:corusent:global_tv:4.3.1::~~~iphone_os~~", + "wfn": { + "Part": "a", + "Vendor": "corusent", + "Product": "global_tv", + "Version": "4.3.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "iphone_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ldapauth_project:ldapauth:2.3.1:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:ldapauth_project:ldapauth:2.3.1::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "ldapauth_project", + "Product": "ldapauth", + "Version": "2.3.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openvswitch:openvswitch:2.9.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openvswitch:openvswitch:2.9.9", + "wfn": { + "Part": "a", + "Vendor": "openvswitch", + "Product": "openvswitch", + "Version": "2.9.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:packagekit_project:packagekit:0.8.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:packagekit_project:packagekit:0.8.4", + "wfn": { + "Part": "a", + "Vendor": "packagekit_project", + "Product": "packagekit", + "Version": "0.8.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:piwik:piwik:1.11.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:piwik:piwik:1.11.1", + "wfn": { + "Part": "a", + "Vendor": "piwik", + "Product": "piwik", + "Version": "1.11.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:8.0.1609:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:8.0.1609", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "8.0.1609", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:npmjs:npm:1.2.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:npmjs:npm:1.2.11", + "wfn": { + "Part": "a", + "Vendor": "npmjs", + "Product": "npm", + "Version": "1.2.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:maximo_for_aviation:7.6.1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:maximo_for_aviation:7.6.1.0", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "maximo_for_aviation", + "Version": "7.6.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:infinispan:infinispan:12.0.0:dev07:*:*:*:*:*:*", + "cpe-url": "cpe:/a:infinispan:infinispan:12.0.0:dev07", + "wfn": { + "Part": "a", + "Vendor": "infinispan", + "Product": "infinispan", + "Version": "12.0.0", + "Update": "dev07", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:exponentcms:exponent_cms:2.3.5:patch2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:exponentcms:exponent_cms:2.3.5:patch2", + "wfn": { + "Part": "a", + "Vendor": "exponentcms", + "Product": "exponent_cms", + "Version": "2.3.5", + "Update": "patch2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:puppet:facter:3.1.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:puppet:facter:3.1.7", + "wfn": { + "Part": "a", + "Vendor": "puppet", + "Product": "facter", + "Version": "3.1.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:boot2docker:boot2docker:17.11.0:rc2:*:*:community:*:*:*", + "cpe-url": "cpe:/o:boot2docker:boot2docker:17.11.0:rc2:~~community~~~", + "wfn": { + "Part": "o", + "Vendor": "boot2docker", + "Product": "boot2docker", + "Version": "17.11.0", + "Update": "rc2", + "Edition": "", + "Language": "", + "SwEdition": "community", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:flask-appbuilder_project:flask-appbuilder:1.9.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:flask-appbuilder_project:flask-appbuilder:1.9.4", + "wfn": { + "Part": "a", + "Vendor": "flask-appbuilder_project", + "Product": "flask-appbuilder", + "Version": "1.9.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:samsung:tizenrt:3.0:gbb:*:*:*:*:*:*", + "cpe-url": "cpe:/o:samsung:tizenrt:3.0:gbb", + "wfn": { + "Part": "o", + "Vendor": "samsung", + "Product": "tizenrt", + "Version": "3.0", + "Update": "gbb", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bit_project:bit:0.6.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bit_project:bit:0.6.2", + "wfn": { + "Part": "a", + "Vendor": "bit_project", + "Product": "bit", + "Version": "0.6.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.3.300:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.3.300", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.3.300", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:isc:dhcp:4.1-esv:r8_rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:isc:dhcp:4.1-esv:r8_rc1", + "wfn": { + "Part": "a", + "Vendor": "isc", + "Product": "dhcp", + "Version": "4.1-esv", + "Update": "r8_rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:bosh_cli:0.0.95:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:bosh_cli:0.0.95", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "bosh_cli", + "Version": "0.0.95", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fortinet:fortimail:5.1.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:fortinet:fortimail:5.1.1", + "wfn": { + "Part": "a", + "Vendor": "fortinet", + "Product": "fortimail", + "Version": "5.1.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlassian:bitbucket:4.14.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:atlassian:bitbucket:4.14.9", + "wfn": { + "Part": "a", + "Vendor": "atlassian", + "Product": "bitbucket", + "Version": "4.14.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:libnl_project:libnl:3.2.21:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:libnl_project:libnl:3.2.21", + "wfn": { + "Part": "a", + "Vendor": "libnl_project", + "Product": "libnl", + "Version": "3.2.21", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:livezilla:livezilla:7.0.2.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:livezilla:livezilla:7.0.2.9", + "wfn": { + "Part": "a", + "Vendor": "livezilla", + "Product": "livezilla", + "Version": "7.0.2.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gwolle_guestbook_project:gwolle_guestbook:2.5.2:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:gwolle_guestbook_project:gwolle_guestbook:2.5.2::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "gwolle_guestbook_project", + "Product": "gwolle_guestbook", + "Version": "2.5.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:microsoft:visual_studio_2019:8.1:*:*:*:*:macos:*:*", + "cpe-url": "cpe:/a:microsoft:visual_studio_2019:8.1::~~~macos~~", + "wfn": { + "Part": "a", + "Vendor": "microsoft", + "Product": "visual_studio_2019", + "Version": "8.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "macos", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:linux:acrn:2018w30.2-140000p:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:linux:acrn:2018w30.2-140000p", + "wfn": { + "Part": "o", + "Vendor": "linux", + "Product": "acrn", + "Version": "2018w30.2-140000p", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:herry:sfpagent:0.4.9:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:herry:sfpagent:0.4.9::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "herry", + "Product": "sfpagent", + "Version": "0.4.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wedevs:happy_addons_for_elementor:2.21.0:*:*:*:-:wordpress:*:*", + "cpe-url": "cpe:/a:wedevs:happy_addons_for_elementor:2.21.0::~~-~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wedevs", + "Product": "happy_addons_for_elementor", + "Version": "2.21.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "-", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:iij:seil_b1_firmware:3.26:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:iij:seil_b1_firmware:3.26", + "wfn": { + "Part": "o", + "Vendor": "iij", + "Product": "seil_b1_firmware", + "Version": "3.26", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mechanize_project:mechanize:0.8.3:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:mechanize_project:mechanize:0.8.3::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "mechanize_project", + "Product": "mechanize", + "Version": "0.8.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:digium:certified_asterisk:1.2.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:digium:certified_asterisk:1.2.7", + "wfn": { + "Part": "a", + "Vendor": "digium", + "Product": "certified_asterisk", + "Version": "1.2.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:dell:vostro_5401:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:dell:vostro_5401:-", + "wfn": { + "Part": "h", + "Vendor": "dell", + "Product": "vostro_5401", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:canonical:microk8s:1.15.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:canonical:microk8s:1.15.3", + "wfn": { + "Part": "a", + "Vendor": "canonical", + "Product": "microk8s", + "Version": "1.15.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:w3m_project:w3m:0.5.3-34.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:w3m_project:w3m:0.5.3-34.1", + "wfn": { + "Part": "a", + "Vendor": "w3m_project", + "Product": "w3m", + "Version": "0.5.3-34.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wekan_project:wekan:2.59:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wekan_project:wekan:2.59", + "wfn": { + "Part": "a", + "Vendor": "wekan_project", + "Product": "wekan", + "Version": "2.59", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pippinsplugins:featured_comments:1.2.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:pippinsplugins:featured_comments:1.2.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "pippinsplugins", + "Product": "featured_comments", + "Version": "1.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:signal:messenger:3.7.0:*:*:*:*:android:*:*", + "cpe-url": "cpe:/a:signal:messenger:3.7.0::~~~android~~", + "wfn": { + "Part": "a", + "Vendor": "signal", + "Product": "messenger", + "Version": "3.7.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "android", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:youtube_embed_project:youtube_embed:5.2:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:youtube_embed_project:youtube_embed:5.2::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "youtube_embed_project", + "Product": "youtube_embed", + "Version": "5.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:camunda:modeler:4.6.0:rc0:*:*:*:*:*:*", + "cpe-url": "cpe:/a:camunda:modeler:4.6.0:rc0", + "wfn": { + "Part": "a", + "Vendor": "camunda", + "Product": "modeler", + "Version": "4.6.0", + "Update": "rc0", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:beanshell:beanshell:1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:beanshell:beanshell:1.0", + "wfn": { + "Part": "a", + "Vendor": "beanshell", + "Product": "beanshell", + "Version": "1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:infolific:ultimate_category_excluder:0.2:beta:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:infolific:ultimate_category_excluder:0.2:beta:~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "infolific", + "Product": "ultimate_category_excluder", + "Version": "0.2", + "Update": "beta", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:isc:bind:9.7.1:rc1:*:*:-:*:*:*", + "cpe-url": "cpe:/a:isc:bind:9.7.1:rc1:~~-~~~", + "wfn": { + "Part": "a", + "Vendor": "isc", + "Product": "bind", + "Version": "9.7.1", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "-", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:shapeshift:keepkey_firmware:5.2.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:shapeshift:keepkey_firmware:5.2.2", + "wfn": { + "Part": "o", + "Vendor": "shapeshift", + "Product": "keepkey_firmware", + "Version": "5.2.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:puppet:puppet:3.7.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:puppet:puppet:3.7.2", + "wfn": { + "Part": "a", + "Vendor": "puppet", + "Product": "puppet", + "Version": "3.7.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sangoma:freepbx:13.0.119.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sangoma:freepbx:13.0.119.2", + "wfn": { + "Part": "a", + "Vendor": "sangoma", + "Product": "freepbx", + "Version": "13.0.119.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:phpunit_project:phpunit:3.2.20:*:*:*:*:-:*:*", + "cpe-url": "cpe:/a:phpunit_project:phpunit:3.2.20::~~~-~~", + "wfn": { + "Part": "a", + "Vendor": "phpunit_project", + "Product": "phpunit", + "Version": "3.2.20", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "-", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:http.rb_project:http.rb:0.8.9:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:http.rb_project:http.rb:0.8.9::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "http.rb_project", + "Product": "http.rb", + "Version": "0.8.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:verbb:image_resizer:0.0.2:*:*:*:*:craft_cms:*:*", + "cpe-url": "cpe:/a:verbb:image_resizer:0.0.2::~~~craft_cms~~", + "wfn": { + "Part": "a", + "Vendor": "verbb", + "Product": "image_resizer", + "Version": "0.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "craft_cms", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:minecraft:minecraft:1.17:*:*:*:java:*:*:*", + "cpe-url": "cpe:/a:minecraft:minecraft:1.17::~~java~~~", + "wfn": { + "Part": "a", + "Vendor": "minecraft", + "Product": "minecraft", + "Version": "1.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "java", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ip_conference_phone_7832_firmware:12.5\\(1\\)sr2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ip_conference_phone_7832_firmware:12.5%281%29sr2", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ip_conference_phone_7832_firmware", + "Version": "12.5(1)sr2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpmobilepack:wordpress_mobile_pack:2.1.5:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpmobilepack:wordpress_mobile_pack:2.1.5::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpmobilepack", + "Product": "wordpress_mobile_pack", + "Version": "2.1.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:abus:secvest_wireless_remote_control_fube50015_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:abus:secvest_wireless_remote_control_fube50015_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "abus", + "Product": "secvest_wireless_remote_control_fube50015_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnu:mailman:2.1.14-1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnu:mailman:2.1.14-1", + "wfn": { + "Part": "a", + "Vendor": "gnu", + "Product": "mailman", + "Version": "2.1.14-1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:inedo:otter:1.5.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:inedo:otter:1.5.1", + "wfn": { + "Part": "a", + "Vendor": "inedo", + "Product": "otter", + "Version": "1.5.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:10web:photo_gallery:1.2.82:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:10web:photo_gallery:1.2.82::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "10web", + "Product": "photo_gallery", + "Version": "1.2.82", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nodejs:node.js:9.5.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nodejs:node.js:9.5.0", + "wfn": { + "Part": "a", + "Vendor": "nodejs", + "Product": "node.js", + "Version": "9.5.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:the-guild:graphql-tools:0.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:the-guild:graphql-tools:0.4.0", + "wfn": { + "Part": "a", + "Vendor": "the-guild", + "Product": "graphql-tools", + "Version": "0.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jetbrains:kotlin:1.4.0:dev250:*:*:*:*:*:*", + "cpe-url": "cpe:/a:jetbrains:kotlin:1.4.0:dev250", + "wfn": { + "Part": "a", + "Vendor": "jetbrains", + "Product": "kotlin", + "Version": "1.4.0", + "Update": "dev250", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:restafary_project:restafary:1.6.4:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:restafary_project:restafary:1.6.4::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "restafary_project", + "Product": "restafary", + "Version": "1.6.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpshopstyling:wp-ecommerce-shop-styling:1.4:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpshopstyling:wp-ecommerce-shop-styling:1.4::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpshopstyling", + "Product": "wp-ecommerce-shop-styling", + "Version": "1.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:buttle_project:buttle:0.0.4:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:buttle_project:buttle:0.0.4::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "buttle_project", + "Product": "buttle", + "Version": "0.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ueberhamm-design:youtube_video_inserter:1.2.0.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:ueberhamm-design:youtube_video_inserter:1.2.0.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "ueberhamm-design", + "Product": "youtube_video_inserter", + "Version": "1.2.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:asr_5000_software:18.1_base:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:asr_5000_software:18.1_base", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "asr_5000_software", + "Version": "18.1_base", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:quagga:quagga:0.99.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:quagga:quagga:0.99.1", + "wfn": { + "Part": "a", + "Vendor": "quagga", + "Product": "quagga", + "Version": "0.99.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cognitoys:stemosaur_firmware:0.0.794:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cognitoys:stemosaur_firmware:0.0.794", + "wfn": { + "Part": "o", + "Vendor": "cognitoys", + "Product": "stemosaur_firmware", + "Version": "0.0.794", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pagerduty:rundeck:3.4.3:rc2:*:*:community:*:*:*", + "cpe-url": "cpe:/a:pagerduty:rundeck:3.4.3:rc2:~~community~~~", + "wfn": { + "Part": "a", + "Vendor": "pagerduty", + "Product": "rundeck", + "Version": "3.4.3", + "Update": "rc2", + "Edition": "", + "Language": "", + "SwEdition": "community", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloudfoundry:cf-deployment:7.10.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cloudfoundry:cf-deployment:7.10.0", + "wfn": { + "Part": "a", + "Vendor": "cloudfoundry", + "Product": "cf-deployment", + "Version": "7.10.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:litespeedtech:litespeed_cache:2.9.7.2:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:litespeedtech:litespeed_cache:2.9.7.2::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "litespeedtech", + "Product": "litespeed_cache", + "Version": "2.9.7.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:netflix:priam:3.11.33:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:netflix:priam:3.11.33", + "wfn": { + "Part": "a", + "Vendor": "netflix", + "Product": "priam", + "Version": "3.11.33", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:8.0.0086:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:8.0.0086", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "8.0.0086", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bolt:bolt_cms:3.3.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bolt:bolt_cms:3.3.4", + "wfn": { + "Part": "a", + "Vendor": "bolt", + "Product": "bolt_cms", + "Version": "3.3.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:synacor:zimbra_collaboration_suite:8.8.8:patch10:*:*:*:*:*:*", + "cpe-url": "cpe:/a:synacor:zimbra_collaboration_suite:8.8.8:patch10", + "wfn": { + "Part": "a", + "Vendor": "synacor", + "Product": "zimbra_collaboration_suite", + "Version": "8.8.8", + "Update": "patch10", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:credhub-release:2.5.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:credhub-release:2.5.2", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "credhub-release", + "Version": "2.5.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gluster:glusterfs:3.5.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gluster:glusterfs:3.5.6", + "wfn": { + "Part": "a", + "Vendor": "gluster", + "Product": "glusterfs", + "Version": "3.5.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnome:glib:2.27.92:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnome:glib:2.27.92", + "wfn": { + "Part": "a", + "Vendor": "gnome", + "Product": "glib", + "Version": "2.27.92", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rom_walton:boinc:7.0.67:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:rom_walton:boinc:7.0.67", + "wfn": { + "Part": "a", + "Vendor": "rom_walton", + "Product": "boinc", + "Version": "7.0.67", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:geode:1.2.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:geode:1.2.0", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "geode", + "Version": "1.2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:online_bus_booking_system_project:online_bus_booking_system:1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:online_bus_booking_system_project:online_bus_booking_system:1.0", + "wfn": { + "Part": "a", + "Vendor": "online_bus_booking_system_project", + "Product": "online_bus_booking_system", + "Version": "1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:jspwiki:2.9.0:incubating_rc4:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:jspwiki:2.9.0:incubating_rc4", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "jspwiki", + "Version": "2.9.0", + "Update": "incubating_rc4", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:z.cash:zcash:1.0.0:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:z.cash:zcash:1.0.0:rc1", + "wfn": { + "Part": "a", + "Vendor": "z.cash", + "Product": "zcash", + "Version": "1.0.0", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:cloud_foundry:221:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:cloud_foundry:221", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "cloud_foundry", + "Version": "221", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ays-pro:quiz_maker:6.2.1.8:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:ays-pro:quiz_maker:6.2.1.8::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "ays-pro", + "Product": "quiz_maker", + "Version": "6.2.1.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:torproject:tor_browser:7.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:torproject:tor_browser:7.5", + "wfn": { + "Part": "a", + "Vendor": "torproject", + "Product": "tor_browser", + "Version": "7.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:revive-adserver:revive_adserver:3.0.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:revive-adserver:revive_adserver:3.0.2", + "wfn": { + "Part": "a", + "Vendor": "revive-adserver", + "Product": "revive_adserver", + "Version": "3.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:opennms:meridian:2019.1.14-1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:opennms:meridian:2019.1.14-1", + "wfn": { + "Part": "a", + "Vendor": "opennms", + "Product": "meridian", + "Version": "2019.1.14-1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bitcoincore:bitcoin_core:0.7.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bitcoincore:bitcoin_core:0.7.2", + "wfn": { + "Part": "a", + "Vendor": "bitcoincore", + "Product": "bitcoin_core", + "Version": "0.7.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:aws_elastic_beanstalk_publisher:1.4.1:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:aws_elastic_beanstalk_publisher:1.4.1::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "aws_elastic_beanstalk_publisher", + "Version": "1.4.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpml:wpml:2.6.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpml:wpml:2.6.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpml", + "Product": "wpml", + "Version": "2.6.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:saasproject:booking_package:1.2.72:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:saasproject:booking_package:1.2.72::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "saasproject", + "Product": "booking_package", + "Version": "1.2.72", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rsvpmaker_project:rsvpmaker:0.7.4:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:rsvpmaker_project:rsvpmaker:0.7.4::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "rsvpmaker_project", + "Product": "rsvpmaker", + "Version": "0.7.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloudfoundry:credhub:1.3.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cloudfoundry:credhub:1.3.7", + "wfn": { + "Part": "a", + "Vendor": "cloudfoundry", + "Product": "credhub", + "Version": "1.3.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:horde:horde_prefs:2.1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:horde:horde_prefs:2.1.0", + "wfn": { + "Part": "a", + "Vendor": "horde", + "Product": "horde_prefs", + "Version": "2.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:linux:linux_kernel:2.6.5:rc3:*:*:*:*:*:*", + "cpe-url": "cpe:/o:linux:linux_kernel:2.6.5:rc3", + "wfn": { + "Part": "o", + "Vendor": "linux", + "Product": "linux_kernel", + "Version": "2.6.5", + "Update": "rc3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:restsharp:restsharp:106.6.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:restsharp:restsharp:106.6.5", + "wfn": { + "Part": "a", + "Vendor": "restsharp", + "Product": "restsharp", + "Version": "106.6.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:lenovo:thinkagile_7y12:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:lenovo:thinkagile_7y12:-", + "wfn": { + "Part": "h", + "Vendor": "lenovo", + "Product": "thinkagile_7y12", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hashicorp:vault:0.8.0:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hashicorp:vault:0.8.0:rc1", + "wfn": { + "Part": "a", + "Vendor": "hashicorp", + "Product": "vault", + "Version": "0.8.0", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wppopupmaker:popup_maker:1.5.3:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wppopupmaker:popup_maker:1.5.3::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wppopupmaker", + "Product": "popup_maker", + "Version": "1.5.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:netgear:r6020_firmware:1.0.0.48:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:netgear:r6020_firmware:1.0.0.48", + "wfn": { + "Part": "o", + "Vendor": "netgear", + "Product": "r6020_firmware", + "Version": "1.0.0.48", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:verdaccio:verdaccio:0.1.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:verdaccio:verdaccio:0.1.1", + "wfn": { + "Part": "a", + "Vendor": "verdaccio", + "Product": "verdaccio", + "Version": "0.1.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:nvidia:quadro_m3000m:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:nvidia:quadro_m3000m:-", + "wfn": { + "Part": "h", + "Vendor": "nvidia", + "Product": "quadro_m3000m", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:intel:s2600cwt_firmware:01.01.0029:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:intel:s2600cwt_firmware:01.01.0029", + "wfn": { + "Part": "o", + "Vendor": "intel", + "Product": "s2600cwt_firmware", + "Version": "01.01.0029", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:linuxfoundation:jaeger:1.7.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:linuxfoundation:jaeger:1.7.0", + "wfn": { + "Part": "a", + "Vendor": "linuxfoundation", + "Product": "jaeger", + "Version": "1.7.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:brainstormforce:starter_templates:1.2.6:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:brainstormforce:starter_templates:1.2.6::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "brainstormforce", + "Product": "starter_templates", + "Version": "1.2.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:oisf:suricata:2.0.1:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:oisf:suricata:2.0.1:rc1", + "wfn": { + "Part": "a", + "Vendor": "oisf", + "Product": "suricata", + "Version": "2.0.1", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:inedo:buildmaster:5.0.10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:inedo:buildmaster:5.0.10", + "wfn": { + "Part": "a", + "Vendor": "inedo", + "Product": "buildmaster", + "Version": "5.0.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:typelevel:http4s:0.16.0:milestone2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:typelevel:http4s:0.16.0:milestone2", + "wfn": { + "Part": "a", + "Vendor": "typelevel", + "Product": "http4s", + "Version": "0.16.0", + "Update": "milestone2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vovsoft:vov_sticky_notes:6.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vovsoft:vov_sticky_notes:6.1", + "wfn": { + "Part": "a", + "Vendor": "vovsoft", + "Product": "vov_sticky_notes", + "Version": "6.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bitnami:containers:7.6.0-debian-10-r38:*:*:*:*:laravel:*:*", + "cpe-url": "cpe:/a:bitnami:containers:7.6.0-debian-10-r38::~~~laravel~~", + "wfn": { + "Part": "a", + "Vendor": "bitnami", + "Product": "containers", + "Version": "7.6.0-debian-10-r38", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "laravel", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnome:glib:2.6.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnome:glib:2.6.4", + "wfn": { + "Part": "a", + "Vendor": "gnome", + "Product": "glib", + "Version": "2.6.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:schedmd:slurm:18.08.0.0:pre1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:schedmd:slurm:18.08.0.0:pre1", + "wfn": { + "Part": "a", + "Vendor": "schedmd", + "Product": "slurm", + "Version": "18.08.0.0", + "Update": "pre1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:chrome:29.0.1547.31:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:chrome:29.0.1547.31", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "chrome", + "Version": "29.0.1547.31", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:8.0.1502:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:8.0.1502", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "8.0.1502", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:weekly_schedule_project:weekly_schedule:2.2.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:weekly_schedule_project:weekly_schedule:2.2.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "weekly_schedule_project", + "Product": "weekly_schedule", + "Version": "2.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:websphere_commerce:8.0.4.10:*:*:*:professional:*:*:*", + "cpe-url": "cpe:/a:ibm:websphere_commerce:8.0.4.10::~~professional~~~", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "websphere_commerce", + "Version": "8.0.4.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "professional", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:chef:chef:15.4.61:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:chef:chef:15.4.61", + "wfn": { + "Part": "a", + "Vendor": "chef", + "Product": "chef", + "Version": "15.4.61", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redhat:bodhi:2.1.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redhat:bodhi:2.1.2", + "wfn": { + "Part": "a", + "Vendor": "redhat", + "Product": "bodhi", + "Version": "2.1.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cartpauj:mingle-forum:1.0.18:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cartpauj:mingle-forum:1.0.18", + "wfn": { + "Part": "a", + "Vendor": "cartpauj", + "Product": "mingle-forum", + "Version": "1.0.18", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wclovers:frontend_manager_for_woocommerce_along_with_bookings_subscription_listings_compatible:2.0.5:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wclovers:frontend_manager_for_woocommerce_along_with_bookings_subscription_listings_compatible:2.0.5::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wclovers", + "Product": "frontend_manager_for_woocommerce_along_with_bookings_subscription_listings_compatible", + "Version": "2.0.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tryton:trytond:3.6.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tryton:trytond:3.6.11", + "wfn": { + "Part": "a", + "Vendor": "tryton", + "Product": "trytond", + "Version": "3.6.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cmsmadesimple:form_builder:0.6b1:*:*:*:*:cms_made_simple:*:*", + "cpe-url": "cpe:/a:cmsmadesimple:form_builder:0.6b1::~~~cms_made_simple~~", + "wfn": { + "Part": "a", + "Vendor": "cmsmadesimple", + "Product": "form_builder", + "Version": "0.6b1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "cms_made_simple", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ios:15.2\\(4\\)jb6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ios:15.2%284%29jb6", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ios", + "Version": "15.2(4)jb6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ldap_\\/_sso_authentication_project:ldap_\\/_sso_authentication:3.2.1:*:*:*:*:typo3:*:*", + "cpe-url": "cpe:/a:ldap_%2f_sso_authentication_project:ldap_%2f_sso_authentication:3.2.1::~~~typo3~~", + "wfn": { + "Part": "a", + "Vendor": "ldap_/_sso_authentication_project", + "Product": "ldap_/_sso_authentication", + "Version": "3.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "typo3", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:adaltas:printf:0.2.3:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:adaltas:printf:0.2.3::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "adaltas", + "Product": "printf", + "Version": "0.2.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:raitan:commandcenter_secure_gateway:5.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:raitan:commandcenter_secure_gateway:5.4.0", + "wfn": { + "Part": "a", + "Vendor": "raitan", + "Product": "commandcenter_secure_gateway", + "Version": "5.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:adobe:acrobat:9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:adobe:acrobat:9", + "wfn": { + "Part": "a", + "Vendor": "adobe", + "Product": "acrobat", + "Version": "9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:klibc_project:klibc:0.172:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:klibc_project:klibc:0.172", + "wfn": { + "Part": "a", + "Vendor": "klibc_project", + "Product": "klibc", + "Version": "0.172", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:luke_herrington:stickynote:7.x-1.x:dev:*:*:*:*:*:*", + "cpe-url": "cpe:/a:luke_herrington:stickynote:7.x-1.x:dev", + "wfn": { + "Part": "a", + "Vendor": "luke_herrington", + "Product": "stickynote", + "Version": "7.x-1.x", + "Update": "dev", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:oppia:oppia:2.6.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:oppia:oppia:2.6.7", + "wfn": { + "Part": "a", + "Vendor": "oppia", + "Product": "oppia", + "Version": "2.6.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:abb:800xa_system:6.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:abb:800xa_system:6.0.1", + "wfn": { + "Part": "a", + "Vendor": "abb", + "Product": "800xa_system", + "Version": "6.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ios:12.2\\(2\\)xb9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ios:12.2%282%29xb9", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ios", + "Version": "12.2(2)xb9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:perl:dbi:0.92:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:perl:dbi:0.92", + "wfn": { + "Part": "a", + "Vendor": "perl", + "Product": "dbi", + "Version": "0.92", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:cordova:1.0.0:rc1:*:*:*:android:*:*", + "cpe-url": "cpe:/a:apache:cordova:1.0.0:rc1:~~~android~~", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "cordova", + "Version": "1.0.0", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "android", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:contiki-os:contiki:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:contiki-os:contiki:-", + "wfn": { + "Part": "o", + "Vendor": "contiki-os", + "Product": "contiki", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:owncloud:owncloud_desktop_client:2.2.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:owncloud:owncloud_desktop_client:2.2.4", + "wfn": { + "Part": "a", + "Vendor": "owncloud", + "Product": "owncloud_desktop_client", + "Version": "2.2.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:microsoft:windows_2000:-:sp2:*:*:server:*:*:*", + "cpe-url": "cpe:/o:microsoft:windows_2000:-:sp2:~~server~~~", + "wfn": { + "Part": "o", + "Vendor": "microsoft", + "Product": "windows_2000", + "Version": "-", + "Update": "sp2", + "Edition": "", + "Language": "", + "SwEdition": "server", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:simple-membership-plugin:simple_membership:1.8.4:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:simple-membership-plugin:simple_membership:1.8.4::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "simple-membership-plugin", + "Product": "simple_membership", + "Version": "1.8.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:f8b04a:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:f8b04a:-", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "f8b04a", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:netsweeper:netsweeper:4.1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:netsweeper:netsweeper:4.1.0", + "wfn": { + "Part": "a", + "Vendor": "netsweeper", + "Product": "netsweeper", + "Version": "4.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.3.529:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.3.529", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.3.529", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sqlalchemy:sqlalchemy:0.9.10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sqlalchemy:sqlalchemy:0.9.10", + "wfn": { + "Part": "a", + "Vendor": "sqlalchemy", + "Product": "sqlalchemy", + "Version": "0.9.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ctfd:ctfd:2.2.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ctfd:ctfd:2.2.2", + "wfn": { + "Part": "a", + "Vendor": "ctfd", + "Product": "ctfd", + "Version": "2.2.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.4.447:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.4.447", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.4.447", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:iodata:hdl2-a_firmware:1.07:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:iodata:hdl2-a_firmware:1.07", + "wfn": { + "Part": "o", + "Vendor": "iodata", + "Product": "hdl2-a_firmware", + "Version": "1.07", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:intel:xeon_e5-1630_v3:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:intel:xeon_e5-1630_v3:-", + "wfn": { + "Part": "h", + "Vendor": "intel", + "Product": "xeon_e5-1630_v3", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:cloud_foundry_uaa_bosh:24.10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:cloud_foundry_uaa_bosh:24.10", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "cloud_foundry_uaa_bosh", + "Version": "24.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:netflix:hollow:2.4.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:netflix:hollow:2.4.2", + "wfn": { + "Part": "a", + "Vendor": "netflix", + "Product": "hollow", + "Version": "2.4.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:webmin:usermin:1.770:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:webmin:usermin:1.770", + "wfn": { + "Part": "a", + "Vendor": "webmin", + "Product": "usermin", + "Version": "1.770", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:recon-ng_project:recon-ng:3.4.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:recon-ng_project:recon-ng:3.4.1", + "wfn": { + "Part": "a", + "Vendor": "recon-ng_project", + "Product": "recon-ng", + "Version": "3.4.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:spinnaker:orca:0.439:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:spinnaker:orca:0.439", + "wfn": { + "Part": "a", + "Vendor": "spinnaker", + "Product": "orca", + "Version": "0.439", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:r-consortium:rmysql:0.10.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:r-consortium:rmysql:0.10.9", + "wfn": { + "Part": "a", + "Vendor": "r-consortium", + "Product": "rmysql", + "Version": "0.10.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wekan_project:wekan:4.12:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wekan_project:wekan:4.12", + "wfn": { + "Part": "a", + "Vendor": "wekan_project", + "Product": "wekan", + "Version": "4.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:phpmyadmin:phpmyadmin:1.2.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:phpmyadmin:phpmyadmin:1.2.4", + "wfn": { + "Part": "a", + "Vendor": "phpmyadmin", + "Product": "phpmyadmin", + "Version": "1.2.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zmanda:amanda:2.5.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:zmanda:amanda:2.5.1", + "wfn": { + "Part": "a", + "Vendor": "zmanda", + "Product": "amanda", + "Version": "2.5.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:ips_sensor_software:5.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:ips_sensor_software:5.0", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "ips_sensor_software", + "Version": "5.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:koha:koha:16.05.00:beta:*:*:*:*:*:*", + "cpe-url": "cpe:/a:koha:koha:16.05.00:beta", + "wfn": { + "Part": "a", + "Vendor": "koha", + "Product": "koha", + "Version": "16.05.00", + "Update": "beta", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pizzashack:rssh:2.0.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pizzashack:rssh:2.0.2", + "wfn": { + "Part": "a", + "Vendor": "pizzashack", + "Product": "rssh", + "Version": "2.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:elastic:kibana_x-pack:5.4.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:elastic:kibana_x-pack:5.4.3", + "wfn": { + "Part": "a", + "Vendor": "elastic", + "Product": "kibana_x-pack", + "Version": "5.4.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:dropbox:dropbox:72.2:*:*:*:*:iphone_os:*:*", + "cpe-url": "cpe:/a:dropbox:dropbox:72.2::~~~iphone_os~~", + "wfn": { + "Part": "a", + "Vendor": "dropbox", + "Product": "dropbox", + "Version": "72.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "iphone_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hygeia_project:hygeia:1.0.2:beta1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hygeia_project:hygeia:1.0.2:beta1", + "wfn": { + "Part": "a", + "Vendor": "hygeia_project", + "Product": "hygeia", + "Version": "1.0.2", + "Update": "beta1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ios:12.3\\(8\\)jea:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ios:12.3%288%29jea", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ios", + "Version": "12.3(8)jea", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:quizandsurveymaster:quiz_and_survey_master:4.4.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:quizandsurveymaster:quiz_and_survey_master:4.4.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "quizandsurveymaster", + "Product": "quiz_and_survey_master", + "Version": "4.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:denx:u-boot:1.1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:denx:u-boot:1.1.0", + "wfn": { + "Part": "a", + "Vendor": "denx", + "Product": "u-boot", + "Version": "1.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:8.1.2374:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:8.1.2374", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "8.1.2374", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:avaya:aura_communication_manager:7.1.3.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:avaya:aura_communication_manager:7.1.3.5", + "wfn": { + "Part": "a", + "Vendor": "avaya", + "Product": "aura_communication_manager", + "Version": "7.1.3.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:huawei:secospace_usg6600_firmware:v500r001c00spc050:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:huawei:secospace_usg6600_firmware:v500r001c00spc050", + "wfn": { + "Part": "o", + "Vendor": "huawei", + "Product": "secospace_usg6600_firmware", + "Version": "v500r001c00spc050", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kiboit:phastpress:1.49:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:kiboit:phastpress:1.49::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "kiboit", + "Product": "phastpress", + "Version": "1.49", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vercel:next.js:1.0.0:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:vercel:next.js:1.0.0::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "vercel", + "Product": "next.js", + "Version": "1.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:scala-lang:scala:2.13.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:scala-lang:scala:2.13.0:-", + "wfn": { + "Part": "a", + "Vendor": "scala-lang", + "Product": "scala", + "Version": "2.13.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:agilebits:knox:2.1.9:-:*:*:*:mac_os_x:*:*", + "cpe-url": "cpe:/a:agilebits:knox:2.1.9:-:~~~mac_os_x~~", + "wfn": { + "Part": "a", + "Vendor": "agilebits", + "Product": "knox", + "Version": "2.1.9", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "mac_os_x", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sqreen:php_microagent:1.9.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sqreen:php_microagent:1.9.2", + "wfn": { + "Part": "a", + "Vendor": "sqreen", + "Product": "php_microagent", + "Version": "1.9.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:h5ai_project:h5ai:0.12:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:h5ai_project:h5ai:0.12", + "wfn": { + "Part": "a", + "Vendor": "h5ai_project", + "Product": "h5ai", + "Version": "0.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:weechat:weechat:3.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:weechat:weechat:3.0.1", + "wfn": { + "Part": "a", + "Vendor": "weechat", + "Product": "weechat", + "Version": "3.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:rabbitmq:1.9.8:*:*:*:*:pivotal_cloud_foundry:*:*", + "cpe-url": "cpe:/a:pivotal_software:rabbitmq:1.9.8::~~~pivotal_cloud_foundry~~", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "rabbitmq", + "Version": "1.9.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "pivotal_cloud_foundry", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ios:12.1eu:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ios:12.1eu", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ios", + "Version": "12.1eu", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ntp:ntp:4.2.7:p349:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ntp:ntp:4.2.7:p349", + "wfn": { + "Part": "a", + "Vendor": "ntp", + "Product": "ntp", + "Version": "4.2.7", + "Update": "p349", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mariadb:mariadb:10.2.26:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mariadb:mariadb:10.2.26", + "wfn": { + "Part": "a", + "Vendor": "mariadb", + "Product": "mariadb", + "Version": "10.2.26", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloudbees:jenkins:1.424.1:-:lts:*:*:*:*:*", + "cpe-url": "cpe:/a:cloudbees:jenkins:1.424.1:-:lts", + "wfn": { + "Part": "a", + "Vendor": "cloudbees", + "Product": "jenkins", + "Version": "1.424.1", + "Update": "-", + "Edition": "lts", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:colossusxt:colossuscoinxt:0.3.23:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:colossusxt:colossuscoinxt:0.3.23:rc1", + "wfn": { + "Part": "a", + "Vendor": "colossusxt", + "Product": "colossuscoinxt", + "Version": "0.3.23", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fortinet:fortianalyzer:6.4.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:fortinet:fortianalyzer:6.4.1", + "wfn": { + "Part": "a", + "Vendor": "fortinet", + "Product": "fortianalyzer", + "Version": "6.4.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gaku:tablacus_explorer:17.6.15:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gaku:tablacus_explorer:17.6.15", + "wfn": { + "Part": "a", + "Vendor": "gaku", + "Product": "tablacus_explorer", + "Version": "17.6.15", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:netsweeper:netsweeper:6.3.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:netsweeper:netsweeper:6.3.5", + "wfn": { + "Part": "a", + "Vendor": "netsweeper", + "Product": "netsweeper", + "Version": "6.3.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:chrome:18.0.1006.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:chrome:18.0.1006.0", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "chrome", + "Version": "18.0.1006.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:linuxfoundation:containerd:1.0.1:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:linuxfoundation:containerd:1.0.1:-", + "wfn": { + "Part": "a", + "Vendor": "linuxfoundation", + "Product": "containerd", + "Version": "1.0.1", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:convert\\:\\:asn1_project:convert\\:\\:asn1:0.27:*:*:*:*:perl:*:*", + "cpe-url": "cpe:/a:convert%3a%3aasn1_project:convert%3a%3aasn1:0.27::~~~perl~~", + "wfn": { + "Part": "a", + "Vendor": "convert::asn1_project", + "Product": "convert::asn1", + "Version": "0.27", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "perl", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sandhillsdev:easy_digital_downloads:2.1.9:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:sandhillsdev:easy_digital_downloads:2.1.9::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "sandhillsdev", + "Product": "easy_digital_downloads", + "Version": "2.1.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ffmpeg:ffmpeg:2.8.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ffmpeg:ffmpeg:2.8.2", + "wfn": { + "Part": "a", + "Vendor": "ffmpeg", + "Product": "ffmpeg", + "Version": "2.8.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:txjia:imcat:3.8:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:txjia:imcat:3.8", + "wfn": { + "Part": "a", + "Vendor": "txjia", + "Product": "imcat", + "Version": "3.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:spiffyplugins:spiffy_calendar:3.4.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:spiffyplugins:spiffy_calendar:3.4.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "spiffyplugins", + "Product": "spiffy_calendar", + "Version": "3.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tryton:trytond:1.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tryton:trytond:1.4.0", + "wfn": { + "Part": "a", + "Vendor": "tryton", + "Product": "trytond", + "Version": "1.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:python:openpyxl:2.1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:python:openpyxl:2.1.0", + "wfn": { + "Part": "a", + "Vendor": "python", + "Product": "openpyxl", + "Version": "2.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:keybase:keybase:1.0.29:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:keybase:keybase:1.0.29", + "wfn": { + "Part": "a", + "Vendor": "keybase", + "Product": "keybase", + "Version": "1.0.29", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mozilla:nss:3.60:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mozilla:nss:3.60", + "wfn": { + "Part": "a", + "Vendor": "mozilla", + "Product": "nss", + "Version": "3.60", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:designmodo:wp_maintenance_mode:1.8.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:designmodo:wp_maintenance_mode:1.8.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "designmodo", + "Product": "wp_maintenance_mode", + "Version": "1.8.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:brave:brave:0.15.314:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:brave:brave:0.15.314", + "wfn": { + "Part": "a", + "Vendor": "brave", + "Product": "brave", + "Version": "0.15.314", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:iij:seil_b1_firmware:3.48:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:iij:seil_b1_firmware:3.48", + "wfn": { + "Part": "o", + "Vendor": "iij", + "Product": "seil_b1_firmware", + "Version": "3.48", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:intel:core_i7:4790s:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:intel:core_i7:4790s", + "wfn": { + "Part": "h", + "Vendor": "intel", + "Product": "core_i7", + "Version": "4790s", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sophos:unified_threat_management_up2date:9.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sophos:unified_threat_management_up2date:9.1", + "wfn": { + "Part": "a", + "Vendor": "sophos", + "Product": "unified_threat_management_up2date", + "Version": "9.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:plainware:hitappoint:6.4.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:plainware:hitappoint:6.4.2", + "wfn": { + "Part": "a", + "Vendor": "plainware", + "Product": "hitappoint", + "Version": "6.4.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zabbix:zabbix:1.8.4:rc2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:zabbix:zabbix:1.8.4:rc2", + "wfn": { + "Part": "a", + "Vendor": "zabbix", + "Product": "zabbix", + "Version": "1.8.4", + "Update": "rc2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:espressif:esp32_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:espressif:esp32_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "espressif", + "Product": "esp32_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:signal:messenger:1.8.2:*:*:*:*:android:*:*", + "cpe-url": "cpe:/a:signal:messenger:1.8.2::~~~android~~", + "wfn": { + "Part": "a", + "Vendor": "signal", + "Product": "messenger", + "Version": "1.8.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "android", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tendermint:tendermint:0.26.0:rc0:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tendermint:tendermint:0.26.0:rc0", + "wfn": { + "Part": "a", + "Vendor": "tendermint", + "Product": "tendermint", + "Version": "0.26.0", + "Update": "rc0", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:brave:brave:1.27.107:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:brave:brave:1.27.107", + "wfn": { + "Part": "a", + "Vendor": "brave", + "Product": "brave", + "Version": "1.27.107", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sumatrapdfreader:sumatrapdf:1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sumatrapdfreader:sumatrapdf:1.0", + "wfn": { + "Part": "a", + "Vendor": "sumatrapdfreader", + "Product": "sumatrapdf", + "Version": "1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:siemens:simatic_ipc647c:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:siemens:simatic_ipc647c:-", + "wfn": { + "Part": "h", + "Vendor": "siemens", + "Product": "simatic_ipc647c", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:codiad:codiad:2.2.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:codiad:codiad:2.2.9", + "wfn": { + "Part": "a", + "Vendor": "codiad", + "Product": "codiad", + "Version": "2.2.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlassian:confluence_data_center:3.5.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:atlassian:confluence_data_center:3.5.11", + "wfn": { + "Part": "a", + "Vendor": "atlassian", + "Product": "confluence_data_center", + "Version": "3.5.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:iptanus:wordpress_file_upload:4.6.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:iptanus:wordpress_file_upload:4.6.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "iptanus", + "Product": "wordpress_file_upload", + "Version": "4.6.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hp:nonstop_netbatch:j06.14.03:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hp:nonstop_netbatch:j06.14.03", + "wfn": { + "Part": "a", + "Vendor": "hp", + "Product": "nonstop_netbatch", + "Version": "j06.14.03", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:8.0.0412:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:8.0.0412", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "8.0.0412", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:emby:emby.releases:3.4.1.20:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:emby:emby.releases:3.4.1.20", + "wfn": { + "Part": "a", + "Vendor": "emby", + "Product": "emby.releases", + "Version": "3.4.1.20", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:brave:brave:1.8.50:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:brave:brave:1.8.50", + "wfn": { + "Part": "a", + "Vendor": "brave", + "Product": "brave", + "Version": "1.8.50", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apollosapp:data-connector-rock:2.3.0:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:apollosapp:data-connector-rock:2.3.0::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "apollosapp", + "Product": "data-connector-rock", + "Version": "2.3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:python:keyring:2.0.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:python:keyring:2.0.3", + "wfn": { + "Part": "a", + "Vendor": "python", + "Product": "keyring", + "Version": "2.0.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sleuthkit:the_sleuth_kit:4.6.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sleuthkit:the_sleuth_kit:4.6.6", + "wfn": { + "Part": "a", + "Vendor": "sleuthkit", + "Product": "the_sleuth_kit", + "Version": "4.6.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:adjam:rekonq:0.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:adjam:rekonq:0.4.0", + "wfn": { + "Part": "a", + "Vendor": "adjam", + "Product": "rekonq", + "Version": "0.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:unified_intelligence_center:11.6\\(1\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:unified_intelligence_center:11.6%281%29", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "unified_intelligence_center", + "Version": "11.6(1)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:chrome:5.0.332.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:chrome:5.0.332.0", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "chrome", + "Version": "5.0.332.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:pipeline_github_notify_step:1.0.5:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:pipeline_github_notify_step:1.0.5::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "pipeline_github_notify_step", + "Version": "1.0.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:netflix:hollow:4.8.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:netflix:hollow:4.8.1", + "wfn": { + "Part": "a", + "Vendor": "netflix", + "Product": "hollow", + "Version": "4.8.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:impress:wp_rollback:1.2.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:impress:wp_rollback:1.2.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "impress", + "Product": "wp_rollback", + "Version": "1.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:concourse:0.6.0:rc21:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:concourse:0.6.0:rc21", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "concourse", + "Version": "0.6.0", + "Update": "rc21", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:nx-os:5.2\\(1\\)sm1\\(5.1\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:nx-os:5.2%281%29sm1%285.1%29", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "nx-os", + "Version": "5.2(1)sm1(5.1)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fortinet:fortiportal:4.2.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:fortinet:fortiportal:4.2.2", + "wfn": { + "Part": "a", + "Vendor": "fortinet", + "Product": "fortiportal", + "Version": "4.2.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:orbital:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:orbital:-", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "orbital", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:symantec:veritas_storage_foundation_for_windows:5.10.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:symantec:veritas_storage_foundation_for_windows:5.10.0", + "wfn": { + "Part": "a", + "Vendor": "symantec", + "Product": "veritas_storage_foundation_for_windows", + "Version": "5.10.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jupyter:notebook:5.1.0:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:jupyter:notebook:5.1.0:rc1", + "wfn": { + "Part": "a", + "Vendor": "jupyter", + "Product": "notebook", + "Version": "5.1.0", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:unity:web_player:4.5.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:unity:web_player:4.5.4", + "wfn": { + "Part": "a", + "Vendor": "unity", + "Product": "web_player", + "Version": "4.5.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:m0p39a:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:m0p39a:-", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "m0p39a", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:knexjs:knex:0.7.5:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:knexjs:knex:0.7.5::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "knexjs", + "Product": "knex", + "Version": "0.7.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mailenable:mailenable:1.18:*:*:*:enterprise:*:*:*", + "cpe-url": "cpe:/a:mailenable:mailenable:1.18::~~enterprise~~~", + "wfn": { + "Part": "a", + "Vendor": "mailenable", + "Product": "mailenable", + "Version": "1.18", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "enterprise", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:btcpayserver:btcpay_server:1.0.2.114:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:btcpayserver:btcpay_server:1.0.2.114", + "wfn": { + "Part": "a", + "Vendor": "btcpayserver", + "Product": "btcpay_server", + "Version": "1.0.2.114", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:incubator_superset:0.34.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:incubator_superset:0.34.0", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "incubator_superset", + "Version": "0.34.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:asset_pipeline_project:asset-pipeline:2.13.0:*:*:*:*:grails:*:*", + "cpe-url": "cpe:/a:asset_pipeline_project:asset-pipeline:2.13.0::~~~grails~~", + "wfn": { + "Part": "a", + "Vendor": "asset_pipeline_project", + "Product": "asset-pipeline", + "Version": "2.13.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "grails", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:flashbackrecorder:flashback:5.23.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:flashbackrecorder:flashback:5.23.0", + "wfn": { + "Part": "a", + "Vendor": "flashbackrecorder", + "Product": "flashback", + "Version": "5.23.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:n9k-c9396tx_firmware:13.2\\(3n\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:n9k-c9396tx_firmware:13.2%283n%29", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "n9k-c9396tx_firmware", + "Version": "13.2(3n)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:flexense:diskboss:6.5:*:*:*:enterprise:*:*:*", + "cpe-url": "cpe:/a:flexense:diskboss:6.5::~~enterprise~~~", + "wfn": { + "Part": "a", + "Vendor": "flexense", + "Product": "diskboss", + "Version": "6.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "enterprise", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:dart:dart_software_development_kit:0.6.21.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:dart:dart_software_development_kit:0.6.21.1", + "wfn": { + "Part": "a", + "Vendor": "dart", + "Product": "dart_software_development_kit", + "Version": "0.6.21.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:activestate:activeperl:5.8.819:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:activestate:activeperl:5.8.819", + "wfn": { + "Part": "a", + "Vendor": "activestate", + "Product": "activeperl", + "Version": "5.8.819", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:aedes_project:aedes:0.13.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:aedes_project:aedes:0.13.1", + "wfn": { + "Part": "a", + "Vendor": "aedes_project", + "Product": "aedes", + "Version": "0.13.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:swoole:swoole_php_framework:1.13.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:swoole:swoole_php_framework:1.13.6", + "wfn": { + "Part": "a", + "Vendor": "swoole", + "Product": "swoole_php_framework", + "Version": "1.13.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:credova:financial:1.4.9:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:credova:financial:1.4.9::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "credova", + "Product": "financial", + "Version": "1.4.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vmware:spring_integration_zip:1.0.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vmware:spring_integration_zip:1.0.0:-", + "wfn": { + "Part": "a", + "Vendor": "vmware", + "Product": "spring_integration_zip", + "Version": "1.0.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nokogiri:nokogiri:1.6.2:beta1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nokogiri:nokogiri:1.6.2:beta1", + "wfn": { + "Part": "a", + "Vendor": "nokogiri", + "Product": "nokogiri", + "Version": "1.6.2", + "Update": "beta1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:multicorewareinc:x265:1.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:multicorewareinc:x265:1.4", + "wfn": { + "Part": "a", + "Vendor": "multicorewareinc", + "Product": "x265", + "Version": "1.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:wago:750-8202:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:wago:750-8202:-", + "wfn": { + "Part": "h", + "Vendor": "wago", + "Product": "750-8202", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:octobercms:october_cms:1.0.228:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:octobercms:october_cms:1.0.228", + "wfn": { + "Part": "a", + "Vendor": "octobercms", + "Product": "october_cms", + "Version": "1.0.228", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:centreon:widget-host-monitoring:19.04.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:centreon:widget-host-monitoring:19.04.5", + "wfn": { + "Part": "a", + "Vendor": "centreon", + "Product": "widget-host-monitoring", + "Version": "19.04.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sonatype:nexus_repository_manager:2.14.15:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sonatype:nexus_repository_manager:2.14.15", + "wfn": { + "Part": "a", + "Vendor": "sonatype", + "Product": "nexus_repository_manager", + "Version": "2.14.15", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ios:12.2\\\\\\(25\\\\\\)seg2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ios:12.2%5c%2825%5c%29seg2", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ios", + "Version": "12.2\\\\(25\\\\)seg2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:eq-3:ccu2_firmware:2.5.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:eq-3:ccu2_firmware:2.5.4", + "wfn": { + "Part": "o", + "Vendor": "eq-3", + "Product": "ccu2_firmware", + "Version": "2.5.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nextcloud:end-to-end_encryption:1.7.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nextcloud:end-to-end_encryption:1.7.0", + "wfn": { + "Part": "a", + "Vendor": "nextcloud", + "Product": "end-to-end_encryption", + "Version": "1.7.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:linuxfoundation:containerd:0.2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:linuxfoundation:containerd:0.2.1", + "wfn": { + "Part": "a", + "Vendor": "linuxfoundation", + "Product": "containerd", + "Version": "0.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wtfutil:wtf:0.0.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wtfutil:wtf:0.0.11", + "wfn": { + "Part": "a", + "Vendor": "wtfutil", + "Product": "wtf", + "Version": "0.0.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:maxthon:maxthon_browser:5.2.3.4000:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:maxthon:maxthon_browser:5.2.3.4000", + "wfn": { + "Part": "a", + "Vendor": "maxthon", + "Product": "maxthon_browser", + "Version": "5.2.3.4000", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fasterxml:jackson-dataformats-binary:2.9.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:fasterxml:jackson-dataformats-binary:2.9.5", + "wfn": { + "Part": "a", + "Vendor": "fasterxml", + "Product": "jackson-dataformats-binary", + "Version": "2.9.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:attachmate:reflection_for_secure_it_client:7.2.1163:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:attachmate:reflection_for_secure_it_client:7.2.1163", + "wfn": { + "Part": "a", + "Vendor": "attachmate", + "Product": "reflection_for_secure_it_client", + "Version": "7.2.1163", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ea:origin_client:10.5.86:*:*:*:*:mac_os:*:*", + "cpe-url": "cpe:/a:ea:origin_client:10.5.86::~~~mac_os~~", + "wfn": { + "Part": "a", + "Vendor": "ea", + "Product": "origin_client", + "Version": "10.5.86", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "mac_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:paloaltonetworks:expedition:1.1.83:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:paloaltonetworks:expedition:1.1.83", + "wfn": { + "Part": "a", + "Vendor": "paloaltonetworks", + "Product": "expedition", + "Version": "1.1.83", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:hp:hp-ux:8.04:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:hp:hp-ux:8.04", + "wfn": { + "Part": "o", + "Vendor": "hp", + "Product": "hp-ux", + "Version": "8.04", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:exposure_notification_verification_server:0.23.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:exposure_notification_verification_server:0.23.0", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "exposure_notification_verification_server", + "Version": "0.23.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:drweb:web_security_space:6.0.0.03100:-:professional:*:*:*:*:*", + "cpe-url": "cpe:/a:drweb:web_security_space:6.0.0.03100:-:professional", + "wfn": { + "Part": "a", + "Vendor": "drweb", + "Product": "web_security_space", + "Version": "6.0.0.03100", + "Update": "-", + "Edition": "professional", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:fortinet:fortiswitch:3.6.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:fortinet:fortiswitch:3.6.6", + "wfn": { + "Part": "o", + "Vendor": "fortinet", + "Product": "fortiswitch", + "Version": "3.6.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kaseya:vsa:9.5.0.20:*:*:*:rmm:*:*:*", + "cpe-url": "cpe:/a:kaseya:vsa:9.5.0.20::~~rmm~~~", + "wfn": { + "Part": "a", + "Vendor": "kaseya", + "Product": "vsa", + "Version": "9.5.0.20", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "rmm", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nghttp2:nghttp2:1.29.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nghttp2:nghttp2:1.29.0", + "wfn": { + "Part": "a", + "Vendor": "nghttp2", + "Product": "nghttp2", + "Version": "1.29.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tcoffee:t-coffee:11.00.8cbe486-1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tcoffee:t-coffee:11.00.8cbe486-1", + "wfn": { + "Part": "a", + "Vendor": "tcoffee", + "Product": "t-coffee", + "Version": "11.00.8cbe486-1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:intel:hns2600bpq24r_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:intel:hns2600bpq24r_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "intel", + "Product": "hns2600bpq24r_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:belden:hirschmann_rsb20-0900mmm2taabe:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:belden:hirschmann_rsb20-0900mmm2taabe:-", + "wfn": { + "Part": "h", + "Vendor": "belden", + "Product": "hirschmann_rsb20-0900mmm2taabe", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:npmjs:tar:4.4.3:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:npmjs:tar:4.4.3::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "npmjs", + "Product": "tar", + "Version": "4.4.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:microchip:atsama5d27c-cnrvao:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:microchip:atsama5d27c-cnrvao:-", + "wfn": { + "Part": "h", + "Vendor": "microchip", + "Product": "atsama5d27c-cnrvao", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tryton:tryton:3.6.13:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tryton:tryton:3.6.13", + "wfn": { + "Part": "a", + "Vendor": "tryton", + "Product": "tryton", + "Version": "3.6.13", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ays-pro:quiz_maker:3.0.8:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:ays-pro:quiz_maker:3.0.8::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "ays-pro", + "Product": "quiz_maker", + "Version": "3.0.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:codeaurora:android-msm:3.12.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:codeaurora:android-msm:3.12.11", + "wfn": { + "Part": "o", + "Vendor": "codeaurora", + "Product": "android-msm", + "Version": "3.12.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tiny.cloud:tinymce:3.4.8:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tiny.cloud:tinymce:3.4.8", + "wfn": { + "Part": "a", + "Vendor": "tiny.cloud", + "Product": "tinymce", + "Version": "3.4.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bracketspace:notification:2.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:bracketspace:notification:2.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "bracketspace", + "Product": "notification", + "Version": "2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:lenovo:thinkpad_e565_bios:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:lenovo:thinkpad_e565_bios:-", + "wfn": { + "Part": "o", + "Vendor": "lenovo", + "Product": "thinkpad_e565_bios", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:spi-inc:ganeti:2.1.0:beta0:*:*:*:*:*:*", + "cpe-url": "cpe:/a:spi-inc:ganeti:2.1.0:beta0", + "wfn": { + "Part": "a", + "Vendor": "spi-inc", + "Product": "ganeti", + "Version": "2.1.0", + "Update": "beta0", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:telegram:telegram_desktop:0.7.12:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:telegram:telegram_desktop:0.7.12", + "wfn": { + "Part": "a", + "Vendor": "telegram", + "Product": "telegram_desktop", + "Version": "0.7.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:encode:uvicorn:0.1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:encode:uvicorn:0.1.0", + "wfn": { + "Part": "a", + "Vendor": "encode", + "Product": "uvicorn", + "Version": "0.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:linux:tizen:4.0:m3:*:*:*:*:*:*", + "cpe-url": "cpe:/o:linux:tizen:4.0:m3", + "wfn": { + "Part": "o", + "Vendor": "linux", + "Product": "tizen", + "Version": "4.0", + "Update": "m3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rancher:rancher:2.5.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:rancher:rancher:2.5.6", + "wfn": { + "Part": "a", + "Vendor": "rancher", + "Product": "rancher", + "Version": "2.5.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:imagemagick:imagemagick:6.9.9-18:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:imagemagick:imagemagick:6.9.9-18", + "wfn": { + "Part": "a", + "Vendor": "imagemagick", + "Product": "imagemagick", + "Version": "6.9.9-18", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hp:system_management_homepage:2.1.3.132:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hp:system_management_homepage:2.1.3.132", + "wfn": { + "Part": "a", + "Vendor": "hp", + "Product": "system_management_homepage", + "Version": "2.1.3.132", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:http_server:2.2.33:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:http_server:2.2.33", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "http_server", + "Version": "2.2.33", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:unity3d:unity_editor:5.5.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:unity3d:unity_editor:5.5.0", + "wfn": { + "Part": "a", + "Vendor": "unity3d", + "Product": "unity_editor", + "Version": "5.5.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:xen-orchestra:xen_orchestra_server:4.3.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:xen-orchestra:xen_orchestra_server:4.3.0", + "wfn": { + "Part": "a", + "Vendor": "xen-orchestra", + "Product": "xen_orchestra_server", + "Version": "4.3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zuuse:beims_contractorweb_.net:5.18.0.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:zuuse:beims_contractorweb_.net:5.18.0.0", + "wfn": { + "Part": "a", + "Vendor": "zuuse", + "Product": "beims_contractorweb_.net", + "Version": "5.18.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mailcow:mailcow\\:_dockerized:0.3.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mailcow:mailcow%3a_dockerized:0.3.2", + "wfn": { + "Part": "a", + "Vendor": "mailcow", + "Product": "mailcow:_dockerized", + "Version": "0.3.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:3cx:live_chat:8.0.32:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:3cx:live_chat:8.0.32::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "3cx", + "Product": "live_chat", + "Version": "8.0.32", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:unified_contact_center_enterprise:11.0\\(1\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:unified_contact_center_enterprise:11.0%281%29", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "unified_contact_center_enterprise", + "Version": "11.0(1)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:weseek:growi:3.1.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:weseek:growi:3.1.2", + "wfn": { + "Part": "a", + "Vendor": "weseek", + "Product": "growi", + "Version": "3.1.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:enalean:tuleap:10.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:enalean:tuleap:10.6", + "wfn": { + "Part": "a", + "Vendor": "enalean", + "Product": "tuleap", + "Version": "10.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:jf812a:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:jf812a:-", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "jf812a", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:webyog:sqlyog:3.52:-:enterprise:*:*:*:*:*", + "cpe-url": "cpe:/a:webyog:sqlyog:3.52:-:enterprise", + "wfn": { + "Part": "a", + "Vendor": "webyog", + "Product": "sqlyog", + "Version": "3.52", + "Update": "-", + "Edition": "enterprise", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pidgin:pidgin:2.10.8:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pidgin:pidgin:2.10.8", + "wfn": { + "Part": "a", + "Vendor": "pidgin", + "Product": "pidgin", + "Version": "2.10.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:libguestfs:libguestfs:1.33.17:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:libguestfs:libguestfs:1.33.17", + "wfn": { + "Part": "a", + "Vendor": "libguestfs", + "Product": "libguestfs", + "Version": "1.33.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:python:urllib3:1.18:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:python:urllib3:1.18", + "wfn": { + "Part": "a", + "Vendor": "python", + "Product": "urllib3", + "Version": "1.18", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:jclouds:1.6.1:incubating-rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:jclouds:1.6.1:incubating-rc1", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "jclouds", + "Version": "1.6.1", + "Update": "incubating-rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:appleple:a-blog_cms:2.7.12:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:appleple:a-blog_cms:2.7.12", + "wfn": { + "Part": "a", + "Vendor": "appleple", + "Product": "a-blog_cms", + "Version": "2.7.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnu:libredwg:0.10.1.2670:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnu:libredwg:0.10.1.2670", + "wfn": { + "Part": "a", + "Vendor": "gnu", + "Product": "libredwg", + "Version": "0.10.1.2670", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:postgresql:postgresql:8.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:postgresql:postgresql:8.0.1", + "wfn": { + "Part": "a", + "Vendor": "postgresql", + "Product": "postgresql", + "Version": "8.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:open_stf:1.0.2:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:open_stf:1.0.2::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "open_stf", + "Version": "1.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:winwar:wp_ebay_product_feeds:0.5:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:winwar:wp_ebay_product_feeds:0.5::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "winwar", + "Product": "wp_ebay_product_feeds", + "Version": "0.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:web-mv:resads:1.0.8:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:web-mv:resads:1.0.8::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "web-mv", + "Product": "resads", + "Version": "1.0.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:uglifyjs_project:uglifyjs:3.0.16:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:uglifyjs_project:uglifyjs:3.0.16::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "uglifyjs_project", + "Product": "uglifyjs", + "Version": "3.0.16", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:frontaccounting:frontaccounting:2.3.22:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:frontaccounting:frontaccounting:2.3.22", + "wfn": { + "Part": "a", + "Vendor": "frontaccounting", + "Product": "frontaccounting", + "Version": "2.3.22", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apple:itunes:7.4.2:-:mac:*:*:*:*:*", + "cpe-url": "cpe:/a:apple:itunes:7.4.2:-:mac", + "wfn": { + "Part": "a", + "Vendor": "apple", + "Product": "itunes", + "Version": "7.4.2", + "Update": "-", + "Edition": "mac", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fluentd:fluentd:1.12.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:fluentd:fluentd:1.12.1", + "wfn": { + "Part": "a", + "Vendor": "fluentd", + "Product": "fluentd", + "Version": "1.12.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sun:java_dynamic_management_kit:5.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sun:java_dynamic_management_kit:5.1", + "wfn": { + "Part": "a", + "Vendor": "sun", + "Product": "java_dynamic_management_kit", + "Version": "5.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:contao:contao:4.5.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:contao:contao:4.5.7", + "wfn": { + "Part": "a", + "Vendor": "contao", + "Product": "contao", + "Version": "4.5.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gvectors:wpdiscuz:5.1.3:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:gvectors:wpdiscuz:5.1.3::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "gvectors", + "Product": "wpdiscuz", + "Version": "5.1.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jupyterhub:kubespawner:0.8.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:jupyterhub:kubespawner:0.8.1", + "wfn": { + "Part": "a", + "Vendor": "jupyterhub", + "Product": "kubespawner", + "Version": "0.8.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tracker-software:pdf-xchange_lite_printer:4.0.154:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tracker-software:pdf-xchange_lite_printer:4.0.154", + "wfn": { + "Part": "a", + "Vendor": "tracker-software", + "Product": "pdf-xchange_lite_printer", + "Version": "4.0.154", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:node-opencv_project:node-opencv:0.0.9:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:node-opencv_project:node-opencv:0.0.9::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "node-opencv_project", + "Product": "node-opencv", + "Version": "0.0.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:flarum:flarum:0.1.0:beta6:*:*:*:*:*:*", + "cpe-url": "cpe:/a:flarum:flarum:0.1.0:beta6", + "wfn": { + "Part": "a", + "Vendor": "flarum", + "Product": "flarum", + "Version": "0.1.0", + "Update": "beta6", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:php:pear:1.4.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:php:pear:1.4.4", + "wfn": { + "Part": "a", + "Vendor": "php", + "Product": "pear", + "Version": "1.4.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:belwith-keeler:hickory_smart:01.01.05:*:*:*:*:iphone_os:*:*", + "cpe-url": "cpe:/a:belwith-keeler:hickory_smart:01.01.05::~~~iphone_os~~", + "wfn": { + "Part": "a", + "Vendor": "belwith-keeler", + "Product": "hickory_smart", + "Version": "01.01.05", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "iphone_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:huawei:secospace_usg6600_firmware:v100r001c30spc500:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:huawei:secospace_usg6600_firmware:v100r001c30spc500", + "wfn": { + "Part": "o", + "Vendor": "huawei", + "Product": "secospace_usg6600_firmware", + "Version": "v100r001c30spc500", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:trousers_project:trousers:0.3.13:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:trousers_project:trousers:0.3.13", + "wfn": { + "Part": "a", + "Vendor": "trousers_project", + "Product": "trousers", + "Version": "0.3.13", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pterodactyl:panel:1.0.0:beta1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pterodactyl:panel:1.0.0:beta1", + "wfn": { + "Part": "a", + "Vendor": "pterodactyl", + "Product": "panel", + "Version": "1.0.0", + "Update": "beta1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:laserjet_managed_flow_mfp_e67550_l3u70a:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:laserjet_managed_flow_mfp_e67550_l3u70a:-", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "laserjet_managed_flow_mfp_e67550_l3u70a", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:freedownloadmanager:freedownloadmanager:2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:freedownloadmanager:freedownloadmanager:2", + "wfn": { + "Part": "a", + "Vendor": "freedownloadmanager", + "Product": "freedownloadmanager", + "Version": "2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:db2:10.1.0.3:*:*:*:enterprise:*:*:*", + "cpe-url": "cpe:/a:ibm:db2:10.1.0.3::~~enterprise~~~", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "db2", + "Version": "10.1.0.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "enterprise", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openstack:oslo.middleware:3.30.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openstack:oslo.middleware:3.30.1", + "wfn": { + "Part": "a", + "Vendor": "openstack", + "Product": "oslo.middleware", + "Version": "3.30.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:simplenews_scheduler_project:simplenews_scheduler:6.x-2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:simplenews_scheduler_project:simplenews_scheduler:6.x-2.1", + "wfn": { + "Part": "a", + "Vendor": "simplenews_scheduler_project", + "Product": "simplenews_scheduler", + "Version": "6.x-2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpexpertdeveloper:wp_private_content_plus:1.7:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpexpertdeveloper:wp_private_content_plus:1.7::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpexpertdeveloper", + "Product": "wp_private_content_plus", + "Version": "1.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:catchplugins:generate_child_theme:-:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:catchplugins:generate_child_theme:-::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "catchplugins", + "Product": "generate_child_theme", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:spa_502g_firmware:7.6.2:sr1:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:spa_502g_firmware:7.6.2:sr1", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "spa_502g_firmware", + "Version": "7.6.2", + "Update": "sr1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cleverplugins:seo_booster:3.6.14:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:cleverplugins:seo_booster:3.6.14::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "cleverplugins", + "Product": "seo_booster", + "Version": "3.6.14", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:go-jose_project:go-jose:2.1.8:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:go-jose_project:go-jose:2.1.8", + "wfn": { + "Part": "a", + "Vendor": "go-jose_project", + "Product": "go-jose", + "Version": "2.1.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pdfinfo_project:pdfinfo:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pdfinfo_project:pdfinfo:-", + "wfn": { + "Part": "a", + "Vendor": "pdfinfo_project", + "Product": "pdfinfo", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pervasive:data_integrator_engine:9.0.3.30:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pervasive:data_integrator_engine:9.0.3.30", + "wfn": { + "Part": "a", + "Vendor": "pervasive", + "Product": "data_integrator_engine", + "Version": "9.0.3.30", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:inmedias:questionaire:3.0.45:beta:*:*:*:typo3:*:*", + "cpe-url": "cpe:/a:inmedias:questionaire:3.0.45:beta:~~~typo3~~", + "wfn": { + "Part": "a", + "Vendor": "inmedias", + "Product": "questionaire", + "Version": "3.0.45", + "Update": "beta", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "typo3", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:webyog:sqlyog:8.15:-:community:*:*:*:*:*", + "cpe-url": "cpe:/a:webyog:sqlyog:8.15:-:community", + "wfn": { + "Part": "a", + "Vendor": "webyog", + "Product": "sqlyog", + "Version": "8.15", + "Update": "-", + "Edition": "community", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redhat:wildfly_core:3.0.0:beta3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redhat:wildfly_core:3.0.0:beta3", + "wfn": { + "Part": "a", + "Vendor": "redhat", + "Product": "wildfly_core", + "Version": "3.0.0", + "Update": "beta3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pressified:sendpress:0.9.8:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:pressified:sendpress:0.9.8::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "pressified", + "Product": "sendpress", + "Version": "0.9.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cakephp:cakephp:3.4.0:beta2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cakephp:cakephp:3.4.0:beta2", + "wfn": { + "Part": "a", + "Vendor": "cakephp", + "Product": "cakephp", + "Version": "3.4.0", + "Update": "beta2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mobyproject:moby:1.12.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mobyproject:moby:1.12.5", + "wfn": { + "Part": "a", + "Vendor": "mobyproject", + "Product": "moby", + "Version": "1.12.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redmine:redmine:2.6.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redmine:redmine:2.6.7", + "wfn": { + "Part": "a", + "Vendor": "redmine", + "Product": "redmine", + "Version": "2.6.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sap:openui5:1.44.18:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sap:openui5:1.44.18", + "wfn": { + "Part": "a", + "Vendor": "sap", + "Product": "openui5", + "Version": "1.44.18", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ikiwiki:ikiwiki:2.55:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ikiwiki:ikiwiki:2.55", + "wfn": { + "Part": "a", + "Vendor": "ikiwiki", + "Product": "ikiwiki", + "Version": "2.55", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:percona:xtrabackup:2.1.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:percona:xtrabackup:2.1.6", + "wfn": { + "Part": "a", + "Vendor": "percona", + "Product": "xtrabackup", + "Version": "2.1.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:libpng:libpng:1.7.0:beta01:*:*:*:*:*:*", + "cpe-url": "cpe:/a:libpng:libpng:1.7.0:beta01", + "wfn": { + "Part": "a", + "Vendor": "libpng", + "Product": "libpng", + "Version": "1.7.0", + "Update": "beta01", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kentico:kentico_cms:12.0.12:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:kentico:kentico_cms:12.0.12", + "wfn": { + "Part": "a", + "Vendor": "kentico", + "Product": "kentico_cms", + "Version": "12.0.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:aufs_project:aufs2:2.6.36:rc3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:aufs_project:aufs2:2.6.36:rc3", + "wfn": { + "Part": "a", + "Vendor": "aufs_project", + "Product": "aufs2", + "Version": "2.6.36", + "Update": "rc3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnu:libredwg:0.8.1898:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnu:libredwg:0.8.1898", + "wfn": { + "Part": "a", + "Vendor": "gnu", + "Product": "libredwg", + "Version": "0.8.1898", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:prost_project:prost:0.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:prost_project:prost:0.4.0", + "wfn": { + "Part": "a", + "Vendor": "prost_project", + "Product": "prost", + "Version": "0.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mjml:mjml:3.3.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mjml:mjml:3.3.4", + "wfn": { + "Part": "a", + "Vendor": "mjml", + "Product": "mjml", + "Version": "3.3.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:dotnetblogengine:blogengine.net:2.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:dotnetblogengine:blogengine.net:2.5", + "wfn": { + "Part": "a", + "Vendor": "dotnetblogengine", + "Product": "blogengine.net", + "Version": "2.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:iij:seil_b1_firmware:3.05:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:iij:seil_b1_firmware:3.05", + "wfn": { + "Part": "o", + "Vendor": "iij", + "Product": "seil_b1_firmware", + "Version": "3.05", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:8.2.3210:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:8.2.3210", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "8.2.3210", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vfbpro:visual_form_builder:3.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:vfbpro:visual_form_builder:3.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "vfbpro", + "Product": "visual_form_builder", + "Version": "3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gleamtech:fileultimate:6.5.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gleamtech:fileultimate:6.5.2", + "wfn": { + "Part": "a", + "Vendor": "gleamtech", + "Product": "fileultimate", + "Version": "6.5.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.0132:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.0132", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.0132", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:intel:xeon_e3-1220:6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:intel:xeon_e3-1220:6", + "wfn": { + "Part": "h", + "Vendor": "intel", + "Product": "xeon_e3-1220", + "Version": "6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:senecajs:seneca:2.0.1:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:senecajs:seneca:2.0.1::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "senecajs", + "Product": "seneca", + "Version": "2.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloud_foundry:bosh:263.9.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cloud_foundry:bosh:263.9.0", + "wfn": { + "Part": "a", + "Vendor": "cloud_foundry", + "Product": "bosh", + "Version": "263.9.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:harpjs:harp:0.11.1:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:harpjs:harp:0.11.1::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "harpjs", + "Product": "harp", + "Version": "0.11.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:totvs:fluig:1.7.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:totvs:fluig:1.7.0", + "wfn": { + "Part": "a", + "Vendor": "totvs", + "Product": "fluig", + "Version": "1.7.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kramdown_project:kramdown:0.14.1:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:kramdown_project:kramdown:0.14.1::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "kramdown_project", + "Product": "kramdown", + "Version": "0.14.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nullsoft:winamp:5.21:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nullsoft:winamp:5.21", + "wfn": { + "Part": "a", + "Vendor": "nullsoft", + "Product": "winamp", + "Version": "5.21", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hibara:attachecase:3.2.2.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hibara:attachecase:3.2.2.0", + "wfn": { + "Part": "a", + "Vendor": "hibara", + "Product": "attachecase", + "Version": "3.2.2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sumatrapdfreader:sumatrapdf:2.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sumatrapdfreader:sumatrapdf:2.5", + "wfn": { + "Part": "a", + "Vendor": "sumatrapdfreader", + "Product": "sumatrapdf", + "Version": "2.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:owncloud:owncloud:1.1.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:owncloud:owncloud:1.1.0:-", + "wfn": { + "Part": "a", + "Vendor": "owncloud", + "Product": "owncloud", + "Version": "1.1.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bundler:bundler:1.14.0:pre2:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:bundler:bundler:1.14.0:pre2:~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "bundler", + "Product": "bundler", + "Version": "1.14.0", + "Update": "pre2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cyrus:imap:2.5.15:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cyrus:imap:2.5.15", + "wfn": { + "Part": "a", + "Vendor": "cyrus", + "Product": "imap", + "Version": "2.5.15", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vaadin:vaadin-menu-bar:2.0.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vaadin:vaadin-menu-bar:2.0.0:-", + "wfn": { + "Part": "a", + "Vendor": "vaadin", + "Product": "vaadin-menu-bar", + "Version": "2.0.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:github:github:2.9.9:*:*:*:enterprise:*:*:*", + "cpe-url": "cpe:/a:github:github:2.9.9::~~enterprise~~~", + "wfn": { + "Part": "a", + "Vendor": "github", + "Product": "github", + "Version": "2.9.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "enterprise", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:tomcat:10.0.0:milestone1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:tomcat:10.0.0:milestone1", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "tomcat", + "Version": "10.0.0", + "Update": "milestone1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:dashboard_view:2.12:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:dashboard_view:2.12::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "dashboard_view", + "Version": "2.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:triple-game:triplea:2.0.17114:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:triple-game:triplea:2.0.17114", + "wfn": { + "Part": "a", + "Vendor": "triple-game", + "Product": "triplea", + "Version": "2.0.17114", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:commons_compress:1.13:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:commons_compress:1.13", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "commons_compress", + "Version": "1.13", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cern:root:5-18-00:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cern:root:5-18-00", + "wfn": { + "Part": "a", + "Vendor": "cern", + "Product": "root", + "Version": "5-18-00", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnome:evolution-ews:3.24.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnome:evolution-ews:3.24.4", + "wfn": { + "Part": "a", + "Vendor": "gnome", + "Product": "evolution-ews", + "Version": "3.24.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gradle:maven:1.2.3:*:*:*:*:gradle:*:*", + "cpe-url": "cpe:/a:gradle:maven:1.2.3::~~~gradle~~", + "wfn": { + "Part": "a", + "Vendor": "gradle", + "Product": "maven", + "Version": "1.2.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "gradle", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:contest_gallery:contest_gallery:9.3.8:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:contest_gallery:contest_gallery:9.3.8::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "contest_gallery", + "Product": "contest_gallery", + "Version": "9.3.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:interactivebrokers:ibapi:0.1.9:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:interactivebrokers:ibapi:0.1.9::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "interactivebrokers", + "Product": "ibapi", + "Version": "0.1.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tinyproxy_project:tinyproxy:1.6.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tinyproxy_project:tinyproxy:1.6.1", + "wfn": { + "Part": "a", + "Vendor": "tinyproxy_project", + "Product": "tinyproxy", + "Version": "1.6.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tiki:tikiwiki_cms\\/groupware:15.4:*:*:*:lts:*:*:*", + "cpe-url": "cpe:/a:tiki:tikiwiki_cms%2fgroupware:15.4::~~lts~~~", + "wfn": { + "Part": "a", + "Vendor": "tiki", + "Product": "tikiwiki_cms/groupware", + "Version": "15.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "lts", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sensu:sensu_core:5.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sensu:sensu_core:5.4.0", + "wfn": { + "Part": "a", + "Vendor": "sensu", + "Product": "sensu_core", + "Version": "5.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:advancestack_10base-t_switching_hub_j3210a:a.03.07:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:advancestack_10base-t_switching_hub_j3210a:a.03.07", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "advancestack_10base-t_switching_hub_j3210a", + "Version": "a.03.07", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:chrome:9.0.597.27:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:chrome:9.0.597.27", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "chrome", + "Version": "9.0.597.27", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:pivotal_cloud_cache:1.2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:pivotal_cloud_cache:1.2.1", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "pivotal_cloud_cache", + "Version": "1.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:accurev:0.4:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:accurev:0.4::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "accurev", + "Version": "0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:maven:3.5.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:maven:3.5.4", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "maven", + "Version": "3.5.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:jabber_\\(xmpp\\)_notifier_and_control:1.9:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:jabber_%28xmpp%29_notifier_and_control:1.9::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "jabber_(xmpp)_notifier_and_control", + "Version": "1.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:adaptivecomputing:torque_resource_manager:2.3.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:adaptivecomputing:torque_resource_manager:2.3.7", + "wfn": { + "Part": "a", + "Vendor": "adaptivecomputing", + "Product": "torque_resource_manager", + "Version": "2.3.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:chrome:26.0.1410.29:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:chrome:26.0.1410.29", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "chrome", + "Version": "26.0.1410.29", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:samba:samba:4.1.21:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:samba:samba:4.1.21", + "wfn": { + "Part": "a", + "Vendor": "samba", + "Product": "samba", + "Version": "4.1.21", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kubernetes:kubernetes:1.16.0:alpha0:*:*:*:*:*:*", + "cpe-url": "cpe:/a:kubernetes:kubernetes:1.16.0:alpha0", + "wfn": { + "Part": "a", + "Vendor": "kubernetes", + "Product": "kubernetes", + "Version": "1.16.0", + "Update": "alpha0", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:python:setuptools:41.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:python:setuptools:41.4.0", + "wfn": { + "Part": "a", + "Vendor": "python", + "Product": "setuptools", + "Version": "41.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gitlab:gitlab:12.1.5:*:*:*:enterprise:*:*:*", + "cpe-url": "cpe:/a:gitlab:gitlab:12.1.5::~~enterprise~~~", + "wfn": { + "Part": "a", + "Vendor": "gitlab", + "Product": "gitlab", + "Version": "12.1.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "enterprise", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:apple:mac_os_x:11.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:apple:mac_os_x:11.0.1", + "wfn": { + "Part": "o", + "Vendor": "apple", + "Product": "mac_os_x", + "Version": "11.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:osgeo:mapserver:4.2.0:beta2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:osgeo:mapserver:4.2.0:beta2", + "wfn": { + "Part": "a", + "Vendor": "osgeo", + "Product": "mapserver", + "Version": "4.2.0", + "Update": "beta2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bitpay:copay_bitcoin_wallet:4.3.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bitpay:copay_bitcoin_wallet:4.3.2", + "wfn": { + "Part": "a", + "Vendor": "bitpay", + "Product": "copay_bitcoin_wallet", + "Version": "4.3.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bayashi:dopvstar\\*:0084:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bayashi:dopvstar%2a:0084", + "wfn": { + "Part": "a", + "Vendor": "bayashi", + "Product": "dopvstar\\*", + "Version": "0084", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:xyzscripts:newsletter_manager:1.1:-:-:*:-:wordpress:*:*", + "cpe-url": "cpe:/a:xyzscripts:newsletter_manager:1.1:-:~-~-~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "xyzscripts", + "Product": "newsletter_manager", + "Version": "1.1", + "Update": "-", + "Edition": "-", + "Language": "", + "SwEdition": "-", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gitlab:runner:9.0.0:rc3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gitlab:runner:9.0.0:rc3", + "wfn": { + "Part": "a", + "Vendor": "gitlab", + "Product": "runner", + "Version": "9.0.0", + "Update": "rc3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hygeia_project:hygeia:1.22.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hygeia_project:hygeia:1.22.7", + "wfn": { + "Part": "a", + "Vendor": "hygeia_project", + "Product": "hygeia", + "Version": "1.22.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bit_project:bit:0.5.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bit_project:bit:0.5.6", + "wfn": { + "Part": "a", + "Vendor": "bit_project", + "Product": "bit", + "Version": "0.5.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:freebsd:freebsd:10.2:p2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:freebsd:freebsd:10.2:p2", + "wfn": { + "Part": "a", + "Vendor": "freebsd", + "Product": "freebsd", + "Version": "10.2", + "Update": "p2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:grafana:agent:0.20.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:grafana:agent:0.20.0", + "wfn": { + "Part": "a", + "Vendor": "grafana", + "Product": "agent", + "Version": "0.20.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ubports:unity8:7.84\\+14.04.20140314-0ubuntu1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ubports:unity8:7.84%2b14.04.20140314-0ubuntu1", + "wfn": { + "Part": "a", + "Vendor": "ubports", + "Product": "unity8", + "Version": "7.84+14.04.20140314-0ubuntu1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mozilla:thunderbird:31.2.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mozilla:thunderbird:31.2.0", + "wfn": { + "Part": "a", + "Vendor": "mozilla", + "Product": "thunderbird", + "Version": "31.2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gonitro:nitro_pro:10.5.9.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gonitro:nitro_pro:10.5.9.9", + "wfn": { + "Part": "a", + "Vendor": "gonitro", + "Product": "nitro_pro", + "Version": "10.5.9.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ntp:ntp:4.2.7:p216:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ntp:ntp:4.2.7:p216", + "wfn": { + "Part": "a", + "Vendor": "ntp", + "Product": "ntp", + "Version": "4.2.7", + "Update": "p216", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:intel:xeon_w-2133:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:intel:xeon_w-2133:-", + "wfn": { + "Part": "h", + "Vendor": "intel", + "Product": "xeon_w-2133", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:linuxfoundation:fabric:1.4.8:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:linuxfoundation:fabric:1.4.8", + "wfn": { + "Part": "a", + "Vendor": "linuxfoundation", + "Product": "fabric", + "Version": "1.4.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pixar:openusd:18.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pixar:openusd:18.11", + "wfn": { + "Part": "a", + "Vendor": "pixar", + "Product": "openusd", + "Version": "18.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ays-pro:quiz_maker:5.4.3:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:ays-pro:quiz_maker:5.4.3::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "ays-pro", + "Product": "quiz_maker", + "Version": "5.4.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpfastestcache:wp_fastest_cache:0.7.5:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpfastestcache:wp_fastest_cache:0.7.5::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpfastestcache", + "Product": "wp_fastest_cache", + "Version": "0.7.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:unified_computing_system_central_software:1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:unified_computing_system_central_software:1.0", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "unified_computing_system_central_software", + "Version": "1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nttdocomo:spmode_mail_android:5000:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nttdocomo:spmode_mail_android:5000", + "wfn": { + "Part": "a", + "Vendor": "nttdocomo", + "Product": "spmode_mail_android", + "Version": "5000", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:swi-prolog:swi-prolog:7.1.32:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:swi-prolog:swi-prolog:7.1.32", + "wfn": { + "Part": "a", + "Vendor": "swi-prolog", + "Product": "swi-prolog", + "Version": "7.1.32", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:facebook:react:16.7.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:facebook:react:16.7.0", + "wfn": { + "Part": "a", + "Vendor": "facebook", + "Product": "react", + "Version": "16.7.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:intel:xeon_e3:x3480:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:intel:xeon_e3:x3480", + "wfn": { + "Part": "h", + "Vendor": "intel", + "Product": "xeon_e3", + "Version": "x3480", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vips:vips:7.11.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vips:vips:7.11.2", + "wfn": { + "Part": "a", + "Vendor": "vips", + "Product": "vips", + "Version": "7.11.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:libpng:libpng:1.6.17:beta01:*:*:*:*:*:*", + "cpe-url": "cpe:/a:libpng:libpng:1.6.17:beta01", + "wfn": { + "Part": "a", + "Vendor": "libpng", + "Product": "libpng", + "Version": "1.6.17", + "Update": "beta01", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:smartbear:swagger-ui:3.6.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:smartbear:swagger-ui:3.6.1", + "wfn": { + "Part": "a", + "Vendor": "smartbear", + "Product": "swagger-ui", + "Version": "3.6.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:1up:oneupuploaderbundle:0.9.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:1up:oneupuploaderbundle:0.9.9", + "wfn": { + "Part": "a", + "Vendor": "1up", + "Product": "oneupuploaderbundle", + "Version": "0.9.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:lenovo:v310-15isk:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:lenovo:v310-15isk:-", + "wfn": { + "Part": "h", + "Vendor": "lenovo", + "Product": "v310-15isk", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mozilla:thunderbird:3.0:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mozilla:thunderbird:3.0:rc1", + "wfn": { + "Part": "a", + "Vendor": "mozilla", + "Product": "thunderbird", + "Version": "3.0", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wp-dbmanager_project:wp-dbmanager:2.79:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wp-dbmanager_project:wp-dbmanager:2.79::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wp-dbmanager_project", + "Product": "wp-dbmanager", + "Version": "2.79", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apereo:opencast:1.4.2:rc2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apereo:opencast:1.4.2:rc2", + "wfn": { + "Part": "a", + "Vendor": "apereo", + "Product": "opencast", + "Version": "1.4.2", + "Update": "rc2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nette:latte:2.6.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nette:latte:2.6.3", + "wfn": { + "Part": "a", + "Vendor": "nette", + "Product": "latte", + "Version": "2.6.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:docker:engine:17.03.2:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:docker:engine:17.03.2:rc1", + "wfn": { + "Part": "a", + "Vendor": "docker", + "Product": "engine", + "Version": "17.03.2", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloudflare:octopki:1.1.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cloudflare:octopki:1.1.3", + "wfn": { + "Part": "a", + "Vendor": "cloudflare", + "Product": "octopki", + "Version": "1.1.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bestit:amazon_pay:7.0.1:*:*:*:*:shopware:*:*", + "cpe-url": "cpe:/a:bestit:amazon_pay:7.0.1::~~~shopware~~", + "wfn": { + "Part": "a", + "Vendor": "bestit", + "Product": "amazon_pay", + "Version": "7.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "shopware", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:otrs:otrs:3.0.0:beta1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:otrs:otrs:3.0.0:beta1", + "wfn": { + "Part": "a", + "Vendor": "otrs", + "Product": "otrs", + "Version": "3.0.0", + "Update": "beta1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:libaacplus_project:libaacplus:1.0.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:libaacplus_project:libaacplus:1.0.2", + "wfn": { + "Part": "a", + "Vendor": "libaacplus_project", + "Product": "libaacplus", + "Version": "1.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ammonia_project:ammonia:2.0.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ammonia_project:ammonia:2.0.0", + "wfn": { + "Part": "a", + "Vendor": "ammonia_project", + "Product": "ammonia", + "Version": "2.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:transloadit:uppy:0.28.0:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:transloadit:uppy:0.28.0::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "transloadit", + "Product": "uppy", + "Version": "0.28.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mit:kerberos:5-1.14:alpha1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mit:kerberos:5-1.14:alpha1", + "wfn": { + "Part": "a", + "Vendor": "mit", + "Product": "kerberos", + "Version": "5-1.14", + "Update": "alpha1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redhat:libvirt:0.4.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redhat:libvirt:0.4.0", + "wfn": { + "Part": "a", + "Vendor": "redhat", + "Product": "libvirt", + "Version": "0.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:itextpdf:itext:1.3.5:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:itextpdf:itext:1.3.5", + "wfn": { + "Part": "a", + "Vendor": "itextpdf", + "Product": "itext", + "Version": "1.3.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:strapi:strapi:3.0.0:beta15:*:*:*:*:*:*", + "cpe-url": "cpe:/a:strapi:strapi:3.0.0:beta15", + "wfn": { + "Part": "a", + "Vendor": "strapi", + "Product": "strapi", + "Version": "3.0.0", + "Update": "beta15", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:microsoft:windows_server_2008:-:sp2:hpc:*:*:*:*:*", + "cpe-url": "cpe:/o:microsoft:windows_server_2008:-:sp2:hpc", + "wfn": { + "Part": "o", + "Vendor": "microsoft", + "Product": "windows_server_2008", + "Version": "-", + "Update": "sp2", + "Edition": "hpc", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:slf4j:slf4j-api:1.7.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:slf4j:slf4j-api:1.7.4", + "wfn": { + "Part": "a", + "Vendor": "slf4j", + "Product": "slf4j-api", + "Version": "1.7.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:oracle:e-business_suite_technology_stack:12.1.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:oracle:e-business_suite_technology_stack:12.1.3", + "wfn": { + "Part": "a", + "Vendor": "oracle", + "Product": "e-business_suite_technology_stack", + "Version": "12.1.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:webfactoryltd:wp_reset_pro:5.81:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:webfactoryltd:wp_reset_pro:5.81::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "webfactoryltd", + "Product": "wp_reset_pro", + "Version": "5.81", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:docsifyjs:docsify:1.7.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:docsifyjs:docsify:1.7.2", + "wfn": { + "Part": "a", + "Vendor": "docsifyjs", + "Product": "docsify", + "Version": "1.7.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:hp:envy_photo_7800_k7s00a_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:hp:envy_photo_7800_k7s00a_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "hp", + "Product": "envy_photo_7800_k7s00a_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zoom:zoom:4.4.55387.0716:*:*:*:*:mac_os:*:*", + "cpe-url": "cpe:/a:zoom:zoom:4.4.55387.0716::~~~mac_os~~", + "wfn": { + "Part": "a", + "Vendor": "zoom", + "Product": "zoom", + "Version": "4.4.55387.0716", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "mac_os", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wesnoth:the_battle_for_wesnoth:0.8.5:rc5:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wesnoth:the_battle_for_wesnoth:0.8.5:rc5", + "wfn": { + "Part": "a", + "Vendor": "wesnoth", + "Product": "the_battle_for_wesnoth", + "Version": "0.8.5", + "Update": "rc5", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:fortinet:fortios:6.0.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:fortinet:fortios:6.0.3", + "wfn": { + "Part": "o", + "Vendor": "fortinet", + "Product": "fortios", + "Version": "6.0.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:processing:processing:2.0:beta4:*:*:*:*:*:*", + "cpe-url": "cpe:/a:processing:processing:2.0:beta4", + "wfn": { + "Part": "a", + "Vendor": "processing", + "Product": "processing", + "Version": "2.0", + "Update": "beta4", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:epson:px-m7050fp_firmware:2017-10-13:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:epson:px-m7050fp_firmware:2017-10-13", + "wfn": { + "Part": "o", + "Vendor": "epson", + "Product": "px-m7050fp_firmware", + "Version": "2017-10-13", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ntp:ntp:4.2.8:p1_beta1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ntp:ntp:4.2.8:p1_beta1", + "wfn": { + "Part": "a", + "Vendor": "ntp", + "Product": "ntp", + "Version": "4.2.8", + "Update": "p1_beta1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:easycorp:zentao:13.0:beta4:*:*:*:*:*:*", + "cpe-url": "cpe:/a:easycorp:zentao:13.0:beta4", + "wfn": { + "Part": "a", + "Vendor": "easycorp", + "Product": "zentao", + "Version": "13.0", + "Update": "beta4", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:git-annex_project:git-annex:6.20160229:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:git-annex_project:git-annex:6.20160229", + "wfn": { + "Part": "a", + "Vendor": "git-annex_project", + "Product": "git-annex", + "Version": "6.20160229", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:delivery_pipeline:0.7.5:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:delivery_pipeline:0.7.5::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "delivery_pipeline", + "Version": "0.7.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hp:c4100_help:70.0.231.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hp:c4100_help:70.0.231.0", + "wfn": { + "Part": "a", + "Vendor": "hp", + "Product": "c4100_help", + "Version": "70.0.231.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apple:cups:1.5.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apple:cups:1.5.4", + "wfn": { + "Part": "a", + "Vendor": "apple", + "Product": "cups", + "Version": "1.5.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:google_compute_engine:1.0.7:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:google_compute_engine:1.0.7::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "google_compute_engine", + "Version": "1.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:support-project:knowledge:1.6.0:pre4:*:*:*:*:*:*", + "cpe-url": "cpe:/a:support-project:knowledge:1.6.0:pre4", + "wfn": { + "Part": "a", + "Vendor": "support-project", + "Product": "knowledge", + "Version": "1.6.0", + "Update": "pre4", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gitlab:gitlab:13.6.1:*:*:*:enterprise:*:*:*", + "cpe-url": "cpe:/a:gitlab:gitlab:13.6.1::~~enterprise~~~", + "wfn": { + "Part": "a", + "Vendor": "gitlab", + "Product": "gitlab", + "Version": "13.6.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "enterprise", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openmage:magento:1.9.1.1:*:*:*:lts:*:*:*", + "cpe-url": "cpe:/a:openmage:magento:1.9.1.1::~~lts~~~", + "wfn": { + "Part": "a", + "Vendor": "openmage", + "Product": "magento", + "Version": "1.9.1.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "lts", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:socket:engine.io-client:1.8.2:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:socket:engine.io-client:1.8.2::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "socket", + "Product": "engine.io-client", + "Version": "1.8.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:b2evolution:b2evolution_cms:6.5.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:b2evolution:b2evolution_cms:6.5.0", + "wfn": { + "Part": "a", + "Vendor": "b2evolution", + "Product": "b2evolution_cms", + "Version": "6.5.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:linuxfoundation:harbor:2.1.0:rc2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:linuxfoundation:harbor:2.1.0:rc2", + "wfn": { + "Part": "a", + "Vendor": "linuxfoundation", + "Product": "harbor", + "Version": "2.1.0", + "Update": "rc2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wekan_project:wekan:3.76:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wekan_project:wekan:3.76", + "wfn": { + "Part": "a", + "Vendor": "wekan_project", + "Product": "wekan", + "Version": "3.76", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:novell:edirectory:8.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:novell:edirectory:8.0", + "wfn": { + "Part": "a", + "Vendor": "novell", + "Product": "edirectory", + "Version": "8.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnu:emacs:19.31:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnu:emacs:19.31", + "wfn": { + "Part": "a", + "Vendor": "gnu", + "Product": "emacs", + "Version": "19.31", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vips:vips:7.7.14:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vips:vips:7.7.14", + "wfn": { + "Part": "a", + "Vendor": "vips", + "Product": "vips", + "Version": "7.7.14", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:hp:cq183a_firmware:1828b:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:hp:cq183a_firmware:1828b", + "wfn": { + "Part": "o", + "Vendor": "hp", + "Product": "cq183a_firmware", + "Version": "1828b", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlassian:editor-core:118.0.0:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:atlassian:editor-core:118.0.0::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "atlassian", + "Product": "editor-core", + "Version": "118.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:lilypond:lilypond:2.19.44:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:lilypond:lilypond:2.19.44", + "wfn": { + "Part": "a", + "Vendor": "lilypond", + "Product": "lilypond", + "Version": "2.19.44", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openstack:tripleo_heat_templates:6.2.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openstack:tripleo_heat_templates:6.2.9", + "wfn": { + "Part": "a", + "Vendor": "openstack", + "Product": "tripleo_heat_templates", + "Version": "6.2.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:oracle:fusion_middleware:11.1.1.3.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:oracle:fusion_middleware:11.1.1.3.0", + "wfn": { + "Part": "a", + "Vendor": "oracle", + "Product": "fusion_middleware", + "Version": "11.1.1.3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tripleplay:onelan_cms:2.0.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tripleplay:onelan_cms:2.0.3", + "wfn": { + "Part": "a", + "Vendor": "tripleplay", + "Product": "onelan_cms", + "Version": "2.0.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:portainer:portainer:1.15.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:portainer:portainer:1.15.0", + "wfn": { + "Part": "a", + "Vendor": "portainer", + "Product": "portainer", + "Version": "1.15.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:firefly-iii:firefly_iii:5.2.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:firefly-iii:firefly_iii:5.2.3", + "wfn": { + "Part": "a", + "Vendor": "firefly-iii", + "Product": "firefly_iii", + "Version": "5.2.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:getkirby:kirby:2.1.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:getkirby:kirby:2.1.2", + "wfn": { + "Part": "a", + "Vendor": "getkirby", + "Product": "kirby", + "Version": "2.1.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:auth0:auth0.js:9.3.2:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:auth0:auth0.js:9.3.2::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "auth0", + "Product": "auth0.js", + "Version": "9.3.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:spring_integration:4.0.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:spring_integration:4.0.2", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "spring_integration", + "Version": "4.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:btcpayserver:btcpayserver:1.0.1.38:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:btcpayserver:btcpayserver:1.0.1.38", + "wfn": { + "Part": "a", + "Vendor": "btcpayserver", + "Product": "btcpayserver", + "Version": "1.0.1.38", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:octobercms:october:1.0.73:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:octobercms:october:1.0.73", + "wfn": { + "Part": "a", + "Vendor": "octobercms", + "Product": "october", + "Version": "1.0.73", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ceph:ceph-ansible:4.0.34.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ceph:ceph-ansible:4.0.34.2", + "wfn": { + "Part": "a", + "Vendor": "ceph", + "Product": "ceph-ansible", + "Version": "4.0.34.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:cisco:asr_920-12sz-im_r:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:cisco:asr_920-12sz-im_r:-", + "wfn": { + "Part": "h", + "Vendor": "cisco", + "Product": "asr_920-12sz-im_r", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apple:quicktime:7.3.0:-:mac:*:*:*:*:*", + "cpe-url": "cpe:/a:apple:quicktime:7.3.0:-:mac", + "wfn": { + "Part": "a", + "Vendor": "apple", + "Product": "quicktime", + "Version": "7.3.0", + "Update": "-", + "Edition": "mac", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openpgpjs:openpgpjs:3.0.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openpgpjs:openpgpjs:3.0.4", + "wfn": { + "Part": "a", + "Vendor": "openpgpjs", + "Product": "openpgpjs", + "Version": "3.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:electronjs:electron:11.0.0:beta15:*:*:*:*:*:*", + "cpe-url": "cpe:/a:electronjs:electron:11.0.0:beta15", + "wfn": { + "Part": "a", + "Vendor": "electronjs", + "Product": "electron", + "Version": "11.0.0", + "Update": "beta15", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:invensys:wonderware_application_server:2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:invensys:wonderware_application_server:2.1", + "wfn": { + "Part": "a", + "Vendor": "invensys", + "Product": "wonderware_application_server", + "Version": "2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:contest_gallery:contest_gallery:1.18:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:contest_gallery:contest_gallery:1.18::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "contest_gallery", + "Product": "contest_gallery", + "Version": "1.18", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pajbot_project:pajbot:1.49:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pajbot_project:pajbot:1.49", + "wfn": { + "Part": "a", + "Vendor": "pajbot_project", + "Product": "pajbot", + "Version": "1.49", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:iobroker:iobroker.admin:3.5.1:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:iobroker:iobroker.admin:3.5.1::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "iobroker", + "Product": "iobroker.admin", + "Version": "3.5.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:maximo_for_oil_and_gas:7.5.0.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:maximo_for_oil_and_gas:7.5.0.4", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "maximo_for_oil_and_gas", + "Version": "7.5.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:firepower_management_center_firmware:6.0.0.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:firepower_management_center_firmware:6.0.0.0", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "firepower_management_center_firmware", + "Version": "6.0.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:adobe:acrobat_reader_dc:15.000.0000:*:*:*:classic:*:*:*", + "cpe-url": "cpe:/a:adobe:acrobat_reader_dc:15.000.0000::~~classic~~~", + "wfn": { + "Part": "a", + "Vendor": "adobe", + "Product": "acrobat_reader_dc", + "Version": "15.000.0000", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "classic", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:node-postgres:pg:0.10.0:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:node-postgres:pg:0.10.0::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "node-postgres", + "Product": "pg", + "Version": "0.10.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:infolific:real-time_find_and_replace:4.0.2:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:infolific:real-time_find_and_replace:4.0.2::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "infolific", + "Product": "real-time_find_and_replace", + "Version": "4.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:asyncos:11.1:hot_patch2:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:asyncos:11.1:hot_patch2", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "asyncos", + "Version": "11.1", + "Update": "hot_patch2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:nx-os:7.0\\(3\\)i3\\(0.170\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:nx-os:7.0%283%29i3%280.170%29", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "nx-os", + "Version": "7.0(3)i3(0.170)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:skype:skype:3.0.0.198:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:skype:skype:3.0.0.198", + "wfn": { + "Part": "a", + "Vendor": "skype", + "Product": "skype", + "Version": "3.0.0.198", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sap:gui:7.70:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sap:gui:7.70:-", + "wfn": { + "Part": "a", + "Vendor": "sap", + "Product": "gui", + "Version": "7.70", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:0231a65t:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:0231a65t:-", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "0231a65t", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:progress:mixlib-archive:1.0.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:progress:mixlib-archive:1.0.7", + "wfn": { + "Part": "a", + "Vendor": "progress", + "Product": "mixlib-archive", + "Version": "1.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tuxfamily:chrony:1.28:pre1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tuxfamily:chrony:1.28:pre1", + "wfn": { + "Part": "a", + "Vendor": "tuxfamily", + "Product": "chrony", + "Version": "1.28", + "Update": "pre1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:custom_search_project:custom_search:6.x-1.10:*:*:*:*:drupal:*:*", + "cpe-url": "cpe:/a:custom_search_project:custom_search:6.x-1.10::~~~drupal~~", + "wfn": { + "Part": "a", + "Vendor": "custom_search_project", + "Product": "custom_search", + "Version": "6.x-1.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "drupal", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:dpl:product_feed_on_woocommerce_for_google\\,_awin\\,_shareasale\\,_bing\\,_and_more:3.5.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:dpl:product_feed_on_woocommerce_for_google%2c_awin%2c_shareasale%2c_bing%2c_and_more:3.5.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "dpl", + "Product": "product_feed_on_woocommerce_for_google,_awin,_shareasale,_bing,_and_more", + "Version": "3.5.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:pureapplication_system:2.1.2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:pureapplication_system:2.1.2.1", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "pureapplication_system", + "Version": "2.1.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:traefik:traefik:2.3.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:traefik:traefik:2.3.4", + "wfn": { + "Part": "a", + "Vendor": "traefik", + "Product": "traefik", + "Version": "2.3.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.3.662:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.3.662", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.3.662", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:i-doit:i-doit:1.10.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:i-doit:i-doit:1.10.2", + "wfn": { + "Part": "a", + "Vendor": "i-doit", + "Product": "i-doit", + "Version": "1.10.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:supsystic:photo_gallery:1.2.6:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:supsystic:photo_gallery:1.2.6::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "supsystic", + "Product": "photo_gallery", + "Version": "1.2.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:elastic:kibana:1.0.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:elastic:kibana:1.0.0:-", + "wfn": { + "Part": "a", + "Vendor": "elastic", + "Product": "kibana", + "Version": "1.0.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tgstation13:tgstation-server:4.0.1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tgstation13:tgstation-server:4.0.1.0", + "wfn": { + "Part": "a", + "Vendor": "tgstation13", + "Product": "tgstation-server", + "Version": "4.0.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:2checkout:ithemes_2checkout:-:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:2checkout:ithemes_2checkout:-::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "2checkout", + "Product": "ithemes_2checkout", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:dbd-mysql_project:dbd-mysql:4.022:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:dbd-mysql_project:dbd-mysql:4.022", + "wfn": { + "Part": "a", + "Vendor": "dbd-mysql_project", + "Product": "dbd-mysql", + "Version": "4.022", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jruby:jruby:1.5.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:jruby:jruby:1.5.6", + "wfn": { + "Part": "a", + "Vendor": "jruby", + "Product": "jruby", + "Version": "1.5.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:alchemy-cms:alchemy_cms:3.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:alchemy-cms:alchemy_cms:3.0.1", + "wfn": { + "Part": "a", + "Vendor": "alchemy-cms", + "Product": "alchemy_cms", + "Version": "3.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rankmath:seo:1.0.9:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:rankmath:seo:1.0.9::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "rankmath", + "Product": "seo", + "Version": "1.0.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:media_library_assistant_project:media_library_assistant:2.54:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:media_library_assistant_project:media_library_assistant:2.54::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "media_library_assistant_project", + "Product": "media_library_assistant", + "Version": "2.54", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:theforeman:katello:0.1.209-1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:theforeman:katello:0.1.209-1", + "wfn": { + "Part": "a", + "Vendor": "theforeman", + "Product": "katello", + "Version": "0.1.209-1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fancybox_project:fancybox:3.0.2:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:fancybox_project:fancybox:3.0.2::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "fancybox_project", + "Product": "fancybox", + "Version": "3.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wp_domain_redirect_project:wp_domain_redirect:1.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wp_domain_redirect_project:wp_domain_redirect:1.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wp_domain_redirect_project", + "Product": "wp_domain_redirect", + "Version": "1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:xen-orchestra:xen_orchestra_server:5.10.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:xen-orchestra:xen_orchestra_server:5.10.2", + "wfn": { + "Part": "a", + "Vendor": "xen-orchestra", + "Product": "xen_orchestra_server", + "Version": "5.10.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:databaseschemaviewer_project:dbschemareader:2.7.4.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:databaseschemaviewer_project:dbschemareader:2.7.4.3", + "wfn": { + "Part": "a", + "Vendor": "databaseschemaviewer_project", + "Product": "dbschemareader", + "Version": "2.7.4.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:intel:converged_security_and_manageability_engine:11.22.86:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:intel:converged_security_and_manageability_engine:11.22.86", + "wfn": { + "Part": "a", + "Vendor": "intel", + "Product": "converged_security_and_manageability_engine", + "Version": "11.22.86", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fujitsu:interstage_application_server:9.1.0:*:*:*:enterprise:*:*:*", + "cpe-url": "cpe:/a:fujitsu:interstage_application_server:9.1.0::~~enterprise~~~", + "wfn": { + "Part": "a", + "Vendor": "fujitsu", + "Product": "interstage_application_server", + "Version": "9.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "enterprise", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:libinfinity_project:libinfinity:0.5.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:libinfinity_project:libinfinity:0.5.2", + "wfn": { + "Part": "a", + "Vendor": "libinfinity_project", + "Product": "libinfinity", + "Version": "0.5.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:macpaw:cleanmymac_x:3.8.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:macpaw:cleanmymac_x:3.8.3", + "wfn": { + "Part": "a", + "Vendor": "macpaw", + "Product": "cleanmymac_x", + "Version": "3.8.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pacman_project:pacman:3.2.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pacman_project:pacman:3.2.0", + "wfn": { + "Part": "a", + "Vendor": "pacman_project", + "Product": "pacman", + "Version": "3.2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:tensorflow:2.1.0:-:*:*:lite:*:*:*", + "cpe-url": "cpe:/a:google:tensorflow:2.1.0:-:~~lite~~~", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "tensorflow", + "Version": "2.1.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "lite", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apple:apple_application_support:1.4.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apple:apple_application_support:1.4.1", + "wfn": { + "Part": "a", + "Vendor": "apple", + "Product": "apple_application_support", + "Version": "1.4.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:schneider-electric:bmep582040s_firmware:2.90:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:schneider-electric:bmep582040s_firmware:2.90", + "wfn": { + "Part": "o", + "Vendor": "schneider-electric", + "Product": "bmep582040s_firmware", + "Version": "2.90", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:morequick:greenbrowser:6.1.0117:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:morequick:greenbrowser:6.1.0117", + "wfn": { + "Part": "a", + "Vendor": "morequick", + "Product": "greenbrowser", + "Version": "6.1.0117", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:freebsd:freebsd:9.3:p43:*:*:*:*:*:*", + "cpe-url": "cpe:/a:freebsd:freebsd:9.3:p43", + "wfn": { + "Part": "a", + "Vendor": "freebsd", + "Product": "freebsd", + "Version": "9.3", + "Update": "p43", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:yamaha:rtv700:8.00.81:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:yamaha:rtv700:8.00.81", + "wfn": { + "Part": "o", + "Vendor": "yamaha", + "Product": "rtv700", + "Version": "8.00.81", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:trihedral:vtscada:11.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:trihedral:vtscada:11.2", + "wfn": { + "Part": "a", + "Vendor": "trihedral", + "Product": "vtscada", + "Version": "11.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnome:gtk:0.99.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnome:gtk:0.99.3", + "wfn": { + "Part": "a", + "Vendor": "gnome", + "Product": "gtk", + "Version": "0.99.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:qpdf_project:qpdf:2.3.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:qpdf_project:qpdf:2.3.0", + "wfn": { + "Part": "a", + "Vendor": "qpdf_project", + "Product": "qpdf", + "Version": "2.3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:klibc_project:klibc:0.121:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:klibc_project:klibc:0.121", + "wfn": { + "Part": "a", + "Vendor": "klibc_project", + "Product": "klibc", + "Version": "0.121", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kunena:kunena:4.0.4:*:*:*:*:joomla\\!:*:*", + "cpe-url": "cpe:/a:kunena:kunena:4.0.4::~~~joomla%21~~", + "wfn": { + "Part": "a", + "Vendor": "kunena", + "Product": "kunena", + "Version": "4.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "joomla!", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:tp-link:tl-wr840n_firmware:3.13.27:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:tp-link:tl-wr840n_firmware:3.13.27", + "wfn": { + "Part": "o", + "Vendor": "tp-link", + "Product": "tl-wr840n_firmware", + "Version": "3.13.27", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:slf4j:slf4j-jdk14:1.6.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:slf4j:slf4j-jdk14:1.6.2", + "wfn": { + "Part": "a", + "Vendor": "slf4j", + "Product": "slf4j-jdk14", + "Version": "1.6.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nextscripts:social_networks_auto_poster:4.2.0:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:nextscripts:social_networks_auto_poster:4.2.0::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "nextscripts", + "Product": "social_networks_auto_poster", + "Version": "4.2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:koha:koha:16.05.03:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:koha:koha:16.05.03", + "wfn": { + "Part": "a", + "Vendor": "koha", + "Product": "koha", + "Version": "16.05.03", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:opennms:opennms:25.2.1-1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:opennms:opennms:25.2.1-1", + "wfn": { + "Part": "a", + "Vendor": "opennms", + "Product": "opennms", + "Version": "25.2.1-1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:formidableforms:formidable:3.03.01:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:formidableforms:formidable:3.03.01::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "formidableforms", + "Product": "formidable", + "Version": "3.03.01", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:lftp_project:lftp:2.4.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:lftp_project:lftp:2.4.2", + "wfn": { + "Part": "a", + "Vendor": "lftp_project", + "Product": "lftp", + "Version": "2.4.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:bitcoin:bitcoin:0.13.0:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:bitcoin:bitcoin:0.13.0:rc1", + "wfn": { + "Part": "a", + "Vendor": "bitcoin", + "Product": "bitcoin", + "Version": "0.13.0", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:groovy:3.0.0:alpha1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:groovy:3.0.0:alpha1", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "groovy", + "Version": "3.0.0", + "Update": "alpha1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:phoenix_media_rename_project:phoenix_media_rename:2.0.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:phoenix_media_rename_project:phoenix_media_rename:2.0.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "phoenix_media_rename_project", + "Product": "phoenix_media_rename", + "Version": "2.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pivotal_software:operations_manager:1.12.20:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pivotal_software:operations_manager:1.12.20", + "wfn": { + "Part": "a", + "Vendor": "pivotal_software", + "Product": "operations_manager", + "Version": "1.12.20", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:phpcheckz:phpcheckz:0.4.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:phpcheckz:phpcheckz:0.4.2", + "wfn": { + "Part": "a", + "Vendor": "phpcheckz", + "Product": "phpcheckz", + "Version": "0.4.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloudfoundry:credhub:1.9.10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cloudfoundry:credhub:1.9.10", + "wfn": { + "Part": "a", + "Vendor": "cloudfoundry", + "Product": "credhub", + "Version": "1.9.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gleamtech:filevista:5.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gleamtech:filevista:5.0.1", + "wfn": { + "Part": "a", + "Vendor": "gleamtech", + "Product": "filevista", + "Version": "5.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openvcloud_project:openvcloud:2.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openvcloud_project:openvcloud:2.0.1", + "wfn": { + "Part": "a", + "Vendor": "openvcloud_project", + "Product": "openvcloud", + "Version": "2.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpseeds:wp_database_backup:5.3:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpseeds:wp_database_backup:5.3::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpseeds", + "Product": "wp_database_backup", + "Version": "5.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:owasp:owasp_modsecurity_core_rule_set:3.0.0:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:owasp:owasp_modsecurity_core_rule_set:3.0.0:rc1", + "wfn": { + "Part": "a", + "Vendor": "owasp", + "Product": "owasp_modsecurity_core_rule_set", + "Version": "3.0.0", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:four_kitchens:block_class:7.x-2.x:dev:*:*:*:drupal:*:*", + "cpe-url": "cpe:/a:four_kitchens:block_class:7.x-2.x:dev:~~~drupal~~", + "wfn": { + "Part": "a", + "Vendor": "four_kitchens", + "Product": "block_class", + "Version": "7.x-2.x", + "Update": "dev", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "drupal", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mediacoderhq:mediacoder:0.8.5800:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mediacoderhq:mediacoder:0.8.5800", + "wfn": { + "Part": "a", + "Vendor": "mediacoderhq", + "Product": "mediacoder", + "Version": "0.8.5800", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:minimagick_project:minimagick:4.7.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:minimagick_project:minimagick:4.7.0", + "wfn": { + "Part": "a", + "Vendor": "minimagick_project", + "Product": "minimagick", + "Version": "4.7.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:phpmyadmin:phpmyadmin:4.1.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:phpmyadmin:phpmyadmin:4.1.7", + "wfn": { + "Part": "a", + "Vendor": "phpmyadmin", + "Product": "phpmyadmin", + "Version": "4.1.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:logitech:harmony_hub:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:logitech:harmony_hub:-", + "wfn": { + "Part": "h", + "Vendor": "logitech", + "Product": "harmony_hub", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:ecessa:shieldlink_sl175ehq_firmware:8.0.19:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:ecessa:shieldlink_sl175ehq_firmware:8.0.19", + "wfn": { + "Part": "o", + "Vendor": "ecessa", + "Product": "shieldlink_sl175ehq_firmware", + "Version": "8.0.19", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:octopus:octopus_deploy:2018.12.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:octopus:octopus_deploy:2018.12.1", + "wfn": { + "Part": "a", + "Vendor": "octopus", + "Product": "octopus_deploy", + "Version": "2018.12.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:alpinelinux:abuild:2.27.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:alpinelinux:abuild:2.27.0", + "wfn": { + "Part": "a", + "Vendor": "alpinelinux", + "Product": "abuild", + "Version": "2.27.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:amazon:freertos:1.2.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:amazon:freertos:1.2.0", + "wfn": { + "Part": "o", + "Vendor": "amazon", + "Product": "freertos", + "Version": "1.2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:microsoft:systems_management_server:1.2:sp3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:microsoft:systems_management_server:1.2:sp3", + "wfn": { + "Part": "a", + "Vendor": "microsoft", + "Product": "systems_management_server", + "Version": "1.2", + "Update": "sp3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:netty:netty:4.1.15:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:netty:netty:4.1.15", + "wfn": { + "Part": "a", + "Vendor": "netty", + "Product": "netty", + "Version": "4.1.15", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ntp:ntp:4.0.97:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ntp:ntp:4.0.97", + "wfn": { + "Part": "a", + "Vendor": "ntp", + "Product": "ntp", + "Version": "4.0.97", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:spss_statistics:24.0.0.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:spss_statistics:24.0.0.0", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "spss_statistics", + "Version": "24.0.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fenrir-inc:sleipnir_mobile:2.1.0:*:*:*:-:android:*:*", + "cpe-url": "cpe:/a:fenrir-inc:sleipnir_mobile:2.1.0::~~-~android~~", + "wfn": { + "Part": "a", + "Vendor": "fenrir-inc", + "Product": "sleipnir_mobile", + "Version": "2.1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "-", + "TargetSw": "android", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:phoenixcontact:fl_switch_4008t-2gt-3fx_sm_firmware:1.21:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:phoenixcontact:fl_switch_4008t-2gt-3fx_sm_firmware:1.21", + "wfn": { + "Part": "o", + "Vendor": "phoenixcontact", + "Product": "fl_switch_4008t-2gt-3fx_sm_firmware", + "Version": "1.21", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wp_svg_icons_project:wp_svg_icons:3.1.8.4:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wp_svg_icons_project:wp_svg_icons:3.1.8.4::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wp_svg_icons_project", + "Product": "wp_svg_icons", + "Version": "3.1.8.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:facebook:hiphop_virtual_machine:3.13.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:facebook:hiphop_virtual_machine:3.13.0", + "wfn": { + "Part": "a", + "Vendor": "facebook", + "Product": "hiphop_virtual_machine", + "Version": "3.13.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jetbrains:kotlin:1.4.0:dev458:*:*:*:*:*:*", + "cpe-url": "cpe:/a:jetbrains:kotlin:1.4.0:dev458", + "wfn": { + "Part": "a", + "Vendor": "jetbrains", + "Product": "kotlin", + "Version": "1.4.0", + "Update": "dev458", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:linux:linux_kernel:2.6.13.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:linux:linux_kernel:2.6.13.2", + "wfn": { + "Part": "o", + "Vendor": "linux", + "Product": "linux_kernel", + "Version": "2.6.13.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:chef:chef:14.0.217:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:chef:chef:14.0.217", + "wfn": { + "Part": "a", + "Vendor": "chef", + "Product": "chef", + "Version": "14.0.217", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:get-simple:getsimple_cms:3.3.14:b1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:get-simple:getsimple_cms:3.3.14:b1", + "wfn": { + "Part": "a", + "Vendor": "get-simple", + "Product": "getsimple_cms", + "Version": "3.3.14", + "Update": "b1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tcl:tcl:8.4.16:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tcl:tcl:8.4.16", + "wfn": { + "Part": "a", + "Vendor": "tcl", + "Product": "tcl", + "Version": "8.4.16", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gogs:gogs:0.6.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gogs:gogs:0.6.9", + "wfn": { + "Part": "a", + "Vendor": "gogs", + "Product": "gogs", + "Version": "0.6.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:postsrsd_prject:postsrsd:1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:postsrsd_prject:postsrsd:1.0", + "wfn": { + "Part": "a", + "Vendor": "postsrsd_prject", + "Product": "postsrsd", + "Version": "1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:axis:c8033_firmware:1.81.040.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:axis:c8033_firmware:1.81.040.1", + "wfn": { + "Part": "o", + "Vendor": "axis", + "Product": "c8033_firmware", + "Version": "1.81.040.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:huawei:mate_10_pro_firmware:bla-l29_8.0.0.148\\(c432\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:huawei:mate_10_pro_firmware:bla-l29_8.0.0.148%28c432%29", + "wfn": { + "Part": "o", + "Vendor": "huawei", + "Product": "mate_10_pro_firmware", + "Version": "bla-l29_8.0.0.148(c432)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:netsarang:xshell:7:build_0065:*:*:*:*:*:*", + "cpe-url": "cpe:/a:netsarang:xshell:7:build_0065", + "wfn": { + "Part": "a", + "Vendor": "netsarang", + "Product": "xshell", + "Version": "7", + "Update": "build_0065", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpdatatables:wpdatatables:2.0.16:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpdatatables:wpdatatables:2.0.16::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpdatatables", + "Product": "wpdatatables", + "Version": "2.0.16", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:clusterlabs:pacemaker:2.0.2:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:clusterlabs:pacemaker:2.0.2:-", + "wfn": { + "Part": "a", + "Vendor": "clusterlabs", + "Product": "pacemaker", + "Version": "2.0.2", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:swi-prolog:swi-prolog:5.4.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:swi-prolog:swi-prolog:5.4.2", + "wfn": { + "Part": "a", + "Vendor": "swi-prolog", + "Product": "swi-prolog", + "Version": "5.4.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wftpserver:wing_ftp_server:3.9.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wftpserver:wing_ftp_server:3.9.0", + "wfn": { + "Part": "a", + "Vendor": "wftpserver", + "Product": "wing_ftp_server", + "Version": "3.9.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpplugin:accept_donations_with_paypal:1.2.5:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpplugin:accept_donations_with_paypal:1.2.5::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpplugin", + "Product": "accept_donations_with_paypal", + "Version": "1.2.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:abcm2ps_project:abcm2ps:8.14.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:abcm2ps_project:abcm2ps:8.14.3", + "wfn": { + "Part": "a", + "Vendor": "abcm2ps_project", + "Product": "abcm2ps", + "Version": "8.14.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:episerver:ektron_cms:8.00:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:episerver:ektron_cms:8.00:-", + "wfn": { + "Part": "a", + "Vendor": "episerver", + "Product": "ektron_cms", + "Version": "8.00", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:laserjet_managed_e85055_t3u51a:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:laserjet_managed_e85055_t3u51a:-", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "laserjet_managed_e85055_t3u51a", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wallabag:wallabag:2.0.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wallabag:wallabag:2.0.0:-", + "wfn": { + "Part": "a", + "Vendor": "wallabag", + "Product": "wallabag", + "Version": "2.0.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:google:chrome:13.0.752.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:google:chrome:13.0.752.0", + "wfn": { + "Part": "a", + "Vendor": "google", + "Product": "chrome", + "Version": "13.0.752.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:intel:xeon_e5-2430_v2_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:intel:xeon_e5-2430_v2_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "intel", + "Product": "xeon_e5-2430_v2_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:url-parse_project:url-parse:1.4.3:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:url-parse_project:url-parse:1.4.3::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "url-parse_project", + "Product": "url-parse", + "Version": "1.4.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:crear.ne.jp:al-mail32:1.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:crear.ne.jp:al-mail32:1.11", + "wfn": { + "Part": "a", + "Vendor": "crear.ne.jp", + "Product": "al-mail32", + "Version": "1.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:triplea-game:triplea:1.9.0.0.12537:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:triplea-game:triplea:1.9.0.0.12537", + "wfn": { + "Part": "a", + "Vendor": "triplea-game", + "Product": "triplea", + "Version": "1.9.0.0.12537", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:yithemes:yith_woocommerce_request_a_quote:1.6.2:*:*:*:premium:wordpress:*:*", + "cpe-url": "cpe:/a:yithemes:yith_woocommerce_request_a_quote:1.6.2::~~premium~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "yithemes", + "Product": "yith_woocommerce_request_a_quote", + "Version": "1.6.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "premium", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:eucalyptus:eucalyptus:3.0.0:beta2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:eucalyptus:eucalyptus:3.0.0:beta2", + "wfn": { + "Part": "a", + "Vendor": "eucalyptus", + "Product": "eucalyptus", + "Version": "3.0.0", + "Update": "beta2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:strategy11:formidable_form_builder:4.0.03:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:strategy11:formidable_form_builder:4.0.03::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "strategy11", + "Product": "formidable_form_builder", + "Version": "4.0.03", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:dhcpcd_project:dhcpcd:6.9.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:dhcpcd_project:dhcpcd:6.9.1", + "wfn": { + "Part": "a", + "Vendor": "dhcpcd_project", + "Product": "dhcpcd", + "Version": "6.9.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rocket.chat:rocket.chat:3.4.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:rocket.chat:rocket.chat:3.4.0:-", + "wfn": { + "Part": "a", + "Vendor": "rocket.chat", + "Product": "rocket.chat", + "Version": "3.4.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:fujitsu:m12-2_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:fujitsu:m12-2_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "fujitsu", + "Product": "m12-2_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:hp:proliant_bl460c_firmware:2.20:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:hp:proliant_bl460c_firmware:2.20", + "wfn": { + "Part": "o", + "Vendor": "hp", + "Product": "proliant_bl460c_firmware", + "Version": "2.20", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openjsf:express:4.11.1:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:openjsf:express:4.11.1::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "openjsf", + "Product": "express", + "Version": "4.11.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:huawei:usg2220bsr_firmware:v300r001c00:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:huawei:usg2220bsr_firmware:v300r001c00", + "wfn": { + "Part": "o", + "Vendor": "huawei", + "Product": "usg2220bsr_firmware", + "Version": "v300r001c00", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:10web:photo_gallery:1.3.67:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:10web:photo_gallery:1.3.67::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "10web", + "Product": "photo_gallery", + "Version": "1.3.67", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:express-gateway:express-gateway_docker_image:1.16.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:express-gateway:express-gateway_docker_image:1.16.3", + "wfn": { + "Part": "a", + "Vendor": "express-gateway", + "Product": "express-gateway_docker_image", + "Version": "1.16.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:zyxel:gs1900-24ep:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:zyxel:gs1900-24ep:-", + "wfn": { + "Part": "h", + "Vendor": "zyxel", + "Product": "gs1900-24ep", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:llvm:compiler:2.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:llvm:compiler:2.2", + "wfn": { + "Part": "a", + "Vendor": "llvm", + "Product": "compiler", + "Version": "2.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:qos:logback:0.9.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:qos:logback:0.9.2", + "wfn": { + "Part": "a", + "Vendor": "qos", + "Product": "logback", + "Version": "0.9.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sap:openui5:1.63.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sap:openui5:1.63.0", + "wfn": { + "Part": "a", + "Vendor": "sap", + "Product": "openui5", + "Version": "1.63.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sugarcrm:sugarcrm:6.5.8:*:*:*:community:*:*:*", + "cpe-url": "cpe:/a:sugarcrm:sugarcrm:6.5.8::~~community~~~", + "wfn": { + "Part": "a", + "Vendor": "sugarcrm", + "Product": "sugarcrm", + "Version": "6.5.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "community", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wordpress:wordpress:4.1:rc3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wordpress:wordpress:4.1:rc3", + "wfn": { + "Part": "a", + "Vendor": "wordpress", + "Product": "wordpress", + "Version": "4.1", + "Update": "rc3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:psutil_project:psutil:5.4.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:psutil_project:psutil:5.4.4", + "wfn": { + "Part": "a", + "Vendor": "psutil_project", + "Product": "psutil", + "Version": "5.4.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:adobe:flash_player:11.2.202.291:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:adobe:flash_player:11.2.202.291", + "wfn": { + "Part": "a", + "Vendor": "adobe", + "Product": "flash_player", + "Version": "11.2.202.291", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:horde:kronolith:3.0.15:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:horde:kronolith:3.0.15", + "wfn": { + "Part": "a", + "Vendor": "horde", + "Product": "kronolith", + "Version": "3.0.15", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gitlab:gitlab:9.4.0:*:*:*:-:*:*:*", + "cpe-url": "cpe:/a:gitlab:gitlab:9.4.0::~~-~~~", + "wfn": { + "Part": "a", + "Vendor": "gitlab", + "Product": "gitlab", + "Version": "9.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "-", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:microsoft:windows_8:-:-:x86:*:*:*:*:*", + "cpe-url": "cpe:/o:microsoft:windows_8:-:-:x86", + "wfn": { + "Part": "o", + "Vendor": "microsoft", + "Product": "windows_8", + "Version": "-", + "Update": "-", + "Edition": "x86", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:emberjs:ember.js:3.11.0:beta1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:emberjs:ember.js:3.11.0:beta1", + "wfn": { + "Part": "a", + "Vendor": "emberjs", + "Product": "ember.js", + "Version": "3.11.0", + "Update": "beta1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:8.0.1587:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:8.0.1587", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "8.0.1587", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cloudera:cloudera_manager:5.13.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cloudera:cloudera_manager:5.13.4", + "wfn": { + "Part": "a", + "Vendor": "cloudera", + "Product": "cloudera_manager", + "Version": "5.13.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:git-scm:git:1.5.5:rc3:*:*:*:*:*:*", + "cpe-url": "cpe:/a:git-scm:git:1.5.5:rc3", + "wfn": { + "Part": "a", + "Vendor": "git-scm", + "Product": "git", + "Version": "1.5.5", + "Update": "rc3", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:coder:code-server:3.9.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:coder:code-server:3.9.1", + "wfn": { + "Part": "a", + "Vendor": "coder", + "Product": "code-server", + "Version": "3.9.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:piwik:piwik:0.2.19:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:piwik:piwik:0.2.19", + "wfn": { + "Part": "a", + "Vendor": "piwik", + "Product": "piwik", + "Version": "0.2.19", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openconext:openconext_engineblock:3.0.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:openconext:openconext_engineblock:3.0.0", + "wfn": { + "Part": "a", + "Vendor": "openconext", + "Product": "openconext_engineblock", + "Version": "3.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:isc:bind:9.8.0:p1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:isc:bind:9.8.0:p1", + "wfn": { + "Part": "a", + "Vendor": "isc", + "Product": "bind", + "Version": "9.8.0", + "Update": "p1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wordfence:wordfence_security:5.0.3:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wordfence:wordfence_security:5.0.3::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wordfence", + "Product": "wordfence_security", + "Version": "5.0.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:canon:eos_m5_firmware:1.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:canon:eos_m5_firmware:1.0.1", + "wfn": { + "Part": "o", + "Vendor": "canon", + "Product": "eos_m5_firmware", + "Version": "1.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:dell:poweredge_r940xa_firmware:2.11.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:dell:poweredge_r940xa_firmware:2.11.2", + "wfn": { + "Part": "o", + "Vendor": "dell", + "Product": "poweredge_r940xa_firmware", + "Version": "2.11.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:litespeedtech:litespeed_cache:1.0.9:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:litespeedtech:litespeed_cache:1.0.9::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "litespeedtech", + "Product": "litespeed_cache", + "Version": "1.0.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:koha:koha:3.20.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:koha:koha:3.20.11", + "wfn": { + "Part": "a", + "Vendor": "koha", + "Product": "koha", + "Version": "3.20.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:elasticsearch:kibana:5.2.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:elasticsearch:kibana:5.2.2", + "wfn": { + "Part": "a", + "Vendor": "elasticsearch", + "Product": "kibana", + "Version": "5.2.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:sony:nw-a47:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:sony:nw-a47:-", + "wfn": { + "Part": "h", + "Vendor": "sony", + "Product": "nw-a47", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:puma:puma:4.3.4:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:puma:puma:4.3.4::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "puma", + "Product": "puma", + "Version": "4.3.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:modx:revolution:2.3.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:modx:revolution:2.3.0", + "wfn": { + "Part": "a", + "Vendor": "modx", + "Product": "revolution", + "Version": "2.3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:denx:u-boot:2017.05:rc2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:denx:u-boot:2017.05:rc2", + "wfn": { + "Part": "a", + "Vendor": "denx", + "Product": "u-boot", + "Version": "2017.05", + "Update": "rc2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:blubrry:powerpress:1.0.10:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:blubrry:powerpress:1.0.10::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "blubrry", + "Product": "powerpress", + "Version": "1.0.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlassian:editor-core:72.1.13:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:atlassian:editor-core:72.1.13::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "atlassian", + "Product": "editor-core", + "Version": "72.1.13", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:silanis:approveit_desktop:7.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:silanis:approveit_desktop:7.3", + "wfn": { + "Part": "a", + "Vendor": "silanis", + "Product": "approveit_desktop", + "Version": "7.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:telerik:ui_for_asp.net_core:2014.2.903:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:telerik:ui_for_asp.net_core:2014.2.903", + "wfn": { + "Part": "a", + "Vendor": "telerik", + "Product": "ui_for_asp.net_core", + "Version": "2014.2.903", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:serve-here.js_project:serve-here.js:1.1.3:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:serve-here.js_project:serve-here.js:1.1.3::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "serve-here.js_project", + "Product": "serve-here.js", + "Version": "1.1.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ios:11.1\\(24c\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ios:11.1%2824c%29", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ios", + "Version": "11.1(24c)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:netgear:jgs524pe:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:netgear:jgs524pe:-", + "wfn": { + "Part": "h", + "Vendor": "netgear", + "Product": "jgs524pe", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:facebook:nuclide:0.182.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:facebook:nuclide:0.182.0", + "wfn": { + "Part": "a", + "Vendor": "facebook", + "Product": "nuclide", + "Version": "0.182.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:unified_customer_voice_portal:9.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:unified_customer_voice_portal:9.0", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "unified_customer_voice_portal", + "Version": "9.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sap:ui5:1.52.28:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sap:ui5:1.52.28", + "wfn": { + "Part": "a", + "Vendor": "sap", + "Product": "ui5", + "Version": "1.52.28", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:encs_5400_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:encs_5400_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "encs_5400_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:alpinelinux:aports:3.0.5:*:*:*:*:alpine:*:*", + "cpe-url": "cpe:/a:alpinelinux:aports:3.0.5::~~~alpine~~", + "wfn": { + "Part": "a", + "Vendor": "alpinelinux", + "Product": "aports", + "Version": "3.0.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "alpine", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:soliddb:6.3.53:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:soliddb:6.3.53", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "soliddb", + "Version": "6.3.53", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:lenovo:yoga_530-14ikb_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:lenovo:yoga_530-14ikb_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "lenovo", + "Product": "yoga_530-14ikb_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:red-gate:smartassembly:6.6.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:red-gate:smartassembly:6.6.3", + "wfn": { + "Part": "a", + "Vendor": "red-gate", + "Product": "smartassembly", + "Version": "6.6.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:underscorejs:underscore:1.3.2:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:underscorejs:underscore:1.3.2::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "underscorejs", + "Product": "underscore", + "Version": "1.3.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wp-property-hive:propertyhive:1.4.10:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wp-property-hive:propertyhive:1.4.10::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wp-property-hive", + "Product": "propertyhive", + "Version": "1.4.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:socusoft:flash_slideshow_maker:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:socusoft:flash_slideshow_maker:-", + "wfn": { + "Part": "a", + "Vendor": "socusoft", + "Product": "flash_slideshow_maker", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rimarts:becky\\!_internet_mail:2.20.01:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:rimarts:becky%21_internet_mail:2.20.01", + "wfn": { + "Part": "a", + "Vendor": "rimarts", + "Product": "becky!_internet_mail", + "Version": "2.20.01", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:invoiceninja:invoice_ninja:2.3.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:invoiceninja:invoice_ninja:2.3.1", + "wfn": { + "Part": "a", + "Vendor": "invoiceninja", + "Product": "invoice_ninja", + "Version": "2.3.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:cisco:telepresence_system_500-37:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:cisco:telepresence_system_500-37:-", + "wfn": { + "Part": "h", + "Vendor": "cisco", + "Product": "telepresence_system_500-37", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:autohotkey:autohotkey:1.1.30.00:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:autohotkey:autohotkey:1.1.30.00", + "wfn": { + "Part": "a", + "Vendor": "autohotkey", + "Product": "autohotkey", + "Version": "1.1.30.00", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nih:ncbi_toolbox:2.2.26:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nih:ncbi_toolbox:2.2.26", + "wfn": { + "Part": "a", + "Vendor": "nih", + "Product": "ncbi_toolbox", + "Version": "2.2.26", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:xnview:xnview:1.99:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:xnview:xnview:1.99", + "wfn": { + "Part": "a", + "Vendor": "xnview", + "Product": "xnview", + "Version": "1.99", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kernel:util-linux:2.25:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:kernel:util-linux:2.25", + "wfn": { + "Part": "a", + "Vendor": "kernel", + "Product": "util-linux", + "Version": "2.25", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:hp:0231a65t:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:hp:0231a65t:-", + "wfn": { + "Part": "h", + "Vendor": "hp", + "Product": "0231a65t", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pgp:e-business_server:7.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pgp:e-business_server:7.1", + "wfn": { + "Part": "a", + "Vendor": "pgp", + "Product": "e-business_server", + "Version": "7.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:electronjs:electron:10.0.0:beta9:*:*:*:*:*:*", + "cpe-url": "cpe:/a:electronjs:electron:10.0.0:beta9", + "wfn": { + "Part": "a", + "Vendor": "electronjs", + "Product": "electron", + "Version": "10.0.0", + "Update": "beta9", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:libpng:libpng:1.6.23:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:libpng:libpng:1.6.23", + "wfn": { + "Part": "a", + "Vendor": "libpng", + "Product": "libpng", + "Version": "1.6.23", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:smackcoders:ultimate_csv_importer:3.2.3:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:smackcoders:ultimate_csv_importer:3.2.3::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "smackcoders", + "Product": "ultimate_csv_importer", + "Version": "3.2.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:cordova:1.8.1:*:*:*:*:android:*:*", + "cpe-url": "cpe:/a:apache:cordova:1.8.1::~~~android~~", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "cordova", + "Version": "1.8.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "android", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redhat:ansible:2.8.0:-:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redhat:ansible:2.8.0:-", + "wfn": { + "Part": "a", + "Vendor": "redhat", + "Product": "ansible", + "Version": "2.8.0", + "Update": "-", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:intel:xeon_e7-8860_v4:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:intel:xeon_e7-8860_v4:-", + "wfn": { + "Part": "a", + "Vendor": "intel", + "Product": "xeon_e7-8860_v4", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:misskey:misskey:10.82.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:misskey:misskey:10.82.3", + "wfn": { + "Part": "a", + "Vendor": "misskey", + "Product": "misskey", + "Version": "10.82.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sprockets_project:sprockets:2.0.0:beta11:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sprockets_project:sprockets:2.0.0:beta11", + "wfn": { + "Part": "a", + "Vendor": "sprockets_project", + "Product": "sprockets", + "Version": "2.0.0", + "Update": "beta11", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ip_phone_7800_firmware:10.2\\(2\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ip_phone_7800_firmware:10.2%282%29", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ip_phone_7800_firmware", + "Version": "10.2(2)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wire:wire-webapp:2020-02-24:staging0:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wire:wire-webapp:2020-02-24:staging0", + "wfn": { + "Part": "a", + "Vendor": "wire", + "Product": "wire-webapp", + "Version": "2020-02-24", + "Update": "staging0", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sap:abap_platform:7.31:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sap:abap_platform:7.31", + "wfn": { + "Part": "a", + "Vendor": "sap", + "Product": "abap_platform", + "Version": "7.31", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:xen-orchestra:xen_orchestra_web:5.7.8:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:xen-orchestra:xen_orchestra_web:5.7.8", + "wfn": { + "Part": "a", + "Vendor": "xen-orchestra", + "Product": "xen_orchestra_web", + "Version": "5.7.8", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:socket:engine.io:1.0.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:socket:engine.io:1.0.2", + "wfn": { + "Part": "a", + "Vendor": "socket", + "Product": "engine.io", + "Version": "1.0.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:rspamd_project:rspamd:0.6.10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:rspamd_project:rspamd:0.6.10", + "wfn": { + "Part": "a", + "Vendor": "rspamd_project", + "Product": "rspamd", + "Version": "0.6.10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlantiswordprocessor:atlantis_word_processor:2.0.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:atlantiswordprocessor:atlantis_word_processor:2.0.4", + "wfn": { + "Part": "a", + "Vendor": "atlantiswordprocessor", + "Product": "atlantis_word_processor", + "Version": "2.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:openlayers:closure-util:1.14.0:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:openlayers:closure-util:1.14.0::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "openlayers", + "Product": "closure-util", + "Version": "1.14.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:novell:nsure_audit:1.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:novell:nsure_audit:1.0.1", + "wfn": { + "Part": "a", + "Vendor": "novell", + "Product": "nsure_audit", + "Version": "1.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:iceni:infix:6.1.9:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:iceni:infix:6.1.9", + "wfn": { + "Part": "a", + "Vendor": "iceni", + "Product": "infix", + "Version": "6.1.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.0.009:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.0.009", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.0.009", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:tomcat:8.0.34:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:tomcat:8.0.34", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "tomcat", + "Version": "8.0.34", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:emqx:emq_x_broker:0.8.1:alpha:*:*:*:*:*:*", + "cpe-url": "cpe:/a:emqx:emq_x_broker:0.8.1:alpha", + "wfn": { + "Part": "a", + "Vendor": "emqx", + "Product": "emq_x_broker", + "Version": "0.8.1", + "Update": "alpha", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:eclipse:business_intelligence_and_reporting_tools:4.3.1:rc2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:eclipse:business_intelligence_and_reporting_tools:4.3.1:rc2", + "wfn": { + "Part": "a", + "Vendor": "eclipse", + "Product": "business_intelligence_and_reporting_tools", + "Version": "4.3.1", + "Update": "rc2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:phoenixcontact:pc_worx:1.50:hotfix1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:phoenixcontact:pc_worx:1.50:hotfix1", + "wfn": { + "Part": "a", + "Vendor": "phoenixcontact", + "Product": "pc_worx", + "Version": "1.50", + "Update": "hotfix1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:lexmark:cx860_firmware:cxtpp.052.204:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:lexmark:cx860_firmware:cxtpp.052.204", + "wfn": { + "Part": "o", + "Vendor": "lexmark", + "Product": "cx860_firmware", + "Version": "cxtpp.052.204", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:network_admission_control_manager_and_server_system_software:4.0.0.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:network_admission_control_manager_and_server_system_software:4.0.0.1", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "network_admission_control_manager_and_server_system_software", + "Version": "4.0.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:tivoli_directory_server:6.1.0.33:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:tivoli_directory_server:6.1.0.33", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "tivoli_directory_server", + "Version": "6.1.0.33", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zettlr:zettlr:1.7.0:beta12:*:*:*:*:*:*", + "cpe-url": "cpe:/a:zettlr:zettlr:1.7.0:beta12", + "wfn": { + "Part": "a", + "Vendor": "zettlr", + "Product": "zettlr", + "Version": "1.7.0", + "Update": "beta12", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ruby-lang:ruby:1.8.6.304:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ruby-lang:ruby:1.8.6.304", + "wfn": { + "Part": "a", + "Vendor": "ruby-lang", + "Product": "ruby", + "Version": "1.8.6.304", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:fusioncharts:apexcharts:3.17.1:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:fusioncharts:apexcharts:3.17.1::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "fusioncharts", + "Product": "apexcharts", + "Version": "3.17.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vercel:next.js:10.0.2:canary5:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:vercel:next.js:10.0.2:canary5:~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "vercel", + "Product": "next.js", + "Version": "10.0.2", + "Update": "canary5", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:apple:iphone_os:14.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:apple:iphone_os:14.4", + "wfn": { + "Part": "o", + "Vendor": "apple", + "Product": "iphone_os", + "Version": "14.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ruby-lang:ruby:1.8.5.31:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ruby-lang:ruby:1.8.5.31", + "wfn": { + "Part": "a", + "Vendor": "ruby-lang", + "Product": "ruby", + "Version": "1.8.5.31", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:avaya:ip_soft_phone:6.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:avaya:ip_soft_phone:6.0", + "wfn": { + "Part": "a", + "Vendor": "avaya", + "Product": "ip_soft_phone", + "Version": "6.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:frostwire:frostwire:1.9.1:build353:*:*:*:android:*:*", + "cpe-url": "cpe:/a:frostwire:frostwire:1.9.1:build353:~~~android~~", + "wfn": { + "Part": "a", + "Vendor": "frostwire", + "Product": "frostwire", + "Version": "1.9.1", + "Update": "build353", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "android", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:d-link:dir-885l:a1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:d-link:dir-885l:a1", + "wfn": { + "Part": "h", + "Vendor": "d-link", + "Product": "dir-885l", + "Version": "a1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:search_meter_project:search_meter:2.13.1:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:search_meter_project:search_meter:2.13.1::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "search_meter_project", + "Product": "search_meter", + "Version": "2.13.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:s9y:serendipity_event_freetag:3.74:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:s9y:serendipity_event_freetag:3.74", + "wfn": { + "Part": "a", + "Vendor": "s9y", + "Product": "serendipity_event_freetag", + "Version": "3.74", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sensiolabs:symfony:5.2.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sensiolabs:symfony:5.2.6", + "wfn": { + "Part": "a", + "Vendor": "sensiolabs", + "Product": "symfony", + "Version": "5.2.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:x:libxrandr:1.2.99.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:x:libxrandr:1.2.99.2", + "wfn": { + "Part": "a", + "Vendor": "x", + "Product": "libxrandr", + "Version": "1.2.99.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:inpsyde:backwpup:3.3.6:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:inpsyde:backwpup:3.3.6::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "inpsyde", + "Product": "backwpup", + "Version": "3.3.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:websphere_application_server:20.0.0.7:*:*:*:liberty:*:*:*", + "cpe-url": "cpe:/a:ibm:websphere_application_server:20.0.0.7::~~liberty~~~", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "websphere_application_server", + "Version": "20.0.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "liberty", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:microsoft:azure-iot-sdk-c:2017-09-08:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:microsoft:azure-iot-sdk-c:2017-09-08", + "wfn": { + "Part": "a", + "Vendor": "microsoft", + "Product": "azure-iot-sdk-c", + "Version": "2017-09-08", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:pdqinc:laserwash_autoxpress_plus:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:pdqinc:laserwash_autoxpress_plus:-", + "wfn": { + "Part": "h", + "Vendor": "pdqinc", + "Product": "laserwash_autoxpress_plus", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:deskpro:deskpro:2021.1.7:*:*:*:cloud:*:*:*", + "cpe-url": "cpe:/a:deskpro:deskpro:2021.1.7::~~cloud~~~", + "wfn": { + "Part": "a", + "Vendor": "deskpro", + "Product": "deskpro", + "Version": "2021.1.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "cloud", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:nuuo:nvrsolo:1.3.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:nuuo:nvrsolo:1.3.0", + "wfn": { + "Part": "o", + "Vendor": "nuuo", + "Product": "nvrsolo", + "Version": "1.3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:httpclient:4.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:httpclient:4.3", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "httpclient", + "Version": "4.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:qnap:photo_station:5.7.12:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:qnap:photo_station:5.7.12", + "wfn": { + "Part": "a", + "Vendor": "qnap", + "Product": "photo_station", + "Version": "5.7.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ithemes:ithemes_security:7.3.2:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:ithemes:ithemes_security:7.3.2::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "ithemes", + "Product": "ithemes_security", + "Version": "7.3.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpcharitable:charitable:1.6.17:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpcharitable:charitable:1.6.17::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpcharitable", + "Product": "charitable", + "Version": "1.6.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:pepperl-fuchs:pgv100-f200-b17-v1d-7477_firmware:2.0.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:pepperl-fuchs:pgv100-f200-b17-v1d-7477_firmware:2.0.0", + "wfn": { + "Part": "o", + "Vendor": "pepperl-fuchs", + "Product": "pgv100-f200-b17-v1d-7477_firmware", + "Version": "2.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:arista:mos:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:arista:mos:-", + "wfn": { + "Part": "o", + "Vendor": "arista", + "Product": "mos", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:blackberry:enterprise_service:12.2.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:blackberry:enterprise_service:12.2.1", + "wfn": { + "Part": "a", + "Vendor": "blackberry", + "Product": "enterprise_service", + "Version": "12.2.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:triplea-game:triplea:1.9.0.0.11975:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:triplea-game:triplea:1.9.0.0.11975", + "wfn": { + "Part": "a", + "Vendor": "triplea-game", + "Product": "triplea", + "Version": "1.9.0.0.11975", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:ip_phone_8861_firmware:10.3\\(1\\)sr4b:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:ip_phone_8861_firmware:10.3%281%29sr4b", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "ip_phone_8861_firmware", + "Version": "10.3(1)sr4b", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:symantec:security_information_manager:4.7.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:symantec:security_information_manager:4.7.4", + "wfn": { + "Part": "a", + "Vendor": "symantec", + "Product": "security_information_manager", + "Version": "4.7.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vmware:vrealize_operations_for_published_applications:6.5.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vmware:vrealize_operations_for_published_applications:6.5.0", + "wfn": { + "Part": "a", + "Vendor": "vmware", + "Product": "vrealize_operations_for_published_applications", + "Version": "6.5.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:apple:watchos:3.1.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:apple:watchos:3.1.3", + "wfn": { + "Part": "o", + "Vendor": "apple", + "Product": "watchos", + "Version": "3.1.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:etherpad:etherpad:1.6.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:etherpad:etherpad:1.6.1", + "wfn": { + "Part": "a", + "Vendor": "etherpad", + "Product": "etherpad", + "Version": "1.6.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:apache:http_server:2.2.16:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:apache:http_server:2.2.16", + "wfn": { + "Part": "a", + "Vendor": "apache", + "Product": "http_server", + "Version": "2.2.16", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:hikvision:ds-2cd2086g2-iu\\/sl_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:hikvision:ds-2cd2086g2-iu%2fsl_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "hikvision", + "Product": "ds-2cd2086g2-iu/sl_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:dell:latitude_5300_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:dell:latitude_5300_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "dell", + "Product": "latitude_5300_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:adobe:robohelp:2020.0.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:adobe:robohelp:2020.0.4", + "wfn": { + "Part": "a", + "Vendor": "adobe", + "Product": "robohelp", + "Version": "2020.0.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sendio:sendio:7.1.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sendio:sendio:7.1.2", + "wfn": { + "Part": "a", + "Vendor": "sendio", + "Product": "sendio", + "Version": "7.1.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tendermint:tendermint:0.19.6:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tendermint:tendermint:0.19.6:rc1", + "wfn": { + "Part": "a", + "Vendor": "tendermint", + "Product": "tendermint", + "Version": "0.19.6", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kakaocorp:kakaotalk:2.7.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:kakaocorp:kakaotalk:2.7.6", + "wfn": { + "Part": "a", + "Vendor": "kakaocorp", + "Product": "kakaotalk", + "Version": "2.7.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:betcash_project:betcash:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:betcash_project:betcash:-", + "wfn": { + "Part": "a", + "Vendor": "betcash_project", + "Product": "betcash", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:jenkins:checkstyle:1.7:*:*:*:*:jenkins:*:*", + "cpe-url": "cpe:/a:jenkins:checkstyle:1.7::~~~jenkins~~", + "wfn": { + "Part": "a", + "Vendor": "jenkins", + "Product": "checkstyle", + "Version": "1.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "jenkins", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:yithemes:yith_woocommerce_pdf_invoice_and_shipping_list:1.4.17:*:*:*:premium:wordpress:*:*", + "cpe-url": "cpe:/a:yithemes:yith_woocommerce_pdf_invoice_and_shipping_list:1.4.17::~~premium~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "yithemes", + "Product": "yith_woocommerce_pdf_invoice_and_shipping_list", + "Version": "1.4.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "premium", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sass-lang:libsass:3.5.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sass-lang:libsass:3.5.3", + "wfn": { + "Part": "a", + "Vendor": "sass-lang", + "Product": "libsass", + "Version": "3.5.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:buffalo:wzr-hp-ag300h:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:buffalo:wzr-hp-ag300h:-", + "wfn": { + "Part": "h", + "Vendor": "buffalo", + "Product": "wzr-hp-ag300h", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mailstore:mailstore_server:12.0.6:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mailstore:mailstore_server:12.0.6", + "wfn": { + "Part": "a", + "Vendor": "mailstore", + "Product": "mailstore_server", + "Version": "12.0.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:darwin:factor:3.0.17:*:*:*:*:node.js:*:*", + "cpe-url": "cpe:/a:darwin:factor:3.0.17::~~~node.js~~", + "wfn": { + "Part": "a", + "Vendor": "darwin", + "Product": "factor", + "Version": "3.0.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "node.js", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:inspireui:mstore_api:2.9.9:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:inspireui:mstore_api:2.9.9::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "inspireui", + "Product": "mstore_api", + "Version": "2.9.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:edac-utils_project:edac-utils:0.12:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:edac-utils_project:edac-utils:0.12", + "wfn": { + "Part": "a", + "Vendor": "edac-utils_project", + "Product": "edac-utils", + "Version": "0.12", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:huawei:jennifer-an00c:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:huawei:jennifer-an00c:-", + "wfn": { + "Part": "h", + "Vendor": "huawei", + "Product": "jennifer-an00c", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:backup-guard:backup_guard:1.1.79:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:backup-guard:backup_guard:1.1.79::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "backup-guard", + "Product": "backup_guard", + "Version": "1.1.79", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:phpbb:phpbb:3.2.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:phpbb:phpbb:3.2.7", + "wfn": { + "Part": "a", + "Vendor": "phpbb", + "Product": "phpbb", + "Version": "3.2.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nodejs:node.js:0.10.21:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nodejs:node.js:0.10.21", + "wfn": { + "Part": "a", + "Vendor": "nodejs", + "Product": "node.js", + "Version": "0.10.21", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:citrix:sd-wan:10.2.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:citrix:sd-wan:10.2.0", + "wfn": { + "Part": "a", + "Vendor": "citrix", + "Product": "sd-wan", + "Version": "10.2.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cpanel:cpanel:58.0.25:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cpanel:cpanel:58.0.25", + "wfn": { + "Part": "a", + "Vendor": "cpanel", + "Product": "cpanel", + "Version": "58.0.25", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:codesys:control_for_plcnext:3.5.15.30:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:codesys:control_for_plcnext:3.5.15.30", + "wfn": { + "Part": "a", + "Vendor": "codesys", + "Product": "control_for_plcnext", + "Version": "3.5.15.30", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:change_and_configuration_management_database:7.1.1.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:change_and_configuration_management_database:7.1.1.7", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "change_and_configuration_management_database", + "Version": "7.1.1.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:7.4.1529:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:7.4.1529", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "7.4.1529", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:alpinelinux:aports:3.13.0:rc5:*:*:*:alpine:*:*", + "cpe-url": "cpe:/a:alpinelinux:aports:3.13.0:rc5:~~~alpine~~", + "wfn": { + "Part": "a", + "Vendor": "alpinelinux", + "Product": "aports", + "Version": "3.13.0", + "Update": "rc5", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "alpine", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tadtools_project:tadtools:3.04:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tadtools_project:tadtools:3.04", + "wfn": { + "Part": "a", + "Vendor": "tadtools_project", + "Product": "tadtools", + "Version": "3.04", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:katello_project:katello:3.3.0.1:*:*:*:*:foreman:*:*", + "cpe-url": "cpe:/a:katello_project:katello:3.3.0.1::~~~foreman~~", + "wfn": { + "Part": "a", + "Vendor": "katello_project", + "Product": "katello", + "Version": "3.3.0.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "foreman", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:extremenetworks:extremewireless_wing:5.7.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:extremenetworks:extremewireless_wing:5.7.2", + "wfn": { + "Part": "o", + "Vendor": "extremenetworks", + "Product": "extremewireless_wing", + "Version": "5.7.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cisco:nx-os:6.2\\(24\\):*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cisco:nx-os:6.2%2824%29", + "wfn": { + "Part": "o", + "Vendor": "cisco", + "Product": "nx-os", + "Version": "6.2(24)", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vmware:spring_security:5.0.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vmware:spring_security:5.0.7", + "wfn": { + "Part": "a", + "Vendor": "vmware", + "Product": "spring_security", + "Version": "5.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:panasonic:eluga_ray_530_firmware:2020-04-10:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:panasonic:eluga_ray_530_firmware:2020-04-10", + "wfn": { + "Part": "o", + "Vendor": "panasonic", + "Product": "eluga_ray_530_firmware", + "Version": "2020-04-10", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:inedo:proget:4.8.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:inedo:proget:4.8.4", + "wfn": { + "Part": "a", + "Vendor": "inedo", + "Product": "proget", + "Version": "4.8.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:redhat:ovirt-engine:4.3.0:alpha2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:redhat:ovirt-engine:4.3.0:alpha2", + "wfn": { + "Part": "a", + "Vendor": "redhat", + "Product": "ovirt-engine", + "Version": "4.3.0", + "Update": "alpha2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kde:paste_applet:4.1.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:kde:paste_applet:4.1.4", + "wfn": { + "Part": "a", + "Vendor": "kde", + "Product": "paste_applet", + "Version": "4.1.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wpdownloadmanager:wordpress_download_manager:2.4.3:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:wpdownloadmanager:wordpress_download_manager:2.4.3::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "wpdownloadmanager", + "Product": "wordpress_download_manager", + "Version": "2.4.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zohocorp:manageengine_remote_access_plus:10.0.256:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:zohocorp:manageengine_remote_access_plus:10.0.256", + "wfn": { + "Part": "a", + "Vendor": "zohocorp", + "Product": "manageengine_remote_access_plus", + "Version": "10.0.256", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:x2engine:x2crm:5.0.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:x2engine:x2crm:5.0.7", + "wfn": { + "Part": "a", + "Vendor": "x2engine", + "Product": "x2crm", + "Version": "5.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:kubernetes:kubernetes:1.6.0:alpha1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:kubernetes:kubernetes:1.6.0:alpha1", + "wfn": { + "Part": "a", + "Vendor": "kubernetes", + "Product": "kubernetes", + "Version": "1.6.0", + "Update": "alpha1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:prestosql:presto:327:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:prestosql:presto:327", + "wfn": { + "Part": "a", + "Vendor": "prestosql", + "Product": "presto", + "Version": "327", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:saltos:saltos:3.7:9160:*:*:*:*:*:*", + "cpe-url": "cpe:/a:saltos:saltos:3.7:9160", + "wfn": { + "Part": "a", + "Vendor": "saltos", + "Product": "saltos", + "Version": "3.7", + "Update": "9160", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:hp:sgi_tempo:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:hp:sgi_tempo:-", + "wfn": { + "Part": "a", + "Vendor": "hp", + "Product": "sgi_tempo", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mongodb:mongodb:3.6.17:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mongodb:mongodb:3.6.17", + "wfn": { + "Part": "a", + "Vendor": "mongodb", + "Product": "mongodb", + "Version": "3.6.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:wftpserver:wing_ftp_server:2.4:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:wftpserver:wing_ftp_server:2.4", + "wfn": { + "Part": "a", + "Vendor": "wftpserver", + "Product": "wing_ftp_server", + "Version": "2.4", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:webkitgtk:webkitgtk:2.7.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:webkitgtk:webkitgtk:2.7.2", + "wfn": { + "Part": "a", + "Vendor": "webkitgtk", + "Product": "webkitgtk", + "Version": "2.7.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ucweb:ucmobile_blovestorm:1.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ucweb:ucmobile_blovestorm:1.0", + "wfn": { + "Part": "a", + "Vendor": "ucweb", + "Product": "ucmobile_blovestorm", + "Version": "1.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cisco:finesse:9.1\\(1\\)_su1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cisco:finesse:9.1%281%29_su1", + "wfn": { + "Part": "a", + "Vendor": "cisco", + "Product": "finesse", + "Version": "9.1(1)_su1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:oracle:collaboration_suite:10.1.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:oracle:collaboration_suite:10.1.1", + "wfn": { + "Part": "a", + "Vendor": "oracle", + "Product": "collaboration_suite", + "Version": "10.1.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:huawei:s9300:v100r003:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:huawei:s9300:v100r003", + "wfn": { + "Part": "h", + "Vendor": "huawei", + "Product": "s9300", + "Version": "v100r003", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sanitize_project:sanitize:4.4.0:*:*:*:*:ruby:*:*", + "cpe-url": "cpe:/a:sanitize_project:sanitize:4.4.0::~~~ruby~~", + "wfn": { + "Part": "a", + "Vendor": "sanitize_project", + "Product": "sanitize", + "Version": "4.4.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "ruby", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:vim:vim:8.0.0087:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:vim:vim:8.0.0087", + "wfn": { + "Part": "a", + "Vendor": "vim", + "Product": "vim", + "Version": "8.0.0087", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:triplea-game:triplea:1.9.0.0.13066:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:triplea-game:triplea:1.9.0.0.13066", + "wfn": { + "Part": "a", + "Vendor": "triplea-game", + "Product": "triplea", + "Version": "1.9.0.0.13066", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:telestar:imperial_i200:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:telestar:imperial_i200:-", + "wfn": { + "Part": "h", + "Vendor": "telestar", + "Product": "imperial_i200", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:sap:openui5:1.56.17:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:sap:openui5:1.56.17", + "wfn": { + "Part": "a", + "Vendor": "sap", + "Product": "openui5", + "Version": "1.56.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:tekmonks:monkshu:2.01:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:tekmonks:monkshu:2.01", + "wfn": { + "Part": "a", + "Vendor": "tekmonks", + "Product": "monkshu", + "Version": "2.01", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:magentocommerce:magento:1.6.1.0:rc1:*:*:*:*:*:*", + "cpe-url": "cpe:/a:magentocommerce:magento:1.6.1.0:rc1", + "wfn": { + "Part": "a", + "Vendor": "magentocommerce", + "Product": "magento", + "Version": "1.6.1.0", + "Update": "rc1", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cantemo:portal:3.4.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:cantemo:portal:3.4.1", + "wfn": { + "Part": "a", + "Vendor": "cantemo", + "Product": "portal", + "Version": "3.4.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:torproject:tor:0.1.0.17:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:torproject:tor:0.1.0.17", + "wfn": { + "Part": "a", + "Vendor": "torproject", + "Product": "tor", + "Version": "0.1.0.17", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:codeasily:grand_flagallery:5.1.5:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:codeasily:grand_flagallery:5.1.5::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "codeasily", + "Product": "grand_flagallery", + "Version": "5.1.5", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:cdatatec:fd1104b_firmware:2.4.04_001:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:cdatatec:fd1104b_firmware:2.4.04_001", + "wfn": { + "Part": "o", + "Vendor": "cdatatec", + "Product": "fd1104b_firmware", + "Version": "2.4.04_001", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:simon_brown:pebble:2.0.0:m2:*:*:*:*:*:*", + "cpe-url": "cpe:/a:simon_brown:pebble:2.0.0:m2", + "wfn": { + "Part": "a", + "Vendor": "simon_brown", + "Product": "pebble", + "Version": "2.0.0", + "Update": "m2", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:npmjs:npm:1.0.0:rc8:*:*:*:*:*:*", + "cpe-url": "cpe:/a:npmjs:npm:1.0.0:rc8", + "wfn": { + "Part": "a", + "Vendor": "npmjs", + "Product": "npm", + "Version": "1.0.0", + "Update": "rc8", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:opmantek:open-audit:1.12.2-1:*:*:*:-:*:*:*", + "cpe-url": "cpe:/a:opmantek:open-audit:1.12.2-1::~~-~~~", + "wfn": { + "Part": "a", + "Vendor": "opmantek", + "Product": "open-audit", + "Version": "1.12.2-1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "-", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:intel:xeon_processor_d-1577_firmware:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:intel:xeon_processor_d-1577_firmware:-", + "wfn": { + "Part": "o", + "Vendor": "intel", + "Product": "xeon_processor_d-1577_firmware", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:atlassian:fisheye:3.5.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:atlassian:fisheye:3.5.1", + "wfn": { + "Part": "a", + "Vendor": "atlassian", + "Product": "fisheye", + "Version": "3.5.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:yithemes:yith_woocommerce_request_a_quote:3.0.0:*:*:*:premium:wordpress:*:*", + "cpe-url": "cpe:/a:yithemes:yith_woocommerce_request_a_quote:3.0.0::~~premium~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "yithemes", + "Product": "yith_woocommerce_request_a_quote", + "Version": "3.0.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "premium", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:h:cisco:ncs_5502:-:*:*:*:*:*:*:*", + "cpe-url": "cpe:/h:cisco:ncs_5502:-", + "wfn": { + "Part": "h", + "Vendor": "cisco", + "Product": "ncs_5502", + "Version": "-", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:mediacoderhq:mediacoder:0.8.5802:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:mediacoderhq:mediacoder:0.8.5802", + "wfn": { + "Part": "a", + "Vendor": "mediacoderhq", + "Product": "mediacoder", + "Version": "0.8.5802", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:contao:contao:2.3.0:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:contao:contao:2.3.0", + "wfn": { + "Part": "a", + "Vendor": "contao", + "Product": "contao", + "Version": "2.3.0", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:zoom:zoom:4.5.9:*:*:*:*:macos:*:*", + "cpe-url": "cpe:/a:zoom:zoom:4.5.9::~~~macos~~", + "wfn": { + "Part": "a", + "Vendor": "zoom", + "Product": "zoom", + "Version": "4.5.9", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "macos", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:elastic:x-pack:5.6.2:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:elastic:x-pack:5.6.2", + "wfn": { + "Part": "a", + "Vendor": "elastic", + "Product": "x-pack", + "Version": "5.6.2", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:debian:apt:0.8.15.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:debian:apt:0.8.15.1", + "wfn": { + "Part": "a", + "Vendor": "debian", + "Product": "apt", + "Version": "0.8.15.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:plainware:shiftcontroller:2.0.6:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:plainware:shiftcontroller:2.0.6::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "plainware", + "Product": "shiftcontroller", + "Version": "2.0.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:o:sgi:irix:6.5.9m:*:*:*:*:*:*:*", + "cpe-url": "cpe:/o:sgi:irix:6.5.9m", + "wfn": { + "Part": "o", + "Vendor": "sgi", + "Product": "irix", + "Version": "6.5.9m", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:nikola_posa:webfoliocms:1.0.7:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:nikola_posa:webfoliocms:1.0.7", + "wfn": { + "Part": "a", + "Vendor": "nikola_posa", + "Product": "webfoliocms", + "Version": "1.0.7", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:katello_project:katello:0.2.55-1:*:*:*:*:foreman:*:*", + "cpe-url": "cpe:/a:katello_project:katello:0.2.55-1::~~~foreman~~", + "wfn": { + "Part": "a", + "Vendor": "katello_project", + "Product": "katello", + "Version": "0.2.55-1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "foreman", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:chocolate-doom:crispy_doom:5.6.3:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:chocolate-doom:crispy_doom:5.6.3", + "wfn": { + "Part": "a", + "Vendor": "chocolate-doom", + "Product": "crispy_doom", + "Version": "5.6.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:cmsmadesimple:bable\\:multilingual_site:0.3.3:*:*:*:*:cms_made_simple:*:*", + "cpe-url": "cpe:/a:cmsmadesimple:bable%3amultilingual_site:0.3.3::~~~cms_made_simple~~", + "wfn": { + "Part": "a", + "Vendor": "cmsmadesimple", + "Product": "bable:multilingual_site", + "Version": "0.3.3", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "cms_made_simple", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pressified:sendpress:0.9.9.9.6:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:pressified:sendpress:0.9.9.9.6::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "pressified", + "Product": "sendpress", + "Version": "0.9.9.9.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:ibm:tivoli_storage_manager_for_virtual_environments:6.4.3.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:ibm:tivoli_storage_manager_for_virtual_environments:6.4.3.1", + "wfn": { + "Part": "a", + "Vendor": "ibm", + "Product": "tivoli_storage_manager_for_virtual_environments", + "Version": "6.4.3.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:debian:advanced_package_tool:0.7.11:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:debian:advanced_package_tool:0.7.11", + "wfn": { + "Part": "a", + "Vendor": "debian", + "Product": "advanced_package_tool", + "Version": "0.7.11", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:triplea-game:triplea:1.10.13997:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:triplea-game:triplea:1.10.13997", + "wfn": { + "Part": "a", + "Vendor": "triplea-game", + "Product": "triplea", + "Version": "1.10.13997", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:facebook:thrift:2018.02.05.00:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:facebook:thrift:2018.02.05.00", + "wfn": { + "Part": "a", + "Vendor": "facebook", + "Product": "thrift", + "Version": "2018.02.05.00", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:qantumthemes:onair2:3.1.6:*:*:*:*:wordpress:*:*", + "cpe-url": "cpe:/a:qantumthemes:onair2:3.1.6::~~~wordpress~~", + "wfn": { + "Part": "a", + "Vendor": "qantumthemes", + "Product": "onair2", + "Version": "3.1.6", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "wordpress", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:pimcore:pimcore:4.4.1:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:pimcore:pimcore:4.4.1", + "wfn": { + "Part": "a", + "Vendor": "pimcore", + "Product": "pimcore", + "Version": "4.4.1", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + }, + { + "cpe-string": "cpe:2.3:a:gnu:libredwg:0.8.1853:*:*:*:*:*:*:*", + "cpe-url": "cpe:/a:gnu:libredwg:0.8.1853", + "wfn": { + "Part": "a", + "Vendor": "gnu", + "Product": "libredwg", + "Version": "0.8.1853", + "Update": "", + "Edition": "", + "Language": "", + "SwEdition": "", + "TargetSw": "", + "TargetHw": "", + "Other": "" + } + } +] \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/type.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/type.go new file mode 100644 index 0000000000000000000000000000000000000000..6dafed4727d618012790d0df6ecec586aa31142f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/type.go @@ -0,0 +1,146 @@ +package pkg + +import "github.com/anchore/packageurl-go" + +// Type represents a Package Type for or within a language ecosystem (there may be multiple package types within a language ecosystem) +type Type string + +const ( + // the full set of supported packages + UnknownPkg Type = "UnknownPackage" + ApkPkg Type = "apk" + AlpmPkg Type = "alpm" + GemPkg Type = "gem" + DebPkg Type = "deb" + RpmPkg Type = "rpm" + NpmPkg Type = "npm" + PythonPkg Type = "python" + PhpComposerPkg Type = "php-composer" + JavaPkg Type = "java-archive" + JenkinsPluginPkg Type = "jenkins-plugin" + GoModulePkg Type = "go-module" + RustPkg Type = "rust-crate" + KbPkg Type = "msrc-kb" + DartPubPkg Type = "dart-pub" + DotnetPkg Type = "dotnet" + CocoapodsPkg Type = "pod" + ConanPkg Type = "conan" + PortagePkg Type = "portage" + HackagePkg Type = "hackage" +) + +// AllPkgs represents all supported package types +var AllPkgs = []Type{ + ApkPkg, + AlpmPkg, + GemPkg, + DebPkg, + RpmPkg, + NpmPkg, + PythonPkg, + PhpComposerPkg, + JavaPkg, + JenkinsPluginPkg, + GoModulePkg, + RustPkg, + KbPkg, + DartPubPkg, + DotnetPkg, + CocoapodsPkg, + ConanPkg, + PortagePkg, + HackagePkg, +} + +// PackageURLType returns the PURL package type for the current package. +func (t Type) PackageURLType() string { + switch t { + case ApkPkg: + return "alpine" + case AlpmPkg: + return "alpm" + case GemPkg: + return packageurl.TypeGem + case DebPkg: + return "deb" + case PythonPkg: + return packageurl.TypePyPi + case PhpComposerPkg: + return packageurl.TypeComposer + case NpmPkg: + return packageurl.TypeNPM + case JavaPkg, JenkinsPluginPkg: + return packageurl.TypeMaven + case RpmPkg: + return packageurl.TypeRPM + case GoModulePkg: + return packageurl.TypeGolang + case RustPkg: + return "cargo" + case DartPubPkg: + return packageurl.TypePub + case DotnetPkg: + return packageurl.TypeDotnet + case CocoapodsPkg: + return packageurl.TypeCocoapods + case ConanPkg: + return packageurl.TypeConan + case PortagePkg: + return "portage" + case HackagePkg: + return packageurl.TypeHackage + default: + // TODO: should this be a "generic" purl type instead? + return "" + } +} + +func TypeFromPURL(p string) Type { + purl, err := packageurl.FromString(p) + if err != nil { + return UnknownPkg + } + + return TypeByName(purl.Type) +} + +func TypeByName(name string) Type { + switch name { + case packageurl.TypeDebian, "deb": + return DebPkg + case packageurl.TypeRPM: + return RpmPkg + case "alpm": + return AlpmPkg + case "alpine": + return ApkPkg + case packageurl.TypeMaven: + return JavaPkg + case packageurl.TypeComposer: + return PhpComposerPkg + case packageurl.TypeGolang: + return GoModulePkg + case packageurl.TypeNPM: + return NpmPkg + case packageurl.TypePyPi: + return PythonPkg + case packageurl.TypeGem: + return GemPkg + case "cargo", "crate": + return RustPkg + case packageurl.TypePub: + return DartPubPkg + case packageurl.TypeDotnet: + return DotnetPkg + case packageurl.TypeCocoapods: + return CocoapodsPkg + case packageurl.TypeConan: + return ConanPkg + case packageurl.TypeHackage: + return HackagePkg + case "portage": + return PortagePkg + default: + return UnknownPkg + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/type_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/type_test.go new file mode 100644 index 0000000000000000000000000000000000000000..2b25749ae51e89443aba71d031e7d3d083bbab39 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/type_test.go @@ -0,0 +1,110 @@ +package pkg + +import ( + "testing" + + "github.com/scylladb/go-set/strset" + + "github.com/stretchr/testify/assert" +) + +func TestTypeFromPURL(t *testing.T) { + + tests := []struct { + name string + purl string + expected Type + }{ + { + purl: "pkg:rpm/fedora/util-linux@2.32.1-27.el8-?arch=amd64", + expected: RpmPkg, + }, + { + purl: "pkg:alpine/util-linux@2.32.1", + expected: ApkPkg, + }, + { + purl: "pkg:deb/debian/curl@7.50.3-1?arch=i386&distro=jessie", + expected: DebPkg, + }, + { + purl: "pkg:npm/util@2.32", + expected: NpmPkg, + }, + { + purl: "pkg:pypi/util-linux@2.32.1-27.el8", + expected: PythonPkg, + }, + { + purl: "pkg:gem/ruby-advisory-db-check@0.12.4", + expected: GemPkg, + }, + { + purl: "pkg:golang/github.com/gorilla/context@234fd47e07d1004f0aed9c", + expected: GoModulePkg, + }, + { + purl: "pkg:cargo/clap@2.33.0", + expected: RustPkg, + }, + { + purl: "pkg:pub/util@1.2.34?hosted_url=pub.hosted.org", + expected: DartPubPkg, + }, + + { + purl: "pkg:dotnet/Microsoft.CodeAnalysis.Razor@2.2.0", + expected: DotnetPkg, + }, + { + purl: "pkg:composer/laravel/laravel@5.5.0", + expected: PhpComposerPkg, + }, + { + purl: "pkg:maven/org.apache.xmlgraphics/batik-anim@1.9.1?type=zip&classifier=dist", + expected: JavaPkg, + }, + { + purl: "pkg:alpm/arch/linux@5.10.0?arch=x86_64&distro=arch", + expected: AlpmPkg, + }, + { + purl: "pkg:cocoapods/GlossButtonNode@3.1.2", + expected: CocoapodsPkg, + }, + { + purl: "pkg:conan/catch2@2.13.8", + expected: ConanPkg, + }, + { + purl: "pkg:hackage/HTTP@4000.3.16", + expected: HackagePkg, + }, + } + + var pkgTypes []string + var expectedTypes = strset.New() + for _, ty := range AllPkgs { + expectedTypes.Add(string(ty)) + } + + // testing microsoft packages and jenkins-plugins is not valid for purl at this time + expectedTypes.Remove(string(KbPkg)) + expectedTypes.Remove(string(JenkinsPluginPkg)) + expectedTypes.Remove(string(PortagePkg)) + + for _, test := range tests { + t.Run(string(test.expected), func(t *testing.T) { + actual := TypeFromPURL(test.purl) + + if actual != "" { + pkgTypes = append(pkgTypes, string(actual)) + } + + assert.Equal(t, test.expected, actual) + }) + } + + assert.ElementsMatch(t, expectedTypes.List(), pkgTypes, "missing one or more package types to test against (maybe a package type was added?)") + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/url.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/url.go new file mode 100644 index 0000000000000000000000000000000000000000..35b8f9c061a56e3a4fec08876caa0a03591b9851 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/url.go @@ -0,0 +1,110 @@ +package pkg + +import ( + "regexp" + "sort" + "strings" + + "github.com/anchore/packageurl-go" + "github.com/anchore/syft/syft/linux" +) + +const ( + PURLQualifierArch = "arch" + PURLQualifierDistro = "distro" + PURLQualifierEpoch = "epoch" + PURLQualifierVCSURL = "vcs_url" + + // PURLQualifierUpstream this qualifier is not in the pURL spec, but is used by grype to perform indirect matching based on source information + PURLQualifierUpstream = "upstream" + + purlCargoPkgType = "cargo" + purlGradlePkgType = "gradle" +) + +type urlIdentifier interface { + PackageURL(*linux.Release) string +} + +func URL(p Package, release *linux.Release) string { + if p.Metadata != nil { + if i, ok := p.Metadata.(urlIdentifier); ok { + return i.PackageURL(release) + } + } + + // the remaining cases are primarily reserved for packages without metadata struct instances + + var purlType = p.Type.PackageURLType() + var name = p.Name + var namespace = "" + + switch { + case purlType == "": + purlType = packageurl.TypeGeneric + case p.Type == GoModulePkg: + re := regexp.MustCompile(`(/)[^/]*$`) + fields := re.Split(p.Name, -1) + if len(fields) > 1 { + namespace = fields[0] + name = strings.TrimPrefix(p.Name, namespace+"/") + } + case p.Type == NpmPkg: + fields := strings.SplitN(p.Name, "/", 2) + if len(fields) > 1 { + namespace = fields[0] + name = fields[1] + } + } + // generate a purl from the package data + return packageurl.NewPackageURL( + purlType, + namespace, + name, + p.Version, + nil, + "", + ).ToString() +} + +func purlQualifiers(vars map[string]string, release *linux.Release) (q packageurl.Qualifiers) { + keys := make([]string, 0, len(vars)) + for k := range vars { + keys = append(keys, k) + } + sort.Strings(keys) + + for _, k := range keys { + val := vars[k] + if val == "" { + continue + } + q = append(q, packageurl.Qualifier{ + Key: k, + Value: vars[k], + }) + } + + distroQualifiers := []string{} + + if release == nil { + return q + } + + if release.ID != "" { + distroQualifiers = append(distroQualifiers, release.ID) + } + + if release.VersionID != "" { + distroQualifiers = append(distroQualifiers, release.VersionID) + } else if release.BuildID != "" { + distroQualifiers = append(distroQualifiers, release.BuildID) + } + + q = append(q, packageurl.Qualifier{ + Key: PURLQualifierDistro, + Value: strings.Join(distroQualifiers, "-"), + }) + + return q +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/pkg/url_test.go b/ci/tools/openeuler-purl/syft-dev/syft/pkg/url_test.go new file mode 100644 index 0000000000000000000000000000000000000000..85be8241f6862186c0bc37a2f827b438a3a3e2c1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/pkg/url_test.go @@ -0,0 +1,300 @@ +package pkg + +import ( + "testing" + + "github.com/anchore/syft/syft/linux" + "github.com/scylladb/go-set/strset" + "github.com/sergi/go-diff/diffmatchpatch" + "github.com/stretchr/testify/assert" +) + +func TestPackageURL(t *testing.T) { + tests := []struct { + name string + pkg Package + distro *linux.Release + expected string + }{ + { + name: "golang", + pkg: Package{ + Name: "github.com/anchore/syft", + Version: "v0.1.0", + Type: GoModulePkg, + }, + expected: "pkg:golang/github.com/anchore/syft@v0.1.0", + }, + { + name: "golang short name", + pkg: Package{ + Name: "go.opencensus.io", + Version: "v0.23.0", + Type: GoModulePkg, + }, + expected: "pkg:golang/go.opencensus.io@v0.23.0", + }, + { + name: "pub", + pkg: Package{ + Name: "bad-name", + Version: "0.1.0", + Type: DartPubPkg, + Metadata: DartPubMetadata{ + Name: "name", + Version: "0.2.0", + HostedURL: "pub.hosted.org", + }, + }, + expected: "pkg:pub/name@0.2.0?hosted_url=pub.hosted.org", + }, + + { + name: "dotnet", + pkg: Package{ + Name: "Microsoft.CodeAnalysis.Razor", + Version: "2.2.0", + Type: DotnetPkg, + Metadata: DotnetDepsMetadata{ + Name: "Microsoft.CodeAnalysis.Razor", + Version: "2.2.0", + }, + }, + expected: "pkg:dotnet/Microsoft.CodeAnalysis.Razor@2.2.0", + }, + { + name: "python", + pkg: Package{ + Name: "bad-name", + Version: "bad-v0.1.0", + Type: PythonPkg, + Metadata: PythonPackageMetadata{ + Name: "name", + Version: "v0.1.0", + }, + }, + expected: "pkg:pypi/name@v0.1.0", + }, + { + name: "gem", + pkg: Package{ + Name: "name", + Version: "v0.1.0", + Type: GemPkg, + }, + expected: "pkg:gem/name@v0.1.0", + }, + { + name: "npm", + pkg: Package{ + Name: "name", + Version: "v0.1.0", + Type: NpmPkg, + }, + expected: "pkg:npm/name@v0.1.0", + }, + { + name: "deb", + distro: &linux.Release{ + ID: "ubuntu", + VersionID: "20.04", + }, + pkg: Package{ + Name: "bad-name", + Version: "bad-v0.1.0", + Type: DebPkg, + Metadata: DpkgMetadata{ + Package: "name", + Version: "v0.1.0", + Architecture: "amd64", + }, + }, + expected: "pkg:deb/ubuntu/name@v0.1.0?arch=amd64&distro=ubuntu-20.04", + }, + { + name: "rpm", + distro: &linux.Release{ + ID: "centos", + VersionID: "7", + }, + pkg: Package{ + Name: "bad-name", + Version: "bad-v0.1.0", + Type: RpmPkg, + Metadata: RpmMetadata{ + Name: "name", + Version: "0.1.0", + Epoch: intRef(2), + Arch: "amd64", + Release: "3", + }, + }, + expected: "pkg:rpm/centos/name@0.1.0-3?arch=amd64&epoch=2&distro=centos-7", + }, + { + name: "cargo", + pkg: Package{ + Name: "name", + Version: "v0.1.0", + Type: RustPkg, + }, + expected: "pkg:cargo/name@v0.1.0", + }, + { + name: "apk", + distro: &linux.Release{ + ID: "alpine", + VersionID: "3.4.6", + }, + pkg: Package{ + Name: "bad-name", + Version: "bad-v0.1.0", + Type: ApkPkg, + Metadata: ApkMetadata{ + Package: "name", + Version: "v0.1.0", + Architecture: "amd64", + }, + }, + expected: "pkg:alpine/name@v0.1.0?arch=amd64&distro=alpine-3.4.6", + }, + { + name: "php-composer", + pkg: Package{ + Name: "bad-name", + Version: "bad-v0.1.0", + Type: PhpComposerPkg, + Metadata: PhpComposerJSONMetadata{ + Name: "vendor/name", + Version: "2.0.1", + }, + }, + expected: "pkg:composer/vendor/name@2.0.1", + }, + { + name: "java", + pkg: Package{ + Name: "bad-name", + Version: "bad-v0.1.0", + Type: JavaPkg, + Metadata: JavaMetadata{ + PomProperties: &PomProperties{}, + PURL: "pkg:maven/g.id/a@v", // assembled by the java cataloger + }, + }, + + expected: "pkg:maven/g.id/a@v", + }, + { + name: "jenkins-plugin", + pkg: Package{ + Name: "bad-name", + Version: "bad-v0.1.0", + Type: JenkinsPluginPkg, + Metadata: JavaMetadata{ + PomProperties: &PomProperties{}, + PURL: "pkg:maven/g.id/a@v", // assembled by the java cataloger + }, + }, + + expected: "pkg:maven/g.id/a@v", + }, + { + name: "alpm", + distro: &linux.Release{ + ID: "arch", + BuildID: "rolling", + }, + pkg: Package{ + Name: "linux", + Version: "5.10.0", + Type: AlpmPkg, + Metadata: AlpmMetadata{ + Package: "linux", + Version: "5.10.0", + }, + }, + + expected: "pkg:alpm/arch/linux@5.10.0?distro=arch-rolling", + }, + { + name: "cocoapods", + pkg: Package{ + Name: "GlossButtonNode", + Version: "3.1.2", + Language: Swift, + Type: CocoapodsPkg, + Metadata: CocoapodsMetadata{ + Name: "GlossButtonNode", + Version: "3.1.2", + }, + }, + expected: "pkg:cocoapods/GlossButtonNode@3.1.2", + }, + { + name: "conan", + pkg: Package{ + Name: "catch2", + Version: "2.13.8", + Type: ConanPkg, + Language: CPP, + MetadataType: ConanaMetadataType, + Metadata: ConanMetadata{ + Name: "catch2", + Version: "2.13.8", + }, + }, + expected: "pkg:conan/catch2@2.13.8", + }, + { + name: "hackage", + pkg: Package{ + Name: "HTTP", + Version: "4000.3.16", + Type: HackagePkg, + Language: Haskell, + MetadataType: HackageMetadataType, + Metadata: HackageMetadata{ + Name: "HTTP", + Version: "4000.3.16", + }, + }, + expected: "pkg:hackage/HTTP@4000.3.16", + }, + } + + var pkgTypes []string + var expectedTypes = strset.New() + for _, ty := range AllPkgs { + expectedTypes.Add(string(ty)) + } + + // testing microsoft packages is not valid for purl at this time + expectedTypes.Remove(string(KbPkg)) + expectedTypes.Remove(string(PortagePkg)) + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + if test.pkg.Type != "" && !contains(pkgTypes, string(test.pkg.Type)) { + pkgTypes = append(pkgTypes, string(test.pkg.Type)) + } + actual := URL(test.pkg, test.distro) + if actual != test.expected { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(test.expected, actual, true) + t.Errorf("diff: %s", dmp.DiffPrettyText(diffs)) + } + }) + } + assert.ElementsMatch(t, expectedTypes.List(), pkgTypes, "missing one or more package types to test against (maybe a package type was added?)") +} + +func contains(values []string, val string) bool { + for _, v := range values { + if val == v { + return true + } + } + + return false +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/sbom/format.go b/ci/tools/openeuler-purl/syft-dev/syft/sbom/format.go new file mode 100644 index 0000000000000000000000000000000000000000..13cfa784899bd7421262a6b8a61257786a814950 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/sbom/format.go @@ -0,0 +1,83 @@ +package sbom + +import ( + "errors" + "io" +) + +var ( + ErrEncodingNotSupported = errors.New("encoding not supported") + ErrDecodingNotSupported = errors.New("decoding not supported") + ErrValidationNotSupported = errors.New("validation not supported") +) + +type FormatID string + +// String returns a string representation of the FormatID. +func (f FormatID) String() string { + return string(f) +} + +type Format interface { + ID() FormatID + Encode(io.Writer, SBOM) error + Decode(io.Reader) (*SBOM, error) + Validate(io.Reader) error +} + +type format struct { + id FormatID + encoder Encoder + decoder Decoder + validator Validator +} + +// Decoder is a function that can convert an SBOM document of a specific format from a reader into Syft native objects. +type Decoder func(reader io.Reader) (*SBOM, error) + +// Encoder is a function that can transform Syft native objects into an SBOM document of a specific format written to the given writer. +type Encoder func(io.Writer, SBOM) error + +// Validator reads the SBOM from the given reader and assesses whether the document conforms to the specific SBOM format. +// The validator should positively confirm if the SBOM is not only the format but also has the minimal set of values +// that the format requires. For example, all syftjson formatted documents have a schema section which should have +// "anchore/syft" within the version --if this isn't found then the validator should raise an error. These active +// assertions protect against "simple" format decoding validations that may lead to false positives (e.g. I decoded +// json successfully therefore this must be the target format, however, all values are their default zero-value and +// really represent a different format that also uses json) +type Validator func(reader io.Reader) error + +func NewFormat(id FormatID, encoder Encoder, decoder Decoder, validator Validator) Format { + return &format{ + id: id, + encoder: encoder, + decoder: decoder, + validator: validator, + } +} + +func (f format) ID() FormatID { + return f.id +} + +func (f format) Encode(output io.Writer, s SBOM) error { + if f.encoder == nil { + return ErrEncodingNotSupported + } + return f.encoder(output, s) +} + +func (f format) Decode(reader io.Reader) (*SBOM, error) { + if f.decoder == nil { + return nil, ErrDecodingNotSupported + } + return f.decoder(reader) +} + +func (f format) Validate(reader io.Reader) error { + if f.validator == nil { + return ErrValidationNotSupported + } + + return f.validator(reader) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/sbom/multi_writer.go b/ci/tools/openeuler-purl/syft-dev/syft/sbom/multi_writer.go new file mode 100644 index 0000000000000000000000000000000000000000..9dbb1124ff45df36ea2883c11806bf72f195b8c6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/sbom/multi_writer.go @@ -0,0 +1,110 @@ +package sbom + +import ( + "fmt" + "os" + "path" + + "github.com/anchore/syft/internal/log" + "github.com/hashicorp/go-multierror" + "github.com/mitchellh/go-homedir" +) + +// multiWriter holds a list of child sbom.Writers to apply all Write and Close operations to +type multiWriter struct { + writers []Writer +} + +// WriterOption Format and path strings used to create sbom.Writer +type WriterOption struct { + Format Format + Path string +} + +func NewWriterOption(f Format, p string) WriterOption { + expandedPath, err := homedir.Expand(p) + if err != nil { + log.Warnf("could not expand given writer output path=%q: %w", p, err) + // ignore errors + expandedPath = p + } + return WriterOption{ + Format: f, + Path: expandedPath, + } +} + +// NewWriter create all report writers from input options; if a file is not specified, os.Stdout is used +func NewWriter(options ...WriterOption) (_ Writer, err error) { + if len(options) == 0 { + return nil, fmt.Errorf("no output options provided") + } + + out := &multiWriter{} + + defer func() { + if err != nil { + // close any previously opened files; we can't really recover from any errors + if err := out.Close(); err != nil { + log.Warnf("unable to close sbom writers: %+v", err) + } + } + }() + + for _, option := range options { + switch len(option.Path) { + case 0: + out.writers = append(out.writers, &streamWriter{ + format: option.Format, + out: os.Stdout, + }) + default: + // create any missing subdirectories + dir := path.Dir(option.Path) + if dir != "" { + s, err := os.Stat(dir) + if err != nil { + err = os.MkdirAll(dir, 0755) // maybe should be os.ModePerm ? + if err != nil { + return nil, err + } + } else if !s.IsDir() { + return nil, fmt.Errorf("output path does not contain a valid directory: %s", option.Path) + } + } + fileOut, err := os.OpenFile(option.Path, os.O_RDWR|os.O_CREATE|os.O_TRUNC, 0644) + if err != nil { + return nil, fmt.Errorf("unable to create report file: %w", err) + } + out.writers = append(out.writers, &streamWriter{ + format: option.Format, + out: fileOut, + close: fileOut.Close, + }) + } + } + + return out, nil +} + +// Write writes the SBOM to all writers +func (m *multiWriter) Write(s SBOM) (errs error) { + for _, w := range m.writers { + err := w.Write(s) + if err != nil { + errs = multierror.Append(errs, err) + } + } + return errs +} + +// Close closes all writers +func (m *multiWriter) Close() (errs error) { + for _, w := range m.writers { + err := w.Close() + if err != nil { + errs = multierror.Append(errs, err) + } + } + return errs +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/sbom/multi_writer_test.go b/ci/tools/openeuler-purl/syft-dev/syft/sbom/multi_writer_test.go new file mode 100644 index 0000000000000000000000000000000000000000..be61c26f7b5b018dbfaf079d74688f7a0588a210 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/sbom/multi_writer_test.go @@ -0,0 +1,204 @@ +package sbom + +import ( + "io" + "path/filepath" + "strings" + "testing" + + "github.com/docker/docker/pkg/homedir" + "github.com/stretchr/testify/assert" +) + +func dummyEncoder(io.Writer, SBOM) error { + return nil +} + +func dummyFormat(name string) Format { + return NewFormat(FormatID(name), dummyEncoder, nil, nil) +} + +type writerConfig struct { + format string + file string +} + +func TestOutputWriter(t *testing.T) { + tmp := t.TempDir() + + testName := func(options []WriterOption, err bool) string { + var out []string + for _, opt := range options { + out = append(out, string(opt.Format.ID())+"="+opt.Path) + } + errs := "" + if err { + errs = "(err)" + } + return strings.Join(out, ", ") + errs + } + + tests := []struct { + outputs []WriterOption + err bool + expected []writerConfig + }{ + { + outputs: []WriterOption{}, + err: true, + }, + { + outputs: []WriterOption{ + { + Format: dummyFormat("table"), + Path: "", + }, + }, + expected: []writerConfig{ + { + format: "table", + }, + }, + }, + { + outputs: []WriterOption{ + { + Format: dummyFormat("json"), + }, + }, + expected: []writerConfig{ + { + format: "json", + }, + }, + }, + { + outputs: []WriterOption{ + { + Format: dummyFormat("json"), + Path: "test-2.json", + }, + }, + expected: []writerConfig{ + { + format: "json", + file: "test-2.json", + }, + }, + }, + { + outputs: []WriterOption{ + { + Format: dummyFormat("json"), + Path: "test-3/1.json", + }, + { + Format: dummyFormat("spdx-json"), + Path: "test-3/2.json", + }, + }, + expected: []writerConfig{ + { + format: "json", + file: "test-3/1.json", + }, + { + format: "spdx-json", + file: "test-3/2.json", + }, + }, + }, + { + outputs: []WriterOption{ + { + Format: dummyFormat("text"), + }, + { + Format: dummyFormat("spdx-json"), + Path: "test-4.json", + }, + }, + expected: []writerConfig{ + { + format: "text", + }, + { + format: "spdx-json", + file: "test-4.json", + }, + }, + }, + } + + for _, test := range tests { + t.Run(testName(test.outputs, test.err), func(t *testing.T) { + outputs := test.outputs + for i := range outputs { + if outputs[i].Path != "" { + outputs[i].Path = tmp + outputs[i].Path + } + } + + writer, err := NewWriter(outputs...) + + if test.err { + assert.Error(t, err) + return + } else { + assert.NoError(t, err) + } + + mw := writer.(*multiWriter) + + assert.Len(t, mw.writers, len(test.expected)) + + for i, e := range test.expected { + w := mw.writers[i].(*streamWriter) + + assert.Equal(t, string(w.format.ID()), e.format) + + if e.file != "" { + assert.FileExists(t, tmp+e.file) + } + + if e.file != "" { + assert.NotNil(t, w.out) + assert.NotNil(t, w.close) + } else { + assert.NotNil(t, w.out) + assert.Nil(t, w.close) + } + } + }) + } +} + +func TestNewWriterOption(t *testing.T) { + tests := []struct { + name string + path string + expected string + }{ + { + name: "expand home dir", + path: "~/place.txt", + expected: filepath.Join(homedir.Get(), "place.txt"), + }, + { + name: "passthrough other paths", + path: "/other/place.txt", + expected: "/other/place.txt", + }, + { + name: "no path", + path: "", + expected: "", + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + o := NewWriterOption(dummyFormat("table"), tt.path) + assert.Equal(t, tt.expected, o.Path) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/sbom/sbom.go b/ci/tools/openeuler-purl/syft-dev/syft/sbom/sbom.go new file mode 100644 index 0000000000000000000000000000000000000000..76daf9d472dc618c4c4544f1e4875ba4e228841d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/sbom/sbom.go @@ -0,0 +1,66 @@ +package sbom + +import ( + "github.com/anchore/syft/syft/artifact" + "github.com/anchore/syft/syft/file" + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +type SBOM struct { + Artifacts Artifacts + Relationships []artifact.Relationship + Source source.Metadata + Descriptor Descriptor +} + +type Artifacts struct { + PackageCatalog *pkg.Catalog + FileMetadata map[source.Coordinates]source.FileMetadata + FileDigests map[source.Coordinates][]file.Digest + FileClassifications map[source.Coordinates][]file.Classification + FileContents map[source.Coordinates]string + Secrets map[source.Coordinates][]file.SearchResult + LinuxDistribution *linux.Release +} + +type Descriptor struct { + Name string + Version string + Configuration interface{} +} + +func AllCoordinates(sbom SBOM) []source.Coordinates { + set := source.NewCoordinateSet() + for coordinates := range sbom.Artifacts.FileMetadata { + set.Add(coordinates) + } + for coordinates := range sbom.Artifacts.FileContents { + set.Add(coordinates) + } + for coordinates := range sbom.Artifacts.FileClassifications { + set.Add(coordinates) + } + for coordinates := range sbom.Artifacts.FileDigests { + set.Add(coordinates) + } + for _, relationship := range sbom.Relationships { + for _, coordinates := range extractCoordinates(relationship) { + set.Add(coordinates) + } + } + return set.ToSlice() +} + +func extractCoordinates(relationship artifact.Relationship) (results []source.Coordinates) { + if coordinates, exists := relationship.From.(source.Coordinates); exists { + results = append(results, coordinates) + } + + if coordinates, exists := relationship.To.(source.Coordinates); exists { + results = append(results, coordinates) + } + + return results +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/sbom/stream_writer.go b/ci/tools/openeuler-purl/syft-dev/syft/sbom/stream_writer.go new file mode 100644 index 0000000000000000000000000000000000000000..a66b81fac5aab56df8d267b7890cbc6d6d72d4b6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/sbom/stream_writer.go @@ -0,0 +1,25 @@ +package sbom + +import ( + "io" +) + +// streamWriter implements sbom.Writer for a given format and io.Writer, also providing a close function for cleanup +type streamWriter struct { + format Format + out io.Writer + close func() error +} + +// Write the provided SBOM to the data stream +func (w *streamWriter) Write(s SBOM) error { + return w.format.Encode(w.out, s) +} + +// Close any resources, such as open files +func (w *streamWriter) Close() error { + if w.close != nil { + return w.close() + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/sbom/writer.go b/ci/tools/openeuler-purl/syft-dev/syft/sbom/writer.go new file mode 100644 index 0000000000000000000000000000000000000000..824e2fd161d172b2af8f78bab35d9652022c44f9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/sbom/writer.go @@ -0,0 +1,13 @@ +package sbom + +import "io" + +// Writer an interface to write SBOMs +type Writer interface { + // Write writes the provided SBOM + Write(SBOM) error + + // Closer a resource cleanup hook which will be called after SBOM + // is written or if an error occurs before Write is called + io.Closer +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/all_layers_resolver.go b/ci/tools/openeuler-purl/syft-dev/syft/source/all_layers_resolver.go new file mode 100644 index 0000000000000000000000000000000000000000..4293dc825b76bd47eb245e3bd07532a77e52c2ac --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/all_layers_resolver.go @@ -0,0 +1,240 @@ +package source + +import ( + "archive/tar" + "fmt" + "io" + + "github.com/anchore/stereoscope/pkg/file" + "github.com/anchore/stereoscope/pkg/filetree" + "github.com/anchore/stereoscope/pkg/image" + "github.com/anchore/syft/internal/log" +) + +var _ FileResolver = (*allLayersResolver)(nil) + +// allLayersResolver implements path and content access for the AllLayers source option for container image data sources. +type allLayersResolver struct { + img *image.Image + layers []int +} + +// newAllLayersResolver returns a new resolver from the perspective of all image layers for the given image. +func newAllLayersResolver(img *image.Image) (*allLayersResolver, error) { + if len(img.Layers) == 0 { + return nil, fmt.Errorf("the image does not contain any layers") + } + + var layers = make([]int, 0) + for idx := range img.Layers { + layers = append(layers, idx) + } + return &allLayersResolver{ + img: img, + layers: layers, + }, nil +} + +// HasPath indicates if the given path exists in the underlying source. +func (r *allLayersResolver) HasPath(path string) bool { + p := file.Path(path) + for _, layerIdx := range r.layers { + tree := r.img.Layers[layerIdx].Tree + if tree.HasPath(p) { + return true + } + } + return false +} + +func (r *allLayersResolver) fileByRef(ref file.Reference, uniqueFileIDs file.ReferenceSet, layerIdx int) ([]file.Reference, error) { + uniqueFiles := make([]file.Reference, 0) + + // since there is potentially considerable work for each symlink/hardlink that needs to be resolved, let's check to see if this is a symlink/hardlink first + entry, err := r.img.FileCatalog.Get(ref) + if err != nil { + return nil, fmt.Errorf("unable to fetch metadata (ref=%+v): %w", ref, err) + } + + if entry.Metadata.TypeFlag == tar.TypeLink || entry.Metadata.TypeFlag == tar.TypeSymlink { + // a link may resolve in this layer or higher, assuming a squashed tree is used to search + // we should search all possible resolutions within the valid source + for _, subLayerIdx := range r.layers[layerIdx:] { + resolvedRef, err := r.img.ResolveLinkByLayerSquash(ref, subLayerIdx) + if err != nil { + return nil, fmt.Errorf("failed to resolve link from layer (layer=%d ref=%+v): %w", subLayerIdx, ref, err) + } + if resolvedRef != nil && !uniqueFileIDs.Contains(*resolvedRef) { + uniqueFileIDs.Add(*resolvedRef) + uniqueFiles = append(uniqueFiles, *resolvedRef) + } + } + } else if !uniqueFileIDs.Contains(ref) { + uniqueFileIDs.Add(ref) + uniqueFiles = append(uniqueFiles, ref) + } + + return uniqueFiles, nil +} + +// FilesByPath returns all file.References that match the given paths from any layer in the image. +func (r *allLayersResolver) FilesByPath(paths ...string) ([]Location, error) { + uniqueFileIDs := file.NewFileReferenceSet() + uniqueLocations := make([]Location, 0) + + for _, path := range paths { + for idx, layerIdx := range r.layers { + tree := r.img.Layers[layerIdx].Tree + _, ref, err := tree.File(file.Path(path), filetree.FollowBasenameLinks, filetree.DoNotFollowDeadBasenameLinks) + if err != nil { + return nil, err + } + if ref == nil { + // no file found, keep looking through layers + continue + } + + // don't consider directories (special case: there is no path information for /) + if ref.RealPath == "/" { + continue + } else if r.img.FileCatalog.Exists(*ref) { + metadata, err := r.img.FileCatalog.Get(*ref) + if err != nil { + return nil, fmt.Errorf("unable to get file metadata for path=%q: %w", ref.RealPath, err) + } + if metadata.Metadata.IsDir { + continue + } + } + + results, err := r.fileByRef(*ref, uniqueFileIDs, idx) + if err != nil { + return nil, err + } + for _, result := range results { + uniqueLocations = append(uniqueLocations, NewLocationFromImage(path, result, r.img)) + } + } + } + return uniqueLocations, nil +} + +// FilesByGlob returns all file.References that match the given path glob pattern from any layer in the image. +func (r *allLayersResolver) FilesByGlob(patterns ...string) ([]Location, error) { + uniqueFileIDs := file.NewFileReferenceSet() + uniqueLocations := make([]Location, 0) + + for _, pattern := range patterns { + for idx, layerIdx := range r.layers { + results, err := r.img.Layers[layerIdx].Tree.FilesByGlob(pattern, filetree.FollowBasenameLinks, filetree.DoNotFollowDeadBasenameLinks) + if err != nil { + return nil, fmt.Errorf("failed to resolve files by glob (%s): %w", pattern, err) + } + + for _, result := range results { + // don't consider directories (special case: there is no path information for /) + if result.RealPath == "/" { + continue + } else if r.img.FileCatalog.Exists(result.Reference) { + metadata, err := r.img.FileCatalog.Get(result.Reference) + if err != nil { + return nil, fmt.Errorf("unable to get file metadata for path=%q: %w", result.MatchPath, err) + } + if metadata.Metadata.IsDir { + continue + } + } + + refResults, err := r.fileByRef(result.Reference, uniqueFileIDs, idx) + if err != nil { + return nil, err + } + for _, refResult := range refResults { + uniqueLocations = append(uniqueLocations, NewLocationFromImage(string(result.MatchPath), refResult, r.img)) + } + } + } + } + + return uniqueLocations, nil +} + +// RelativeFileByPath fetches a single file at the given path relative to the layer squash of the given reference. +// This is helpful when attempting to find a file that is in the same layer or lower as another file. +func (r *allLayersResolver) RelativeFileByPath(location Location, path string) *Location { + entry, err := r.img.FileCatalog.Get(location.ref) + if err != nil { + return nil + } + + exists, relativeRef, err := entry.Layer.SquashedTree.File(file.Path(path), filetree.FollowBasenameLinks) + if err != nil { + log.Errorf("failed to find path=%q in squash: %+w", path, err) + return nil + } + if !exists && relativeRef == nil { + return nil + } + + relativeLocation := NewLocationFromImage(path, *relativeRef, r.img) + + return &relativeLocation +} + +// FileContentsByLocation fetches file contents for a single file reference, irregardless of the source layer. +// If the path does not exist an error is returned. +func (r *allLayersResolver) FileContentsByLocation(location Location) (io.ReadCloser, error) { + entry, err := r.img.FileCatalog.Get(location.ref) + if err != nil { + return nil, fmt.Errorf("unable to get metadata for path=%q from file catalog: %w", location.RealPath, err) + } + + switch entry.Metadata.TypeFlag { + case tar.TypeSymlink, tar.TypeLink: + // the location we are searching may be a symlink, we should always work with the resolved file + newLocation := r.RelativeFileByPath(location, location.VirtualPath) + if newLocation == nil { + // this is a dead link + return nil, fmt.Errorf("no contents for location=%q", location.VirtualPath) + } + location = *newLocation + } + + return r.img.FileContentsByRef(location.ref) +} + +func (r *allLayersResolver) FilesByMIMEType(types ...string) ([]Location, error) { + var locations []Location + for _, layerIdx := range r.layers { + layer := r.img.Layers[layerIdx] + + refs, err := layer.FilesByMIMEType(types...) + if err != nil { + return nil, err + } + + for _, ref := range refs { + locations = append(locations, NewLocationFromImage(string(ref.RealPath), ref, r.img)) + } + } + + return locations, nil +} + +func (r *allLayersResolver) AllLocations() <-chan Location { + results := make(chan Location) + go func() { + defer close(results) + for _, layerIdx := range r.layers { + tree := r.img.Layers[layerIdx].Tree + for _, ref := range tree.AllFiles(file.AllTypes...) { + results <- NewLocationFromImage(string(ref.RealPath), ref, r.img) + } + } + }() + return results +} + +func (r *allLayersResolver) FileMetadataByLocation(location Location) (FileMetadata, error) { + return fileMetadataByLocation(r.img, location) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/all_layers_resolver_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/all_layers_resolver_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e9e0780125f6152db8424a7db67504ace35902ae --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/all_layers_resolver_test.go @@ -0,0 +1,543 @@ +package source + +import ( + "github.com/stretchr/testify/require" + "io" + "testing" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/stereoscope/pkg/imagetest" +) + +type resolution struct { + layer uint + path string +} + +func TestAllLayersResolver_FilesByPath(t *testing.T) { + cases := []struct { + name string + linkPath string + resolutions []resolution + forcePositiveHasPath bool + }{ + { + name: "link with previous data", + linkPath: "/link-1", + resolutions: []resolution{ + { + layer: 1, + path: "/file-1.txt", + }, + }, + }, + { + name: "link with in layer data", + linkPath: "/link-within", + resolutions: []resolution{ + { + layer: 5, + path: "/file-3.txt", + }, + }, + }, + { + name: "link with overridden data", + linkPath: "/link-2", + resolutions: []resolution{ + { + layer: 4, + path: "/file-2.txt", + }, + { + layer: 7, + path: "/file-2.txt", + }, + }, + }, + { + name: "indirect link (with overridden data)", + linkPath: "/link-indirect", + resolutions: []resolution{ + { + layer: 4, + path: "/file-2.txt", + }, + { + layer: 7, + path: "/file-2.txt", + }, + }, + }, + { + name: "dead link", + linkPath: "/link-dead", + resolutions: []resolution{}, + forcePositiveHasPath: true, + }, + { + name: "ignore directories", + linkPath: "/bin", + resolutions: []resolution{}, + // directories don't resolve BUT do exist + forcePositiveHasPath: true, + }, + } + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", "image-symlinks") + + resolver, err := newAllLayersResolver(img) + if err != nil { + t.Fatalf("could not create resolver: %+v", err) + } + + hasPath := resolver.HasPath(c.linkPath) + if !c.forcePositiveHasPath { + if len(c.resolutions) > 0 && !hasPath { + t.Errorf("expected HasPath() to indicate existance, but did not") + } else if len(c.resolutions) == 0 && hasPath { + t.Errorf("expeced HasPath() to NOT indicate existance, but does") + } + } else if !hasPath { + t.Errorf("expected HasPath() to indicate existance, but did not (force path)") + } + + refs, err := resolver.FilesByPath(c.linkPath) + if err != nil { + t.Fatalf("could not use resolver: %+v", err) + } + + if len(refs) != len(c.resolutions) { + t.Fatalf("unexpected number of resolutions: %d", len(refs)) + } + + for idx, actual := range refs { + expected := c.resolutions[idx] + + if string(actual.ref.RealPath) != expected.path { + t.Errorf("bad resolve path: '%s'!='%s'", string(actual.ref.RealPath), expected.path) + } + + if expected.path != "" && string(actual.ref.RealPath) != actual.RealPath { + t.Errorf("we should always prefer real paths over ones with links") + } + + entry, err := img.FileCatalog.Get(actual.ref) + if err != nil { + t.Fatalf("failed to get metadata: %+v", err) + } + + if entry.Layer.Metadata.Index != expected.layer { + t.Errorf("bad resolve layer: '%d'!='%d'", entry.Layer.Metadata.Index, expected.layer) + } + } + }) + } +} + +func TestAllLayersResolver_FilesByGlob(t *testing.T) { + cases := []struct { + name string + glob string + resolutions []resolution + }{ + { + name: "link with previous data", + glob: "**/*ink-1", + resolutions: []resolution{ + { + layer: 1, + path: "/file-1.txt", + }, + }, + }, + { + name: "link with in layer data", + glob: "**/*nk-within", + resolutions: []resolution{ + { + layer: 5, + path: "/file-3.txt", + }, + }, + }, + { + name: "link with overridden data", + glob: "**/*ink-2", + resolutions: []resolution{ + { + layer: 4, + path: "/file-2.txt", + }, + { + layer: 7, + path: "/file-2.txt", + }, + }, + }, + { + name: "indirect link (with overridden data)", + glob: "**/*nk-indirect", + resolutions: []resolution{ + { + layer: 4, + path: "/file-2.txt", + }, + { + layer: 7, + path: "/file-2.txt", + }, + }, + }, + { + name: "dead link", + glob: "**/*k-dead", + resolutions: []resolution{}, + }, + { + name: "ignore directories", + glob: "**/bin", + resolutions: []resolution{}, + }, + } + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", "image-symlinks") + + resolver, err := newAllLayersResolver(img) + if err != nil { + t.Fatalf("could not create resolver: %+v", err) + } + + refs, err := resolver.FilesByGlob(c.glob) + if err != nil { + t.Fatalf("could not use resolver: %+v", err) + } + + if len(refs) != len(c.resolutions) { + t.Fatalf("unexpected number of resolutions: %d", len(refs)) + } + + for idx, actual := range refs { + expected := c.resolutions[idx] + + if string(actual.ref.RealPath) != expected.path { + t.Errorf("bad resolve path: '%s'!='%s'", string(actual.ref.RealPath), expected.path) + } + + if expected.path != "" && string(actual.ref.RealPath) != actual.RealPath { + t.Errorf("we should always prefer real paths over ones with links") + } + + entry, err := img.FileCatalog.Get(actual.ref) + if err != nil { + t.Fatalf("failed to get metadata: %+v", err) + } + + if entry.Layer.Metadata.Index != expected.layer { + t.Errorf("bad resolve layer: '%d'!='%d'", entry.Layer.Metadata.Index, expected.layer) + } + } + }) + } +} + +func Test_imageAllLayersResolver_FilesByMIMEType(t *testing.T) { + + tests := []struct { + fixtureName string + mimeType string + expectedPaths []string + }{ + { + fixtureName: "image-duplicate-path", + mimeType: "text/plain", + expectedPaths: []string{"/somefile-1.txt", "/somefile-1.txt"}, + }, + } + for _, test := range tests { + t.Run(test.fixtureName, func(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", test.fixtureName) + + resolver, err := newAllLayersResolver(img) + assert.NoError(t, err) + + locations, err := resolver.FilesByMIMEType(test.mimeType) + assert.NoError(t, err) + + assert.Len(t, test.expectedPaths, len(locations)) + for idx, l := range locations { + assert.Equal(t, test.expectedPaths[idx], l.RealPath, "does not have path %q", l.RealPath) + } + }) + } +} + +func Test_imageAllLayersResolver_hasFilesystemIDInLocation(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", "image-duplicate-path") + + resolver, err := newAllLayersResolver(img) + assert.NoError(t, err) + + locations, err := resolver.FilesByMIMEType("text/plain") + assert.NoError(t, err) + assert.NotEmpty(t, locations) + for _, location := range locations { + assert.NotEmpty(t, location.FileSystemID) + } + + locations, err = resolver.FilesByGlob("*.txt") + assert.NoError(t, err) + assert.NotEmpty(t, locations) + for _, location := range locations { + assert.NotEmpty(t, location.FileSystemID) + } + + locations, err = resolver.FilesByPath("/somefile-1.txt") + assert.NoError(t, err) + assert.NotEmpty(t, locations) + for _, location := range locations { + assert.NotEmpty(t, location.FileSystemID) + } + +} + +func TestAllLayersImageResolver_FilesContents(t *testing.T) { + + tests := []struct { + name string + fixture string + contents []string + }{ + { + name: "one degree", + fixture: "link-2", + contents: []string{ + "file 2!", // from the first resolved layer's perspective + "NEW file override!", // from the second resolved layers perspective + }, + }, + { + name: "two degrees", + fixture: "link-indirect", + contents: []string{ + "file 2!", + "NEW file override!", + }, + }, + { + name: "dead link", + fixture: "link-dead", + contents: []string{}, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", "image-symlinks") + + resolver, err := newAllLayersResolver(img) + assert.NoError(t, err) + + refs, err := resolver.FilesByPath(test.fixture) + require.NoError(t, err) + + // the given path should have an overridden file + require.Len(t, refs, len(test.contents)) + + for idx, loc := range refs { + reader, err := resolver.FileContentsByLocation(loc) + require.NoError(t, err) + + actual, err := io.ReadAll(reader) + require.NoError(t, err) + + assert.Equal(t, test.contents[idx], string(actual)) + } + + }) + } +} + +func Test_imageAllLayersResolver_resolvesLinks(t *testing.T) { + tests := []struct { + name string + runner func(FileResolver) []Location + expected []Location + }{ + { + name: "by mimetype", + runner: func(resolver FileResolver) []Location { + // links should not show up when searching mimetype + actualLocations, err := resolver.FilesByMIMEType("text/plain") + assert.NoError(t, err) + return actualLocations + }, + expected: []Location{ + { + Coordinates: Coordinates{ + RealPath: "/etc/group", + }, + VirtualPath: "/etc/group", + }, + { + Coordinates: Coordinates{ + RealPath: "/etc/passwd", + }, + VirtualPath: "/etc/passwd", + }, + { + Coordinates: Coordinates{ + RealPath: "/etc/shadow", + }, + VirtualPath: "/etc/shadow", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-1.txt", + }, + VirtualPath: "/file-1.txt", + }, + // copy 1 + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/file-2.txt", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-3.txt", + }, + VirtualPath: "/file-3.txt", + }, + // copy 2 + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/file-2.txt", + }, + // copy 1 + { + Coordinates: Coordinates{ + RealPath: "/parent/file-4.txt", + }, + VirtualPath: "/parent/file-4.txt", + }, + // copy 2 + { + Coordinates: Coordinates{ + RealPath: "/parent/file-4.txt", + }, + VirtualPath: "/parent/file-4.txt", + }, + }, + }, + { + name: "by glob", + runner: func(resolver FileResolver) []Location { + // links are searched, but resolve to the real files + actualLocations, err := resolver.FilesByGlob("*ink-*") + assert.NoError(t, err) + return actualLocations + }, + expected: []Location{ + { + Coordinates: Coordinates{ + RealPath: "/file-1.txt", + }, + VirtualPath: "/link-1", + }, + // copy 1 + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-2", + }, + // copy 2 + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-2", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-3.txt", + }, + VirtualPath: "/link-within", + }, + }, + }, + { + name: "by path to degree 1 link", + runner: func(resolver FileResolver) []Location { + // links resolve to the final file + actualLocations, err := resolver.FilesByPath("/link-2") + assert.NoError(t, err) + return actualLocations + }, + expected: []Location{ + // we have multiple copies across layers + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-2", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-2", + }, + }, + }, + { + name: "by path to degree 2 link", + runner: func(resolver FileResolver) []Location { + // multiple links resolves to the final file + actualLocations, err := resolver.FilesByPath("/link-indirect") + assert.NoError(t, err) + return actualLocations + }, + expected: []Location{ + // we have multiple copies across layers + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-indirect", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-indirect", + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + img := imagetest.GetFixtureImage(t, "docker-archive", "image-symlinks") + + resolver, err := newAllLayersResolver(img) + assert.NoError(t, err) + + actualLocations := test.runner(resolver) + assert.Len(t, actualLocations, len(test.expected)) + for i, actual := range actualLocations { + assert.Equal(t, test.expected[i].RealPath, actual.RealPath) + assert.Equal(t, test.expected[i].VirtualPath, actual.VirtualPath) + } + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/coordinate_set.go b/ci/tools/openeuler-purl/syft-dev/syft/source/coordinate_set.go new file mode 100644 index 0000000000000000000000000000000000000000..0ae080c270f220809c7f9b7f80f8fb212769a11b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/coordinate_set.go @@ -0,0 +1,86 @@ +package source + +import ( + "sort" + + "github.com/mitchellh/hashstructure/v2" + "github.com/scylladb/go-set/strset" +) + +type CoordinateSet struct { + set map[Coordinates]struct{} +} + +func NewCoordinateSet(coordinates ...Coordinates) (s CoordinateSet) { + for _, l := range coordinates { + s.Add(l) + } + + return s +} + +func (s *CoordinateSet) Add(coordinates ...Coordinates) { + if s.set == nil { + s.set = make(map[Coordinates]struct{}) + } + for _, l := range coordinates { + s.set[l] = struct{}{} + } +} + +func (s CoordinateSet) Remove(coordinates ...Coordinates) { + if s.set == nil { + return + } + for _, l := range coordinates { + delete(s.set, l) + } +} + +func (s CoordinateSet) Contains(l Coordinates) bool { + if s.set == nil { + return false + } + _, ok := s.set[l] + return ok +} + +func (s CoordinateSet) Paths() []string { + if s.set == nil { + return nil + } + + paths := strset.New() + for _, c := range s.ToSlice() { + paths.Add(c.RealPath) + } + pathSlice := paths.List() + sort.Strings(pathSlice) + return pathSlice +} + +func (s CoordinateSet) ToSlice() []Coordinates { + if s.set == nil { + return nil + } + coordinates := make([]Coordinates, len(s.set)) + idx := 0 + for v := range s.set { + coordinates[idx] = v + idx++ + } + sort.SliceStable(coordinates, func(i, j int) bool { + if coordinates[i].RealPath == coordinates[j].RealPath { + return coordinates[i].FileSystemID < coordinates[j].FileSystemID + } + return coordinates[i].RealPath < coordinates[j].RealPath + }) + return coordinates +} + +func (s CoordinateSet) Hash() (uint64, error) { + return hashstructure.Hash(s.ToSlice(), hashstructure.FormatV2, &hashstructure.HashOptions{ + ZeroNil: true, + SlicesAsSets: true, + }) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/coordinate_set_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/coordinate_set_test.go new file mode 100644 index 0000000000000000000000000000000000000000..5601cdc9152ecd92685251eb05345334007eda83 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/coordinate_set_test.go @@ -0,0 +1,117 @@ +package source + +import ( + "github.com/anchore/syft/syft/artifact" + "github.com/stretchr/testify/require" + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestCoordinatesSet(t *testing.T) { + + binA := Coordinates{ + RealPath: "/bin", + FileSystemID: "a", + } + + binB := Coordinates{ + RealPath: "/bin", + FileSystemID: "b", + } + + tests := []struct { + name string + input []Coordinates + expected []Coordinates + }{ + { + name: "de-dup same location", + input: []Coordinates{ + binA, binA, binA, + }, + expected: []Coordinates{ + binA, + }, + }, + { + name: "dont de-dup different filesystem", + input: []Coordinates{ + binB, binA, + }, + expected: []Coordinates{ + binA, binB, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + set := NewCoordinateSet(test.input...) + assert.Equal(t, test.expected, set.ToSlice()) + }) + } +} + +func TestCoordinateSet_Hash(t *testing.T) { + etcA := Coordinates{ + RealPath: "/etc", + FileSystemID: "a", + } + + etcB := Coordinates{ + RealPath: "/etc", + FileSystemID: "b", + } + + binA := Coordinates{ + RealPath: "/bin", + FileSystemID: "a", + } + + binB := Coordinates{ + RealPath: "/bin", + FileSystemID: "b", + } + + tests := []struct { + name string + setA CoordinateSet + setB CoordinateSet + want assert.ComparisonAssertionFunc + }{ + { + name: "empty sets have the same hash", + setA: NewCoordinateSet(), + setB: NewCoordinateSet(), + want: assert.Equal, + }, + { + name: "sets with same elements have the same hash", + setA: NewCoordinateSet(binA, etcA), + setB: NewCoordinateSet(etcA, binA), + want: assert.Equal, + }, + { + name: "sets with different elements have different hashes", + setA: NewCoordinateSet(binA, etcA), + setB: NewCoordinateSet(binA), + want: assert.NotEqual, + }, + { + name: "sets with same paths but different FS IDs have different hashes", + setA: NewCoordinateSet(etcA, binA), + setB: NewCoordinateSet(etcB, binB), + want: assert.NotEqual, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + gotA, err := artifact.IDByHash(tt.setA) + require.NoError(t, err) + gotB, err := artifact.IDByHash(tt.setB) + require.NoError(t, err) + tt.want(t, gotA, gotB) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/coordinates.go b/ci/tools/openeuler-purl/syft-dev/syft/source/coordinates.go new file mode 100644 index 0000000000000000000000000000000000000000..c35d3dcc297eaf6611b95695ee0e024f41355c60 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/coordinates.go @@ -0,0 +1,34 @@ +package source + +import ( + "fmt" + + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/artifact" +) + +// Coordinates contains the minimal information needed to describe how to find a file within any possible source object (e.g. image and directory sources) +type Coordinates struct { + RealPath string `json:"path" cyclonedx:"path"` // The path where all path ancestors have no hardlinks / symlinks + FileSystemID string `json:"layerID,omitempty" cyclonedx:"layerID"` // An ID representing the filesystem. For container images, this is a layer digest. For directories or a root filesystem, this is blank. +} + +func (c Coordinates) ID() artifact.ID { + f, err := artifact.IDByHash(c) + if err != nil { + // TODO: what to do in this case? + log.Warnf("unable to get fingerprint of location coordinate=%+v: %+v", c, err) + return "" + } + + return f +} + +func (c Coordinates) String() string { + str := fmt.Sprintf("RealPath=%q", c.RealPath) + + if c.FileSystemID != "" { + str += fmt.Sprintf(" Layer=%q", c.FileSystemID) + } + return fmt.Sprintf("Location<%s>", str) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver.go b/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver.go new file mode 100644 index 0000000000000000000000000000000000000000..be90dd82a26c498d6d9e22e07bee6962d1465d94 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver.go @@ -0,0 +1,585 @@ +package source + +import ( + "errors" + "fmt" + "io" + "io/fs" + "os" + "path" + "path/filepath" + "runtime" + "strings" + + "github.com/anchore/syft/internal" + + "github.com/anchore/stereoscope/pkg/file" + "github.com/anchore/stereoscope/pkg/filetree" + "github.com/anchore/syft/internal/bus" + "github.com/anchore/syft/internal/log" + "github.com/anchore/syft/syft/event" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/go-progress" +) + +const WindowsOS = "windows" + +var unixSystemRuntimePrefixes = []string{ + "/proc", + "/dev", + "/sys", +} + +var _ FileResolver = (*directoryResolver)(nil) + +type pathFilterFn func(string, os.FileInfo) bool + +// directoryResolver implements path and content access for the directory data source. +type directoryResolver struct { + path string + currentWdRelativeToRoot string + currentWd string + fileTree *filetree.FileTree + metadata map[file.ID]FileMetadata + // TODO: wire up to report these paths in the json report + pathFilterFns []pathFilterFn + refsByMIMEType map[string][]file.Reference + errPaths map[string]error +} + +func newDirectoryResolver(root string, pathFilters ...pathFilterFn) (*directoryResolver, error) { + currentWD, err := os.Getwd() + if err != nil { + return nil, fmt.Errorf("could not gret CWD: %w", err) + } + // we have to account for the root being accessed through a symlink path and always resolve the real path. Otherwise + // we will not be able to normalize given paths that fall under the resolver + cleanCWD, err := filepath.EvalSymlinks(currentWD) + if err != nil { + return nil, fmt.Errorf("could not evaluate CWD symlinks: %w", err) + } + + cleanRoot, err := filepath.EvalSymlinks(root) + if err != nil { + return nil, fmt.Errorf("could not evaluate root=%q symlinks: %w", root, err) + } + + var currentWdRelRoot string + if path.IsAbs(cleanRoot) { + currentWdRelRoot, err = filepath.Rel(cleanCWD, cleanRoot) + if err != nil { + return nil, fmt.Errorf("could not determine given root path to CWD: %w", err) + } + } else { + currentWdRelRoot = filepath.Clean(cleanRoot) + } + + resolver := directoryResolver{ + path: cleanRoot, + currentWd: cleanCWD, + currentWdRelativeToRoot: currentWdRelRoot, + fileTree: filetree.NewFileTree(), + metadata: make(map[file.ID]FileMetadata), + pathFilterFns: append([]pathFilterFn{isUnallowableFileType, isUnixSystemRuntimePath}, pathFilters...), + refsByMIMEType: make(map[string][]file.Reference), + errPaths: make(map[string]error), + } + + return &resolver, indexAllRoots(cleanRoot, resolver.indexTree) +} + +func (r *directoryResolver) indexTree(root string, stager *progress.Stage) ([]string, error) { + log.Debugf("indexing filesystem path=%q", root) + + var roots []string + var err error + + root, err = filepath.Abs(root) + if err != nil { + return nil, err + } + + // we want to be able to index single files with the directory resolver. However, we should also allow for attempting + // to index paths that do not exist (that is, a root that does not exist is not an error case that should stop indexing). + // For this reason we look for an opportunity to discover if the given root is a file, and if so add a single root, + // but continue forth with index regardless if the given root path exists or not. + fi, err := os.Stat(root) + if err != nil && fi != nil && !fi.IsDir() { + // note: we want to index the path regardless of an error stat-ing the path + newRoot, _ := r.indexPath(root, fi, nil) + if newRoot != "" { + roots = append(roots, newRoot) + } + return roots, nil + } + + return roots, filepath.Walk(root, + func(path string, info os.FileInfo, err error) error { + stager.Current = path + + newRoot, err := r.indexPath(path, info, err) + + if err != nil { + return err + } + + if newRoot != "" { + roots = append(roots, newRoot) + } + + return nil + }) +} + +func (r *directoryResolver) indexPath(path string, info os.FileInfo, err error) (string, error) { + // link cycles could cause a revisit --we should not allow this + if r.hasBeenIndexed(path) { + return "", nil + } + + // ignore any path which a filter function returns true + for _, filterFn := range r.pathFilterFns { + if filterFn != nil && filterFn(path, info) { + if info != nil && info.IsDir() { + return "", fs.SkipDir + } + return "", nil + } + } + + if r.isFileAccessErr(path, err) { + return "", nil + } + + if info == nil { + // walk may not be able to provide a FileInfo object, don't allow for this to stop indexing; keep track of the paths and continue. + r.errPaths[path] = fmt.Errorf("no file info observable at path=%q", path) + return "", nil + } + + // here we check to see if we need to normalize paths to posix on the way in coming from windows + if runtime.GOOS == WindowsOS { + path = windowsToPosix(path) + } + + newRoot, err := r.addPathToIndex(path, info) + if r.isFileAccessErr(path, err) { + return "", nil + } + + return newRoot, nil +} + +func (r *directoryResolver) isFileAccessErr(path string, err error) bool { + // don't allow for errors to stop indexing, keep track of the paths and continue. + if err != nil { + log.Warnf("unable to access path=%q: %+v", path, err) + r.errPaths[path] = err + return true + } + return false +} + +func (r directoryResolver) addPathToIndex(p string, info os.FileInfo) (string, error) { + switch t := newFileTypeFromMode(info.Mode()); t { + case SymbolicLink: + return r.addSymlinkToIndex(p, info) + case Directory: + return "", r.addDirectoryToIndex(p, info) + case RegularFile: + return "", r.addFileToIndex(p, info) + default: + return "", fmt.Errorf("unsupported file type: %s", t) + } +} + +func (r directoryResolver) hasBeenIndexed(p string) bool { + filePath := file.Path(p) + if !r.fileTree.HasPath(filePath) { + return false + } + + exists, ref, err := r.fileTree.File(filePath) + if err != nil || !exists || ref == nil { + return false + } + + // cases like "/" will be in the tree, but not been indexed yet (a special case). We want to capture + // these cases as new paths to index. + _, exists = r.metadata[ref.ID()] + return exists +} + +func (r directoryResolver) addDirectoryToIndex(p string, info os.FileInfo) error { + ref, err := r.fileTree.AddDir(file.Path(p)) + if err != nil { + return err + } + + location := NewLocationFromDirectory(p, *ref) + metadata := fileMetadataFromPath(p, info, r.isInIndex(location)) + r.addFileMetadataToIndex(ref, metadata) + + return nil +} + +func (r directoryResolver) addFileToIndex(p string, info os.FileInfo) error { + ref, err := r.fileTree.AddFile(file.Path(p)) + if err != nil { + return err + } + + location := NewLocationFromDirectory(p, *ref) + metadata := fileMetadataFromPath(p, info, r.isInIndex(location)) + r.addFileMetadataToIndex(ref, metadata) + + return nil +} + +func (r directoryResolver) addSymlinkToIndex(p string, info os.FileInfo) (string, error) { + var usedInfo = info + + linkTarget, err := os.Readlink(p) + if err != nil { + return "", fmt.Errorf("unable to readlink for path=%q: %w", p, err) + } + + // note: if the link is not absolute (e.g, /dev/stderr -> fd/2 ) we need to resolve it relative to the directory + // in question (e.g. resolve to /dev/fd/2) + if !filepath.IsAbs(linkTarget) { + linkTarget = filepath.Join(filepath.Dir(p), linkTarget) + } + + ref, err := r.fileTree.AddSymLink(file.Path(p), file.Path(linkTarget)) + if err != nil { + return "", err + } + + targetAbsPath := linkTarget + if !filepath.IsAbs(targetAbsPath) { + targetAbsPath = filepath.Clean(filepath.Join(path.Dir(p), linkTarget)) + } + + location := NewLocationFromDirectory(p, *ref) + location.VirtualPath = p + metadata := fileMetadataFromPath(p, usedInfo, r.isInIndex(location)) + metadata.LinkDestination = linkTarget + r.addFileMetadataToIndex(ref, metadata) + + return targetAbsPath, nil +} + +func (r directoryResolver) addFileMetadataToIndex(ref *file.Reference, metadata FileMetadata) { + if ref != nil { + if metadata.MIMEType != "" { + r.refsByMIMEType[metadata.MIMEType] = append(r.refsByMIMEType[metadata.MIMEType], *ref) + } + r.metadata[ref.ID()] = metadata + } +} + +func (r directoryResolver) requestPath(userPath string) (string, error) { + if filepath.IsAbs(userPath) { + // don't allow input to potentially hop above root path + userPath = path.Join(r.path, userPath) + } else { + // ensure we take into account any relative difference between the root path and the CWD for relative requests + userPath = path.Join(r.currentWdRelativeToRoot, userPath) + } + + var err error + userPath, err = filepath.Abs(userPath) + if err != nil { + return "", err + } + return userPath, nil +} + +func (r directoryResolver) responsePath(path string) string { + // check to see if we need to encode back to Windows from posix + if runtime.GOOS == WindowsOS { + path = posixToWindows(path) + } + + // always return references relative to the request path (not absolute path) + if filepath.IsAbs(path) { + // we need to account for the cwd relative to the running process and the given root for the directory resolver + prefix := filepath.Clean(filepath.Join(r.currentWd, r.currentWdRelativeToRoot)) + return strings.TrimPrefix(path, prefix+string(filepath.Separator)) + } + return path +} + +// HasPath indicates if the given path exists in the underlying source. +func (r *directoryResolver) HasPath(userPath string) bool { + requestPath, err := r.requestPath(userPath) + if err != nil { + return false + } + return r.fileTree.HasPath(file.Path(requestPath)) +} + +// Stringer to represent a directory path data source +func (r directoryResolver) String() string { + return fmt.Sprintf("dir:%s", r.path) +} + +// FilesByPath returns all file.References that match the given paths from the directory. +func (r directoryResolver) FilesByPath(userPaths ...string) ([]Location, error) { + var references = make([]Location, 0) + + for _, userPath := range userPaths { + userStrPath, err := r.requestPath(userPath) + if err != nil { + log.Warnf("unable to get file by path=%q : %+v", userPath, err) + continue + } + + // we should be resolving symlinks and preserving this information as a VirtualPath to the real file + evaluatedPath, err := filepath.EvalSymlinks(userStrPath) + if err != nil { + log.Debugf("directory resolver unable to evaluate symlink for path=%q : %+v", userPath, err) + continue + } + + // TODO: why not use stored metadata? + fileMeta, err := os.Stat(evaluatedPath) + if errors.Is(err, os.ErrNotExist) { + // note: there are other kinds of errors other than os.ErrNotExist that may be given that is platform + // specific, but essentially hints at the same overall problem (that the path does not exist). Such an + // error could be syscall.ENOTDIR (see https://github.com/golang/go/issues/18974). + continue + } else if err != nil { + // we don't want to consider any other syscalls that may hint at non-existence of the file/dir as + // invalid paths. This logging statement is meant to raise IO or permissions related problems. + var pathErr *os.PathError + if !errors.As(err, &pathErr) { + log.Warnf("path is not valid (%s): %+v", evaluatedPath, err) + } + continue + } + + // don't consider directories + if fileMeta.IsDir() { + continue + } + + if runtime.GOOS == WindowsOS { + userStrPath = windowsToPosix(userStrPath) + } + + exists, ref, err := r.fileTree.File(file.Path(userStrPath), filetree.FollowBasenameLinks) + if err == nil && exists { + loc := NewVirtualLocationFromDirectory( + r.responsePath(string(ref.RealPath)), // the actual path relative to the resolver root + r.responsePath(userStrPath), // the path used to access this file, relative to the resolver root + *ref, + ) + references = append(references, loc) + } + } + + return references, nil +} + +// FilesByGlob returns all file.References that match the given path glob pattern from any layer in the image. +func (r directoryResolver) FilesByGlob(patterns ...string) ([]Location, error) { + result := make([]Location, 0) + + for _, pattern := range patterns { + globResults, err := r.fileTree.FilesByGlob(pattern, filetree.FollowBasenameLinks) + if err != nil { + return nil, err + } + for _, globResult := range globResults { + loc := NewVirtualLocationFromDirectory( + r.responsePath(string(globResult.Reference.RealPath)), // the actual path relative to the resolver root + r.responsePath(string(globResult.MatchPath)), // the path used to access this file, relative to the resolver root + globResult.Reference, + ) + result = append(result, loc) + } + } + + return result, nil +} + +// RelativeFileByPath fetches a single file at the given path relative to the layer squash of the given reference. +// This is helpful when attempting to find a file that is in the same layer or lower as another file. For the +// directoryResolver, this is a simple path lookup. +func (r *directoryResolver) RelativeFileByPath(_ Location, path string) *Location { + paths, err := r.FilesByPath(path) + if err != nil { + return nil + } + if len(paths) == 0 { + return nil + } + + return &paths[0] +} + +// FileContentsByLocation fetches file contents for a single file reference relative to a directory. +// If the path does not exist an error is returned. +func (r directoryResolver) FileContentsByLocation(location Location) (io.ReadCloser, error) { + if location.ref.RealPath == "" { + return nil, errors.New("empty path given") + } + if !r.isInIndex(location) { + // this is in cases where paths have been explicitly excluded from the tree index. In which case + // we should DENY all content requests. Why? These paths have been indicated to be inaccessible (either + // by preference or these files are not readable by the current user). + return nil, fmt.Errorf("file content is inaccessible path=%q", location.ref.RealPath) + } + // RealPath is posix so for windows directory resolver we need to translate + // to its true on disk path. + filePath := string(location.ref.RealPath) + if runtime.GOOS == WindowsOS { + filePath = posixToWindows(filePath) + } + return file.NewLazyReadCloser(filePath), nil +} + +func (r directoryResolver) isInIndex(location Location) bool { + if location.ref.RealPath == "" { + return false + } + return r.fileTree.HasPath(location.ref.RealPath, filetree.FollowBasenameLinks) +} + +func (r *directoryResolver) AllLocations() <-chan Location { + results := make(chan Location) + go func() { + defer close(results) + // this should be all non-directory types + for _, ref := range r.fileTree.AllFiles(file.TypeReg, file.TypeSymlink, file.TypeHardLink, file.TypeBlockDevice, file.TypeCharacterDevice, file.TypeFifo) { + results <- NewLocationFromDirectory(r.responsePath(string(ref.RealPath)), ref) + } + }() + return results +} + +func (r *directoryResolver) FileMetadataByLocation(location Location) (FileMetadata, error) { + metadata, exists := r.metadata[location.ref.ID()] + if !exists { + return FileMetadata{}, fmt.Errorf("location: %+v : %w", location, os.ErrNotExist) + } + + return metadata, nil +} + +func (r *directoryResolver) FilesByMIMEType(types ...string) ([]Location, error) { + var locations []Location + for _, ty := range types { + if refs, ok := r.refsByMIMEType[ty]; ok { + for _, ref := range refs { + locations = append(locations, NewLocationFromDirectory(r.responsePath(string(ref.RealPath)), ref)) + } + } + } + return locations, nil +} + +func windowsToPosix(windowsPath string) (posixPath string) { + // volume should be encoded at the start (e.g /c/) where c is the volume + volumeName := filepath.VolumeName(windowsPath) + pathWithoutVolume := strings.TrimPrefix(windowsPath, volumeName) + volumeLetter := strings.ToLower(strings.TrimSuffix(volumeName, ":")) + + // translate non-escaped backslash to forwardslash + translatedPath := strings.ReplaceAll(pathWithoutVolume, "\\", "/") + + // always have `/` as the root... join all components, e.g.: + // convert: C:\\some\windows\Place + // into: /c/some/windows/Place + return path.Clean("/" + strings.Join([]string{volumeLetter, translatedPath}, "/")) +} + +func posixToWindows(posixPath string) (windowsPath string) { + // decode the volume (e.g. /c/ --> C:\\) - There should always be a volume name. + pathFields := strings.Split(posixPath, "/") + volumeName := strings.ToUpper(pathFields[1]) + `:\\` + + // translate non-escaped forward slashes into backslashes + remainingTranslatedPath := strings.Join(pathFields[2:], "\\") + + // combine volume name and backslash components + return filepath.Clean(volumeName + remainingTranslatedPath) +} + +func isUnixSystemRuntimePath(path string, _ os.FileInfo) bool { + return internal.HasAnyOfPrefixes(path, unixSystemRuntimePrefixes...) +} + +func isUnallowableFileType(_ string, info os.FileInfo) bool { + if info == nil { + // we can't filter out by filetype for non-existent files + return false + } + switch newFileTypeFromMode(info.Mode()) { + case CharacterDevice, Socket, BlockDevice, FIFONode, IrregularFile: + return true + // note: symlinks that point to these files may still get by. + // We handle this later in processing to help prevent against infinite links traversal. + } + + return false +} + +func indexAllRoots(root string, indexer func(string, *progress.Stage) ([]string, error)) error { + // why account for multiple roots? To cover cases when there is a symlink that references above the root path, + // in which case we need to additionally index where the link resolves to. it's for this reason why the filetree + // must be relative to the root of the filesystem (and not just relative to the given path). + pathsToIndex := []string{root} + fullPathsMap := map[string]struct{}{} + + stager, prog := indexingProgress(root) + defer prog.SetCompleted() +loop: + for { + var currentPath string + switch len(pathsToIndex) { + case 0: + break loop + case 1: + currentPath, pathsToIndex = pathsToIndex[0], nil + default: + currentPath, pathsToIndex = pathsToIndex[0], pathsToIndex[1:] + } + + additionalRoots, err := indexer(currentPath, stager) + if err != nil { + return fmt.Errorf("unable to index filesystem path=%q: %w", currentPath, err) + } + + for _, newRoot := range additionalRoots { + if _, ok := fullPathsMap[newRoot]; !ok { + fullPathsMap[newRoot] = struct{}{} + pathsToIndex = append(pathsToIndex, newRoot) + } + } + } + + return nil +} + +func indexingProgress(path string) (*progress.Stage, *progress.Manual) { + stage := &progress.Stage{} + prog := &progress.Manual{ + Total: -1, + } + + bus.Publish(partybus.Event{ + Type: event.FileIndexingStarted, + Source: path, + Value: struct { + progress.Stager + progress.Progressable + }{ + Stager: progress.Stager(stage), + Progressable: prog, + }, + }) + + return stage, prog +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver_test.go new file mode 100644 index 0000000000000000000000000000000000000000..f178414c55b26503473b018f8ac90354c42499d4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver_test.go @@ -0,0 +1,888 @@ +//go:build !windows +// +build !windows + +package source + +import ( + "io" + "io/fs" + "io/ioutil" + "os" + "path" + "path/filepath" + "reflect" + "strings" + "testing" + "time" + + "github.com/stretchr/testify/require" + + "github.com/scylladb/go-set/strset" + + "github.com/anchore/stereoscope/pkg/file" + "github.com/stretchr/testify/assert" + "github.com/wagoodman/go-progress" +) + +func TestDirectoryResolver_FilesByPath_relativeRoot(t *testing.T) { + cases := []struct { + name string + relativeRoot string + input string + expected []string + }{ + { + name: "should find a file from an absolute input", + relativeRoot: "./test-fixtures/", + input: "/image-symlinks/file-1.txt", + expected: []string{ + "image-symlinks/file-1.txt", + }, + }, + { + name: "should find a file from a relative path", + relativeRoot: "./test-fixtures/", + input: "image-symlinks/file-1.txt", + expected: []string{ + "image-symlinks/file-1.txt", + }, + }, + { + name: "should find a file from a relative path (root above cwd)", + relativeRoot: "../", + input: "sbom/sbom.go", + expected: []string{ + "sbom/sbom.go", + }, + }, + } + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + resolver, err := newDirectoryResolver(c.relativeRoot) + assert.NoError(t, err) + + refs, err := resolver.FilesByPath(c.input) + require.NoError(t, err) + assert.Len(t, refs, len(c.expected)) + s := strset.New() + for _, actual := range refs { + s.Add(actual.RealPath) + } + assert.ElementsMatch(t, c.expected, s.List()) + }) + } +} + +func TestDirectoryResolver_FilesByPath_absoluteRoot(t *testing.T) { + cases := []struct { + name string + relativeRoot string + input string + expected []string + }{ + { + name: "should find a file from an absolute input", + relativeRoot: "./test-fixtures/", + input: "/image-symlinks/file-1.txt", + expected: []string{ + "image-symlinks/file-1.txt", + }, + }, + { + name: "should find a file from a relative path", + relativeRoot: "./test-fixtures/", + input: "image-symlinks/file-1.txt", + expected: []string{ + "image-symlinks/file-1.txt", + }, + }, + { + name: "should find a file from a relative path (root above cwd)", + relativeRoot: "../", + input: "sbom/sbom.go", + expected: []string{ + "sbom/sbom.go", + }, + }, + } + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + // note: this test is all about asserting correct functionality when the given analysis path + // is an absolute path + absRoot, err := filepath.Abs(c.relativeRoot) + require.NoError(t, err) + + resolver, err := newDirectoryResolver(absRoot) + assert.NoError(t, err) + + refs, err := resolver.FilesByPath(c.input) + require.NoError(t, err) + assert.Len(t, refs, len(c.expected)) + s := strset.New() + for _, actual := range refs { + s.Add(actual.RealPath) + } + assert.ElementsMatch(t, c.expected, s.List()) + }) + } +} + +func TestDirectoryResolver_FilesByPath(t *testing.T) { + cases := []struct { + name string + root string + input string + expected string + refCount int + forcePositiveHasPath bool + }{ + { + name: "finds a file (relative)", + root: "./test-fixtures/", + input: "image-symlinks/file-1.txt", + expected: "image-symlinks/file-1.txt", + refCount: 1, + }, + { + name: "finds a file with relative indirection", + root: "./test-fixtures/../test-fixtures", + input: "image-symlinks/file-1.txt", + expected: "image-symlinks/file-1.txt", + refCount: 1, + }, + { + name: "managed non-existing files (relative)", + root: "./test-fixtures/", + input: "test-fixtures/image-symlinks/bogus.txt", + refCount: 0, + }, + { + name: "finds a file (absolute)", + root: "./test-fixtures/", + input: "/image-symlinks/file-1.txt", + expected: "image-symlinks/file-1.txt", + refCount: 1, + }, + { + name: "directories ignored", + root: "./test-fixtures/", + input: "/image-symlinks", + refCount: 0, + forcePositiveHasPath: true, + }, + } + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + resolver, err := newDirectoryResolver(c.root) + assert.NoError(t, err) + + hasPath := resolver.HasPath(c.input) + if !c.forcePositiveHasPath { + if c.refCount != 0 && !hasPath { + t.Errorf("expected HasPath() to indicate existence, but did not") + } else if c.refCount == 0 && hasPath { + t.Errorf("expected HasPath() to NOT indicate existence, but does") + } + } else if !hasPath { + t.Errorf("expected HasPath() to indicate existence, but did not (force path)") + } + + refs, err := resolver.FilesByPath(c.input) + require.NoError(t, err) + assert.Len(t, refs, c.refCount) + for _, actual := range refs { + assert.Equal(t, c.expected, actual.RealPath) + } + }) + } +} + +func TestDirectoryResolver_MultipleFilesByPath(t *testing.T) { + cases := []struct { + name string + input []string + refCount int + }{ + { + name: "finds multiple files", + input: []string{"image-symlinks/file-1.txt", "image-symlinks/file-2.txt"}, + refCount: 2, + }, + { + name: "skips non-existing files", + input: []string{"image-symlinks/bogus.txt", "image-symlinks/file-1.txt"}, + refCount: 1, + }, + { + name: "does not return anything for non-existing directories", + input: []string{"non-existing/bogus.txt", "non-existing/file-1.txt"}, + refCount: 0, + }, + } + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures") + assert.NoError(t, err) + refs, err := resolver.FilesByPath(c.input...) + assert.NoError(t, err) + + if len(refs) != c.refCount { + t.Errorf("unexpected number of refs: %d != %d", len(refs), c.refCount) + } + }) + } +} + +func TestDirectoryResolver_FilesByGlobMultiple(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures") + assert.NoError(t, err) + refs, err := resolver.FilesByGlob("**/image-symlinks/file*") + assert.NoError(t, err) + + assert.Len(t, refs, 2) +} + +func TestDirectoryResolver_FilesByGlobRecursive(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures/image-symlinks") + assert.NoError(t, err) + refs, err := resolver.FilesByGlob("**/*.txt") + assert.NoError(t, err) + assert.Len(t, refs, 6) +} + +func TestDirectoryResolver_FilesByGlobSingle(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures") + assert.NoError(t, err) + refs, err := resolver.FilesByGlob("**/image-symlinks/*1.txt") + assert.NoError(t, err) + + assert.Len(t, refs, 1) + assert.Equal(t, "image-symlinks/file-1.txt", refs[0].RealPath) +} + +func TestDirectoryResolver_FilesByPath_ResolvesSymlinks(t *testing.T) { + + tests := []struct { + name string + fixture string + }{ + { + name: "one degree", + fixture: "link_to_new_readme", + }, + { + name: "two degrees", + fixture: "link_to_link_to_new_readme", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures/symlinks-simple") + assert.NoError(t, err) + + refs, err := resolver.FilesByPath(test.fixture) + require.NoError(t, err) + assert.Len(t, refs, 1) + + reader, err := resolver.FileContentsByLocation(refs[0]) + require.NoError(t, err) + + actual, err := io.ReadAll(reader) + require.NoError(t, err) + + expected, err := os.ReadFile("test-fixtures/symlinks-simple/readme") + require.NoError(t, err) + + assert.Equal(t, string(expected), string(actual)) + }) + } +} + +func TestDirectoryResolverDoesNotIgnoreRelativeSystemPaths(t *testing.T) { + // let's make certain that "dev/place" is not ignored, since it is not "/dev/place" + resolver, err := newDirectoryResolver("test-fixtures/system_paths/target") + assert.NoError(t, err) + // ensure the correct filter function is wired up by default + expectedFn := reflect.ValueOf(isUnallowableFileType) + actualFn := reflect.ValueOf(resolver.pathFilterFns[0]) + assert.Equal(t, expectedFn.Pointer(), actualFn.Pointer()) + + // all paths should be found (non filtering matches a path) + locations, err := resolver.FilesByGlob("**/place") + assert.NoError(t, err) + // 4: within target/ + // 1: target/link --> relative path to "place" + // 1: outside_root/link_target/place + assert.Len(t, locations, 6) + + // ensure that symlink indexing outside of root worked + testLocation := "test-fixtures/system_paths/outside_root/link_target/place" + ok := false + for _, location := range locations { + if strings.HasSuffix(location.RealPath, testLocation) { + ok = true + } + } + + if !ok { + t.Fatalf("could not find test location=%q", testLocation) + } +} + +var _ fs.FileInfo = (*testFileInfo)(nil) + +type testFileInfo struct { + mode os.FileMode +} + +func (t testFileInfo) Name() string { + panic("implement me") +} + +func (t testFileInfo) Size() int64 { + panic("implement me") +} + +func (t testFileInfo) Mode() fs.FileMode { + return t.mode +} + +func (t testFileInfo) ModTime() time.Time { + panic("implement me") +} + +func (t testFileInfo) IsDir() bool { + panic("implement me") +} + +func (t testFileInfo) Sys() interface{} { + panic("implement me") +} + +func Test_isUnallowableFileType(t *testing.T) { + tests := []struct { + name string + info os.FileInfo + expected bool + }{ + { + name: "regular file", + info: testFileInfo{ + mode: 0, + }, + expected: false, + }, + { + name: "dir", + info: testFileInfo{ + mode: os.ModeDir, + }, + expected: false, + }, + { + name: "symlink", + info: testFileInfo{ + mode: os.ModeSymlink, + }, + expected: false, + }, + { + name: "socket", + info: testFileInfo{ + mode: os.ModeSocket, + }, + expected: true, + }, + { + name: "named pipe", + info: testFileInfo{ + mode: os.ModeNamedPipe, + }, + expected: true, + }, + { + name: "char device", + info: testFileInfo{ + mode: os.ModeCharDevice, + }, + expected: true, + }, + { + name: "block device", + info: testFileInfo{ + mode: os.ModeDevice, + }, + expected: true, + }, + { + name: "irregular", + info: testFileInfo{ + mode: os.ModeIrregular, + }, + expected: true, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.Equal(t, test.expected, isUnallowableFileType("dont/care", test.info)) + }) + } +} + +func Test_directoryResolver_index(t *testing.T) { + // note: this test is testing the effects from newDirectoryResolver, indexTree, and addPathToIndex + r, err := newDirectoryResolver("test-fixtures/system_paths/target") + if err != nil { + t.Fatalf("unable to get indexed dir resolver: %+v", err) + } + tests := []struct { + name string + path string + }{ + { + name: "has dir", + path: "test-fixtures/system_paths/target/home", + }, + { + name: "has path", + path: "test-fixtures/system_paths/target/home/place", + }, + { + name: "has symlink", + path: "test-fixtures/system_paths/target/link/a-symlink", + }, + { + name: "has symlink target", + path: "test-fixtures/system_paths/outside_root/link_target/place", + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + info, err := os.Stat(test.path) + assert.NoError(t, err) + + // note: the index uses absolute paths, so assertions MUST keep this in mind + cwd, err := os.Getwd() + require.NoError(t, err) + + p := file.Path(path.Join(cwd, test.path)) + assert.Equal(t, true, r.fileTree.HasPath(p)) + exists, ref, err := r.fileTree.File(p) + assert.Equal(t, true, exists) + if assert.NoError(t, err) { + return + } + assert.Equal(t, info, r.metadata[ref.ID()]) + }) + } +} + +func Test_handleFileAccessErr(t *testing.T) { + tests := []struct { + name string + input error + expectedPathTracked bool + }{ + { + name: "permission error does not propagate", + input: os.ErrPermission, + expectedPathTracked: true, + }, + { + name: "file does not exist error does not propagate", + input: os.ErrNotExist, + expectedPathTracked: true, + }, + { + name: "non-permission errors are tracked", + input: os.ErrInvalid, + expectedPathTracked: true, + }, + { + name: "non-errors ignored", + input: nil, + expectedPathTracked: false, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + r := directoryResolver{ + errPaths: make(map[string]error), + } + p := "a/place" + assert.Equal(t, r.isFileAccessErr(p, test.input), test.expectedPathTracked) + _, exists := r.errPaths[p] + assert.Equal(t, test.expectedPathTracked, exists) + }) + } +} + +type indexerMock struct { + observedRoots []string + additionalRoots map[string][]string +} + +func (m *indexerMock) indexer(s string, _ *progress.Stage) ([]string, error) { + m.observedRoots = append(m.observedRoots, s) + return m.additionalRoots[s], nil +} + +func Test_indexAllRoots(t *testing.T) { + tests := []struct { + name string + root string + mock indexerMock + expectedRoots []string + }{ + { + name: "no additional roots", + root: "a/place", + mock: indexerMock{ + additionalRoots: make(map[string][]string), + }, + expectedRoots: []string{ + "a/place", + }, + }, + { + name: "additional roots from a single call", + root: "a/place", + mock: indexerMock{ + additionalRoots: map[string][]string{ + "a/place": { + "another/place", + "yet-another/place", + }, + }, + }, + expectedRoots: []string{ + "a/place", + "another/place", + "yet-another/place", + }, + }, + { + name: "additional roots from a multiple calls", + root: "a/place", + mock: indexerMock{ + additionalRoots: map[string][]string{ + "a/place": { + "another/place", + "yet-another/place", + }, + "yet-another/place": { + "a-quiet-place-2", + "a-final/place", + }, + }, + }, + expectedRoots: []string{ + "a/place", + "another/place", + "yet-another/place", + "a-quiet-place-2", + "a-final/place", + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + assert.NoError(t, indexAllRoots(test.root, test.mock.indexer)) + }) + } +} + +func Test_directoryResolver_FilesByMIMEType(t *testing.T) { + tests := []struct { + fixturePath string + mimeType string + expectedPaths *strset.Set + }{ + { + fixturePath: "./test-fixtures/image-simple", + mimeType: "text/plain", + expectedPaths: strset.New("file-1.txt", "file-2.txt", "target/really/nested/file-3.txt", "Dockerfile"), + }, + } + for _, test := range tests { + t.Run(test.fixturePath, func(t *testing.T) { + resolver, err := newDirectoryResolver(test.fixturePath) + assert.NoError(t, err) + locations, err := resolver.FilesByMIMEType(test.mimeType) + assert.NoError(t, err) + assert.Equal(t, test.expectedPaths.Size(), len(locations)) + for _, l := range locations { + assert.True(t, test.expectedPaths.Has(l.RealPath), "does not have path %q", l.RealPath) + } + }) + } +} + +func Test_IndexingNestedSymLinks(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures/symlinks-simple") + require.NoError(t, err) + + // check that we can get the real path + locations, err := resolver.FilesByPath("./readme") + require.NoError(t, err) + assert.Len(t, locations, 1) + + // check that we can access the same file via 1 symlink + locations, err = resolver.FilesByPath("./link_to_new_readme") + require.NoError(t, err) + require.Len(t, locations, 1) + assert.Equal(t, "readme", locations[0].RealPath) + assert.Equal(t, "link_to_new_readme", locations[0].VirtualPath) + + // check that we can access the same file via 2 symlinks + locations, err = resolver.FilesByPath("./link_to_link_to_new_readme") + require.NoError(t, err) + require.Len(t, locations, 1) + assert.Equal(t, "readme", locations[0].RealPath) + assert.Equal(t, "link_to_link_to_new_readme", locations[0].VirtualPath) + + // check that we can access the same file via 2 symlinks + locations, err = resolver.FilesByGlob("**/link_*") + require.NoError(t, err) + require.Len(t, locations, 2) + + // returned locations can be in any order + expectedVirtualPaths := []string{ + "link_to_link_to_new_readme", + "link_to_new_readme", + } + + expectedRealPaths := []string{ + "readme", + } + + actualRealPaths := strset.New() + actualVirtualPaths := strset.New() + for _, a := range locations { + actualVirtualPaths.Add(a.VirtualPath) + actualRealPaths.Add(a.RealPath) + } + + assert.ElementsMatch(t, expectedVirtualPaths, actualVirtualPaths.List()) + assert.ElementsMatch(t, expectedRealPaths, actualRealPaths.List()) +} + +func Test_IndexingNestedSymLinks_ignoredIndexes(t *testing.T) { + filterFn := func(path string, _ os.FileInfo) bool { + return strings.HasSuffix(path, string(filepath.Separator)+"readme") + } + + resolver, err := newDirectoryResolver("./test-fixtures/symlinks-simple", filterFn) + require.NoError(t, err) + + // the path to the real file is PRUNED from the index, so we should NOT expect a location returned + locations, err := resolver.FilesByPath("./readme") + require.NoError(t, err) + assert.Empty(t, locations) + + // check that we cannot access the file even via symlink + locations, err = resolver.FilesByPath("./link_to_new_readme") + require.NoError(t, err) + assert.Empty(t, locations) + + // check that we still cannot access the same file via 2 symlinks + locations, err = resolver.FilesByPath("./link_to_link_to_new_readme") + require.NoError(t, err) + assert.Empty(t, locations) +} + +func Test_IndexingNestedSymLinksOutsideOfRoot(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures/symlinks-multiple-roots/root") + require.NoError(t, err) + + // check that we can get the real path + locations, err := resolver.FilesByPath("./readme") + require.NoError(t, err) + assert.Len(t, locations, 1) + + // check that we can access the same file via 2 symlinks (link_to_link_to_readme -> link_to_readme -> readme) + locations, err = resolver.FilesByPath("./link_to_link_to_readme") + require.NoError(t, err) + assert.Len(t, locations, 1) + + // something looks wrong here + t.Failed() +} + +func Test_RootViaSymlink(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures/symlinked-root/nested/link-root") + require.NoError(t, err) + + locations, err := resolver.FilesByPath("./file1.txt") + require.NoError(t, err) + assert.Len(t, locations, 1) + + locations, err = resolver.FilesByPath("./nested/file2.txt") + require.NoError(t, err) + assert.Len(t, locations, 1) + + locations, err = resolver.FilesByPath("./nested/linked-file1.txt") + require.NoError(t, err) + assert.Len(t, locations, 1) +} + +func Test_directoryResolver_FileContentsByLocation(t *testing.T) { + cwd, err := os.Getwd() + require.NoError(t, err) + + tests := []struct { + name string + location Location + expects string + err bool + }{ + { + name: "use file reference for content requests", + location: NewLocationFromDirectory("some/place", file.Reference{ + RealPath: file.Path(filepath.Join(cwd, "test-fixtures/image-simple/file-1.txt")), + }), + expects: "this file has contents", + }, + { + name: "error on empty file reference", + location: NewLocationFromDirectory("doesn't matter", file.Reference{}), + err: true, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + r, err := newDirectoryResolver(".") + require.NoError(t, err) + + actual, err := r.FileContentsByLocation(test.location) + if test.err { + require.Error(t, err) + return + } + + require.NoError(t, err) + if test.expects != "" { + b, err := ioutil.ReadAll(actual) + require.NoError(t, err) + assert.Equal(t, test.expects, string(b)) + } + }) + } +} + +func Test_isUnixSystemRuntimePath(t *testing.T) { + tests := []struct { + path string + expected bool + }{ + { + path: "proc/place", + expected: false, + }, + { + path: "/proc/place", + expected: true, + }, + { + path: "/proc", + expected: true, + }, + { + path: "/pro/c", + expected: false, + }, + { + path: "/pro", + expected: false, + }, + { + path: "/dev", + expected: true, + }, + { + path: "/sys", + expected: true, + }, + { + path: "/something/sys", + expected: false, + }, + } + for _, test := range tests { + t.Run(test.path, func(t *testing.T) { + assert.Equal(t, test.expected, isUnixSystemRuntimePath(test.path, nil)) + }) + } +} + +func Test_SymlinkLoopWithGlobsShouldResolve(t *testing.T) { + test := func(t *testing.T) { + resolver, err := newDirectoryResolver("./test-fixtures/symlinks-loop") + require.NoError(t, err) + + locations, err := resolver.FilesByGlob("**/file.target") + require.NoError(t, err) + // Note: I'm not certain that this behavior is correct, but it is not an infinite loop (which is the point of the test) + // - block/loop0/file.target + // - devices/loop0/file.target + // - devices/loop0/subsystem/loop0/file.target + assert.Len(t, locations, 3) + } + + testWithTimeout(t, 5*time.Second, test) +} + +func testWithTimeout(t *testing.T, timeout time.Duration, test func(*testing.T)) { + done := make(chan bool) + go func() { + test(t) + done <- true + }() + + select { + case <-time.After(timeout): + t.Fatal("test timed out") + case <-done: + } +} + +func Test_IncludeRootPathInIndex(t *testing.T) { + filterFn := func(path string, _ os.FileInfo) bool { + return path != "/" + } + + resolver, err := newDirectoryResolver("/", filterFn) + require.NoError(t, err) + + exists, ref, err := resolver.fileTree.File(file.Path("/")) + require.NoError(t, err) + require.NotNil(t, ref) + assert.True(t, exists) + + _, exists = resolver.metadata[ref.ID()] + require.True(t, exists) +} + +func TestDirectoryResolver_indexPath(t *testing.T) { + // TODO: Ideally we can use an OS abstraction, which would obviate the need for real FS setup. + tempFile, err := os.CreateTemp("", "") + require.NoError(t, err) + + resolver, err := newDirectoryResolver(tempFile.Name()) + require.NoError(t, err) + + t.Run("filtering path with nil os.FileInfo", func(t *testing.T) { + // We use one of these prefixes in order to trigger a pathFilterFn + filteredPath := unixSystemRuntimePrefixes[0] + + var fileInfo os.FileInfo = nil + + assert.NotPanics(t, func() { + _, err := resolver.indexPath(filteredPath, fileInfo, nil) + assert.NoError(t, err) + }) + }) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver_windows_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver_windows_test.go new file mode 100644 index 0000000000000000000000000000000000000000..18cbb7856c4cf3091f07760941c19a0864c0ae03 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/directory_resolver_windows_test.go @@ -0,0 +1,126 @@ +package source + +import "testing" + +func Test_windowsToPosix(t *testing.T) { + type args struct { + windowsPath string + } + tests := []struct { + name string + args args + wantPosixPath string + }{ + { + name: "basic case", + args: args{ + windowsPath: `C:\some\windows\place`, + }, + wantPosixPath: "/c/some/windows/place", + }, + { + name: "escaped case", + args: args{ + windowsPath: `C:\\some\\windows\\place`, + }, + wantPosixPath: "/c/some/windows/place", + }, + { + name: "forward slash", + args: args{ + windowsPath: `C:/foo/bar`, + }, + wantPosixPath: "/c/foo/bar", + }, + { + name: "mix slash", + args: args{ + windowsPath: `C:\foo/bar\`, + }, + wantPosixPath: "/c/foo/bar", + }, + { + name: "case sensitive case", + args: args{ + windowsPath: `C:\Foo/bAr\`, + }, + wantPosixPath: "/c/Foo/bAr", + }, + { + name: "special char case", + args: args{ + windowsPath: `C:\ふー\バー`, + }, + wantPosixPath: "/c/ふー/バー", + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + if gotPosixPath := windowsToPosix(tt.args.windowsPath); gotPosixPath != tt.wantPosixPath { + t.Errorf("windowsToPosix() = %v, want %v", gotPosixPath, tt.wantPosixPath) + } + }) + } +} + +func Test_posixToWindows(t *testing.T) { + type args struct { + posixPath string + } + tests := []struct { + name string + args args + wantWindowsPath string + }{ + { + name: "basic case", + args: args{ + posixPath: "/c/some/windows/place", + }, + wantWindowsPath: `C:\some\windows\place`, + }, + { + name: "escaped case", + args: args{ + posixPath: "/c/some/windows/place", + }, + wantWindowsPath: `C:\\some\\windows\\place`, + }, + { + name: "forward slash", + args: args{ + posixPath: "/c/foo/bar", + }, + wantWindowsPath: `C:/foo/bar`, + }, + { + name: "mix slash", + args: args{ + posixPath: "/c/foo/bar", + }, + wantWindowsPath: `C:\foo/bar\`, + }, + { + name: "case sensitive case", + args: args{ + posixPath: "/c/Foo/bAr", + }, + wantWindowsPath: `C:\Foo/bAr\`, + }, + { + name: "special char case", + args: args{ + posixPath: "/c/ふー/バー", + }, + wantWindowsPath: `C:\ふー\バー`, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + if gotWindowsPath := posixToWindows(tt.args.posixPath); gotWindowsPath != tt.wantWindowsPath { + t.Errorf("posixToWindows() = %v, want %v", gotWindowsPath, tt.wantWindowsPath) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/excluding_file_resolver.go b/ci/tools/openeuler-purl/syft-dev/syft/source/excluding_file_resolver.go new file mode 100644 index 0000000000000000000000000000000000000000..50969116a8122519c9e33a82d191631d94fb5035 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/excluding_file_resolver.go @@ -0,0 +1,101 @@ +package source + +import ( + "fmt" + "io" +) + +type excludeFn func(string) bool + +// excludingResolver decorates a resolver with an exclusion function that is used to +// filter out entries in the delegate resolver +type excludingResolver struct { + delegate FileResolver + excludeFn excludeFn +} + +// NewExcludingResolver create a new resolver which wraps the provided delegate and excludes +// entries based on a provided path exclusion function +func NewExcludingResolver(delegate FileResolver, excludeFn excludeFn) FileResolver { + return &excludingResolver{ + delegate, + excludeFn, + } +} + +func (r *excludingResolver) FileContentsByLocation(location Location) (io.ReadCloser, error) { + if locationMatches(&location, r.excludeFn) { + return nil, fmt.Errorf("no such location: %+v", location.RealPath) + } + return r.delegate.FileContentsByLocation(location) +} + +func (r *excludingResolver) FileMetadataByLocation(location Location) (FileMetadata, error) { + if locationMatches(&location, r.excludeFn) { + return FileMetadata{}, fmt.Errorf("no such location: %+v", location.RealPath) + } + return r.delegate.FileMetadataByLocation(location) +} + +func (r *excludingResolver) HasPath(path string) bool { + if r.excludeFn(path) { + return false + } + return r.delegate.HasPath(path) +} + +func (r *excludingResolver) FilesByPath(paths ...string) ([]Location, error) { + locations, err := r.delegate.FilesByPath(paths...) + return filterLocations(locations, err, r.excludeFn) +} + +func (r *excludingResolver) FilesByGlob(patterns ...string) ([]Location, error) { + locations, err := r.delegate.FilesByGlob(patterns...) + return filterLocations(locations, err, r.excludeFn) +} + +func (r *excludingResolver) FilesByMIMEType(types ...string) ([]Location, error) { + locations, err := r.delegate.FilesByMIMEType(types...) + return filterLocations(locations, err, r.excludeFn) +} + +func (r *excludingResolver) RelativeFileByPath(location Location, path string) *Location { + l := r.delegate.RelativeFileByPath(location, path) + if l != nil && locationMatches(l, r.excludeFn) { + return nil + } + return l +} + +func (r *excludingResolver) AllLocations() <-chan Location { + c := make(chan Location) + go func() { + defer close(c) + for location := range r.delegate.AllLocations() { + if !locationMatches(&location, r.excludeFn) { + c <- location + } + } + }() + return c +} + +func locationMatches(location *Location, exclusionFn excludeFn) bool { + return exclusionFn(location.RealPath) || exclusionFn(location.VirtualPath) +} + +func filterLocations(locations []Location, err error, exclusionFn excludeFn) ([]Location, error) { + if err != nil { + return nil, err + } + if exclusionFn != nil { + for i := 0; i < len(locations); i++ { + location := &locations[i] + if locationMatches(location, exclusionFn) { + locations = append(locations[:i], locations[i+1:]...) + i-- + } + } + } + return locations, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/excluding_file_resolver_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/excluding_file_resolver_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4cfe187279be37591361486831faae332e07fdd9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/excluding_file_resolver_test.go @@ -0,0 +1,197 @@ +package source + +import ( + "io" + "strings" + "testing" + + "github.com/anchore/stereoscope/pkg/file" + + "github.com/stretchr/testify/assert" +) + +func TestExcludingResolver(t *testing.T) { + + tests := []struct { + name string + locations []string + excludeFn excludeFn + expected []string + }{ + { + name: "keeps locations", + locations: []string{"a", "b", "c"}, + excludeFn: func(s string) bool { + return false + }, + expected: []string{"a", "b", "c"}, + }, + { + name: "removes locations", + locations: []string{"d", "e", "f"}, + excludeFn: func(s string) bool { + return true + }, + expected: []string{}, + }, + { + name: "removes first match", + locations: []string{"g", "h", "i"}, + excludeFn: func(s string) bool { + return s == "g" + }, + expected: []string{"h", "i"}, + }, + { + name: "removes last match", + locations: []string{"j", "k", "l"}, + excludeFn: func(s string) bool { + return s == "l" + }, + expected: []string{"j", "k"}, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + resolver := &mockResolver{ + locations: test.locations, + } + excludingResolver := NewExcludingResolver(resolver, test.excludeFn) + + locations, _ := excludingResolver.FilesByPath() + assert.ElementsMatch(t, locationPaths(locations), test.expected) + + locations, _ = excludingResolver.FilesByGlob() + assert.ElementsMatch(t, locationPaths(locations), test.expected) + + locations, _ = excludingResolver.FilesByMIMEType() + assert.ElementsMatch(t, locationPaths(locations), test.expected) + + locations = []Location{} + + channel := excludingResolver.AllLocations() + for location := range channel { + locations = append(locations, location) + } + assert.ElementsMatch(t, locationPaths(locations), test.expected) + + diff := difference(test.locations, test.expected) + + for _, path := range diff { + assert.False(t, excludingResolver.HasPath(path)) + c, err := excludingResolver.FileContentsByLocation(makeLocation(path)) + assert.Nil(t, c) + assert.Error(t, err) + m, err := excludingResolver.FileMetadataByLocation(makeLocation(path)) + assert.Empty(t, m.LinkDestination) + assert.Error(t, err) + l := excludingResolver.RelativeFileByPath(makeLocation(""), path) + assert.Nil(t, l) + } + + for _, path := range test.expected { + assert.True(t, excludingResolver.HasPath(path)) + c, err := excludingResolver.FileContentsByLocation(makeLocation(path)) + assert.NotNil(t, c) + assert.Nil(t, err) + m, err := excludingResolver.FileMetadataByLocation(makeLocation(path)) + assert.NotEmpty(t, m.LinkDestination) + assert.Nil(t, err) + l := excludingResolver.RelativeFileByPath(makeLocation(""), path) + assert.NotNil(t, l) + } + }) + } +} + +// difference returns the elements in `a` that aren't in `b`. +func difference(a, b []string) []string { + mb := make(map[string]struct{}, len(b)) + for _, x := range b { + mb[x] = struct{}{} + } + var diff []string + for _, x := range a { + if _, found := mb[x]; !found { + diff = append(diff, x) + } + } + return diff +} + +func makeLocation(path string) Location { + return Location{ + Coordinates: Coordinates{ + RealPath: path, + FileSystemID: "", + }, + VirtualPath: "", + ref: file.Reference{}, + } +} + +func locationPaths(locations []Location) []string { + paths := []string{} + for _, l := range locations { + paths = append(paths, l.RealPath) + } + return paths +} + +type mockResolver struct { + locations []string +} + +func (r *mockResolver) getLocations() ([]Location, error) { + out := []Location{} + for _, path := range r.locations { + out = append(out, makeLocation(path)) + } + return out, nil +} + +func (r *mockResolver) FileContentsByLocation(_ Location) (io.ReadCloser, error) { + return io.NopCloser(strings.NewReader("Hello, world!")), nil +} + +func (r *mockResolver) FileMetadataByLocation(_ Location) (FileMetadata, error) { + return FileMetadata{ + LinkDestination: "MOCK", + }, nil +} + +func (r *mockResolver) HasPath(_ string) bool { + return true +} + +func (r *mockResolver) FilesByPath(_ ...string) ([]Location, error) { + return r.getLocations() +} + +func (r *mockResolver) FilesByGlob(_ ...string) ([]Location, error) { + return r.getLocations() +} + +func (r *mockResolver) FilesByMIMEType(_ ...string) ([]Location, error) { + return r.getLocations() +} + +func (r *mockResolver) RelativeFileByPath(_ Location, path string) *Location { + return &Location{ + Coordinates: Coordinates{ + RealPath: path, + }, + } +} + +func (r *mockResolver) AllLocations() <-chan Location { + c := make(chan Location) + go func() { + defer close(c) + locations, _ := r.getLocations() + for _, location := range locations { + c <- location + } + }() + return c +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/file_details.go b/ci/tools/openeuler-purl/syft-dev/syft/source/file_details.go new file mode 100644 index 0000000000000000000000000000000000000000..f656c071d71ea2108be8045ea71c232ba36fd436 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/file_details.go @@ -0,0 +1,21 @@ +//go:build linux || darwin +// +build linux darwin + +package source + +import ( + "os" + "syscall" +) + +// GetXid is the UID GID system info for unix +func GetXid(info os.FileInfo) (uid, gid int) { + uid = -1 + gid = -1 + if stat, ok := info.Sys().(*syscall.Stat_t); ok { + uid = int(stat.Uid) + gid = int(stat.Gid) + } + + return uid, gid +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/file_details_win.go b/ci/tools/openeuler-purl/syft-dev/syft/source/file_details_win.go new file mode 100644 index 0000000000000000000000000000000000000000..31fd05063e72471a532cfa94dfb0eb77bde5e1ab --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/file_details_win.go @@ -0,0 +1,13 @@ +//go:build windows +// +build windows + +package source + +import ( + "os" +) + +// GetXid is a placeholder for windows file information +func GetXid(info os.FileInfo) (uid, gid int) { + return -1, -1 +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/file_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/source/file_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..432a1d8f4e08e2eb6eb5d9bf46617b405e01235f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/file_metadata.go @@ -0,0 +1,69 @@ +package source + +import ( + "os" + + "github.com/anchore/stereoscope/pkg/file" + + "github.com/anchore/syft/internal/log" + + "github.com/anchore/stereoscope/pkg/image" +) + +type FileMetadata struct { + Mode os.FileMode + Type FileType + UserID int + GroupID int + LinkDestination string + Size int64 + MIMEType string +} + +func fileMetadataByLocation(img *image.Image, location Location) (FileMetadata, error) { + entry, err := img.FileCatalog.Get(location.ref) + if err != nil { + return FileMetadata{}, err + } + + return FileMetadata{ + Mode: entry.Metadata.Mode, + Type: newFileTypeFromTarHeaderTypeFlag(entry.Metadata.TypeFlag), + UserID: entry.Metadata.UserID, + GroupID: entry.Metadata.GroupID, + LinkDestination: entry.Metadata.Linkname, + Size: entry.Metadata.Size, + MIMEType: entry.Metadata.MIMEType, + }, nil +} + +func fileMetadataFromPath(path string, info os.FileInfo, withMIMEType bool) FileMetadata { + var mimeType string + uid, gid := GetXid(info) + + if withMIMEType { + f, err := os.Open(path) + if err != nil { + // TODO: it may be that the file is inaccessible, however, this is not an error or a warning. In the future we need to track these as known-unknowns + f = nil + } else { + defer func() { + if err := f.Close(); err != nil { + log.Warnf("unable to close file while obtaining metadata: %s", path) + } + }() + } + + mimeType = file.MIMEType(f) + } + + return FileMetadata{ + Mode: info.Mode(), + Type: newFileTypeFromMode(info.Mode()), + // unsupported across platforms + UserID: uid, + GroupID: gid, + Size: info.Size(), + MIMEType: mimeType, + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/file_metadata_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/file_metadata_test.go new file mode 100644 index 0000000000000000000000000000000000000000..3bdedb42ff1e5cbd17d38b739aaabdd95370a2a3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/file_metadata_test.go @@ -0,0 +1,57 @@ +//go:build !windows +// +build !windows + +package source + +import ( + "os" + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func Test_fileMetadataFromPath(t *testing.T) { + + tests := []struct { + path string + withMIMEType bool + expectedType string + expectedMIMEType string + }{ + { + path: "test-fixtures/symlinks-simple/readme", + withMIMEType: true, + expectedType: "RegularFile", + expectedMIMEType: "text/plain", + }, + { + path: "test-fixtures/symlinks-simple/link_to_new_readme", + withMIMEType: true, + expectedType: "SymbolicLink", + expectedMIMEType: "text/plain", + }, + { + path: "test-fixtures/symlinks-simple/readme", + withMIMEType: false, + expectedType: "RegularFile", + expectedMIMEType: "", + }, + { + path: "test-fixtures/symlinks-simple/link_to_new_readme", + withMIMEType: false, + expectedType: "SymbolicLink", + expectedMIMEType: "", + }, + } + for _, test := range tests { + t.Run(test.path, func(t *testing.T) { + info, err := os.Lstat(test.path) + require.NoError(t, err) + + actual := fileMetadataFromPath(test.path, info, test.withMIMEType) + assert.Equal(t, test.expectedMIMEType, actual.MIMEType) + assert.Equal(t, test.expectedType, string(actual.Type)) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/file_resolver.go b/ci/tools/openeuler-purl/syft-dev/syft/source/file_resolver.go new file mode 100644 index 0000000000000000000000000000000000000000..b6ccb4815955a5154494f05361c6acddd1a2e279 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/file_resolver.go @@ -0,0 +1,41 @@ +package source + +import ( + "io" +) + +// FileResolver is an interface that encompasses how to get specific file references and file contents for a generic data source. +type FileResolver interface { + FileContentResolver + FilePathResolver + FileLocationResolver + FileMetadataResolver +} + +// FileContentResolver knows how to get file content for a given Location +type FileContentResolver interface { + FileContentsByLocation(Location) (io.ReadCloser, error) +} + +type FileMetadataResolver interface { + FileMetadataByLocation(Location) (FileMetadata, error) +} + +// FilePathResolver knows how to get a Location for given string paths and globs +type FilePathResolver interface { + // HasPath indicates if the given path exists in the underlying source. + HasPath(string) bool + // FilesByPath fetches a set of file references which have the given path (for an image, there may be multiple matches) + FilesByPath(paths ...string) ([]Location, error) + // FilesByGlob fetches a set of file references which the given glob matches + FilesByGlob(patterns ...string) ([]Location, error) + // FilesByMIMEType fetches a set of file references which the contents have been classified as one of the given MIME Types + FilesByMIMEType(types ...string) ([]Location, error) + // RelativeFileByPath fetches a single file at the given path relative to the layer squash of the given reference. + // This is helpful when attempting to find a file that is in the same layer or lower as another file. + RelativeFileByPath(_ Location, path string) *Location +} + +type FileLocationResolver interface { + AllLocations() <-chan Location +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/file_type.go b/ci/tools/openeuler-purl/syft-dev/syft/source/file_type.go new file mode 100644 index 0000000000000000000000000000000000000000..370ea0f8df0fd44e765c2a05729de67261f7c0c9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/file_type.go @@ -0,0 +1,70 @@ +package source + +import ( + "archive/tar" + "os" +) + +const ( + RegularFile FileType = "RegularFile" + // IrregularFile is how syft defines files that are neither regular, symbolic or directory. + // For ref: the seven standard Unix file types are regular, directory, symbolic link, + // FIFO special, block special, character special, and socket as defined by POSIX. + IrregularFile FileType = "IrregularFile" + HardLink FileType = "HardLink" + SymbolicLink FileType = "SymbolicLink" + CharacterDevice FileType = "CharacterDevice" + BlockDevice FileType = "BlockDevice" + Directory FileType = "Directory" + FIFONode FileType = "FIFONode" + Socket FileType = "Socket" +) + +type FileType string + +func newFileTypeFromTarHeaderTypeFlag(flag byte) FileType { + switch flag { + case tar.TypeReg, tar.TypeRegA: + return RegularFile + case tar.TypeLink: + return HardLink + case tar.TypeSymlink: + return SymbolicLink + case tar.TypeChar: + return CharacterDevice + case tar.TypeBlock: + return BlockDevice + case tar.TypeDir: + return Directory + case tar.TypeFifo: + return FIFONode + } + return IrregularFile +} + +func newFileTypeFromMode(mode os.FileMode) FileType { + switch { + case isSet(mode, os.ModeSymlink): + return SymbolicLink + case isSet(mode, os.ModeIrregular): + return IrregularFile + case isSet(mode, os.ModeCharDevice): + return CharacterDevice + case isSet(mode, os.ModeDevice): + return BlockDevice + case isSet(mode, os.ModeNamedPipe): + return FIFONode + case isSet(mode, os.ModeSocket): + return Socket + case mode.IsDir(): + return Directory + case mode.IsRegular(): + return RegularFile + default: + return IrregularFile + } +} + +func isSet(mode, field os.FileMode) bool { + return mode&field != 0 +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/image_metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/source/image_metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..0d70ed775aba41396a02a2494a838a0528051553 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/image_metadata.go @@ -0,0 +1,62 @@ +package source + +import "github.com/anchore/stereoscope/pkg/image" + +// ImageMetadata represents all static metadata that defines what a container image is. This is useful to later describe +// "what" was cataloged without needing the more complicated stereoscope Image objects or FileResolver objects. +type ImageMetadata struct { + UserInput string `json:"userInput"` + ID string `json:"imageID"` + ManifestDigest string `json:"manifestDigest"` + MediaType string `json:"mediaType"` + Tags []string `json:"tags"` + Size int64 `json:"imageSize"` + Layers []LayerMetadata `json:"layers"` + RawManifest []byte `json:"manifest"` + RawConfig []byte `json:"config"` + RepoDigests []string `json:"repoDigests"` + Architecture string `json:"architecture"` + Variant string `json:"architectureVariant,omitempty"` + OS string `json:"os"` +} + +// LayerMetadata represents all static metadata that defines what a container image layer is. +type LayerMetadata struct { + MediaType string `json:"mediaType"` + Digest string `json:"digest"` + Size int64 `json:"size"` +} + +// NewImageMetadata creates a new ImageMetadata object populated from the given stereoscope Image object and user configuration. +func NewImageMetadata(img *image.Image, userInput string) ImageMetadata { + // populate artifacts... + tags := make([]string, len(img.Metadata.Tags)) + for idx, tag := range img.Metadata.Tags { + tags[idx] = tag.String() + } + theImg := ImageMetadata{ + ID: img.Metadata.ID, + UserInput: userInput, + ManifestDigest: img.Metadata.ManifestDigest, + Size: img.Metadata.Size, + MediaType: string(img.Metadata.MediaType), + Tags: tags, + Layers: make([]LayerMetadata, len(img.Layers)), + RawConfig: img.Metadata.RawConfig, + RawManifest: img.Metadata.RawManifest, + RepoDigests: img.Metadata.RepoDigests, + Architecture: img.Metadata.Architecture, + Variant: img.Metadata.Variant, + OS: img.Metadata.OS, + } + + // populate image metadata + for idx, l := range img.Layers { + theImg.Layers[idx] = LayerMetadata{ + MediaType: string(l.Metadata.MediaType), + Digest: l.Metadata.Digest, + Size: l.Metadata.Size, + } + } + return theImg +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/image_squash_resolver.go b/ci/tools/openeuler-purl/syft-dev/syft/source/image_squash_resolver.go new file mode 100644 index 0000000000000000000000000000000000000000..8977023a102a0fba93e30f3b84e62b1b1355545f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/image_squash_resolver.go @@ -0,0 +1,194 @@ +package source + +import ( + "archive/tar" + "fmt" + "io" + + "github.com/anchore/stereoscope/pkg/file" + "github.com/anchore/stereoscope/pkg/filetree" + "github.com/anchore/stereoscope/pkg/image" +) + +var _ FileResolver = (*imageSquashResolver)(nil) + +// imageSquashResolver implements path and content access for the Squashed source option for container image data sources. +type imageSquashResolver struct { + img *image.Image +} + +// newImageSquashResolver returns a new resolver from the perspective of the squashed representation for the given image. +func newImageSquashResolver(img *image.Image) (*imageSquashResolver, error) { + if img.SquashedTree() == nil { + return nil, fmt.Errorf("the image does not have have a squashed tree") + } + + return &imageSquashResolver{ + img: img, + }, nil +} + +// HasPath indicates if the given path exists in the underlying source. +func (r *imageSquashResolver) HasPath(path string) bool { + return r.img.SquashedTree().HasPath(file.Path(path)) +} + +// FilesByPath returns all file.References that match the given paths within the squashed representation of the image. +func (r *imageSquashResolver) FilesByPath(paths ...string) ([]Location, error) { + uniqueFileIDs := file.NewFileReferenceSet() + uniqueLocations := make([]Location, 0) + + for _, path := range paths { + tree := r.img.SquashedTree() + _, ref, err := tree.File(file.Path(path), filetree.FollowBasenameLinks) + if err != nil { + return nil, err + } + if ref == nil { + // no file found, keep looking through layers + continue + } + + // don't consider directories (special case: there is no path information for /) + if ref.RealPath == "/" { + continue + } else if r.img.FileCatalog.Exists(*ref) { + metadata, err := r.img.FileCatalog.Get(*ref) + if err != nil { + return nil, fmt.Errorf("unable to get file metadata for path=%q: %w", ref.RealPath, err) + } + if metadata.Metadata.IsDir { + continue + } + } + + // a file may be a symlink, process it as such and resolve it + resolvedRef, err := r.img.ResolveLinkByImageSquash(*ref) + if err != nil { + return nil, fmt.Errorf("failed to resolve link from img (ref=%+v): %w", ref, err) + } + + if resolvedRef != nil && !uniqueFileIDs.Contains(*resolvedRef) { + uniqueFileIDs.Add(*resolvedRef) + uniqueLocations = append(uniqueLocations, NewLocationFromImage(path, *resolvedRef, r.img)) + } + } + + return uniqueLocations, nil +} + +// FilesByGlob returns all file.References that match the given path glob pattern within the squashed representation of the image. +func (r *imageSquashResolver) FilesByGlob(patterns ...string) ([]Location, error) { + uniqueFileIDs := file.NewFileReferenceSet() + uniqueLocations := make([]Location, 0) + + for _, pattern := range patterns { + results, err := r.img.SquashedTree().FilesByGlob(pattern, filetree.FollowBasenameLinks) + if err != nil { + return nil, fmt.Errorf("failed to resolve files by glob (%s): %w", pattern, err) + } + + for _, result := range results { + // don't consider directories (special case: there is no path information for /) + if result.MatchPath == "/" { + continue + } + + if r.img.FileCatalog.Exists(result.Reference) { + metadata, err := r.img.FileCatalog.Get(result.Reference) + if err != nil { + return nil, fmt.Errorf("unable to get file metadata for path=%q: %w", result.MatchPath, err) + } + if metadata.Metadata.IsDir { + continue + } + } + + resolvedLocations, err := r.FilesByPath(string(result.MatchPath)) + if err != nil { + return nil, fmt.Errorf("failed to find files by path (result=%+v): %w", result, err) + } + for _, resolvedLocation := range resolvedLocations { + if !uniqueFileIDs.Contains(resolvedLocation.ref) { + uniqueFileIDs.Add(resolvedLocation.ref) + uniqueLocations = append(uniqueLocations, resolvedLocation) + } + } + } + } + + return uniqueLocations, nil +} + +// RelativeFileByPath fetches a single file at the given path relative to the layer squash of the given reference. +// This is helpful when attempting to find a file that is in the same layer or lower as another file. For the +// imageSquashResolver, this is a simple path lookup. +func (r *imageSquashResolver) RelativeFileByPath(_ Location, path string) *Location { + paths, err := r.FilesByPath(path) + if err != nil { + return nil + } + if len(paths) == 0 { + return nil + } + + return &paths[0] +} + +// FileContentsByLocation fetches file contents for a single file reference, regardless of the source layer. +// If the path does not exist an error is returned. +func (r *imageSquashResolver) FileContentsByLocation(location Location) (io.ReadCloser, error) { + entry, err := r.img.FileCatalog.Get(location.ref) + if err != nil { + return nil, fmt.Errorf("unable to get metadata for path=%q from file catalog: %w", location.RealPath, err) + } + + switch entry.Metadata.TypeFlag { + case tar.TypeSymlink, tar.TypeLink: + // the location we are searching may be a symlink, we should always work with the resolved file + locations, err := r.FilesByPath(location.RealPath) + if err != nil { + return nil, fmt.Errorf("failed to resolve content location at location=%+v: %w", location, err) + } + + switch len(locations) { + case 0: + return nil, fmt.Errorf("link resolution failed while resolving content location: %+v", location) + case 1: + location = locations[0] + default: + return nil, fmt.Errorf("link resolution resulted in multiple results while resolving content location: %+v", location) + } + } + + return r.img.FileContentsByRef(location.ref) +} + +func (r *imageSquashResolver) AllLocations() <-chan Location { + results := make(chan Location) + go func() { + defer close(results) + for _, ref := range r.img.SquashedTree().AllFiles(file.AllTypes...) { + results <- NewLocationFromImage(string(ref.RealPath), ref, r.img) + } + }() + return results +} + +func (r *imageSquashResolver) FilesByMIMEType(types ...string) ([]Location, error) { + refs, err := r.img.FilesByMIMETypeFromSquash(types...) + if err != nil { + return nil, err + } + + var locations []Location + for _, ref := range refs { + locations = append(locations, NewLocationFromImage(string(ref.RealPath), ref, r.img)) + } + + return locations, nil +} + +func (r *imageSquashResolver) FileMetadataByLocation(location Location) (FileMetadata, error) { + return fileMetadataByLocation(r.img, location) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/image_squash_resolver_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/image_squash_resolver_test.go new file mode 100644 index 0000000000000000000000000000000000000000..7f0819b9ec77f2214034440dd9b0987bef9b3317 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/image_squash_resolver_test.go @@ -0,0 +1,500 @@ +package source + +import ( + "github.com/stretchr/testify/require" + "io" + "testing" + + "github.com/scylladb/go-set/strset" + "github.com/stretchr/testify/assert" + + "github.com/anchore/stereoscope/pkg/imagetest" +) + +func TestImageSquashResolver_FilesByPath(t *testing.T) { + cases := []struct { + name string + linkPath string + resolveLayer uint + resolvePath string + forcePositiveHasPath bool + }{ + { + name: "link with previous data", + linkPath: "/link-1", + resolveLayer: 1, + resolvePath: "/file-1.txt", + }, + { + name: "link with in layer data", + linkPath: "/link-within", + resolveLayer: 5, + resolvePath: "/file-3.txt", + }, + { + name: "link with overridden data", + linkPath: "/link-2", + resolveLayer: 7, + resolvePath: "/file-2.txt", + }, + { + name: "indirect link (with overridden data)", + linkPath: "/link-indirect", + resolveLayer: 7, + resolvePath: "/file-2.txt", + }, + { + name: "dead link", + linkPath: "/link-dead", + resolveLayer: 8, + resolvePath: "", + // the path should exist, even if the link is dead + forcePositiveHasPath: true, + }, + { + name: "ignore directories", + linkPath: "/bin", + resolvePath: "", + // the path should exist, even if we ignore it + forcePositiveHasPath: true, + }, + { + name: "parent is a link (with overridden data)", + linkPath: "/parent-link/file-4.txt", + resolveLayer: 11, + resolvePath: "/parent/file-4.txt", + }, + } + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", "image-symlinks") + + resolver, err := newImageSquashResolver(img) + if err != nil { + t.Fatalf("could not create resolver: %+v", err) + } + + hasPath := resolver.HasPath(c.linkPath) + if !c.forcePositiveHasPath { + if c.resolvePath != "" && !hasPath { + t.Errorf("expected HasPath() to indicate existance, but did not") + } else if c.resolvePath == "" && hasPath { + t.Errorf("expeced HasPath() to NOT indicate existance, but does") + } + } else if !hasPath { + t.Errorf("expected HasPath() to indicate existance, but did not (force path)") + } + + refs, err := resolver.FilesByPath(c.linkPath) + if err != nil { + t.Fatalf("could not use resolver: %+v", err) + } + + expectedRefs := 1 + if c.resolvePath == "" { + expectedRefs = 0 + } + + if len(refs) != expectedRefs { + t.Fatalf("unexpected number of resolutions: %d", len(refs)) + } + + if expectedRefs == 0 { + // nothing else to assert + return + } + + actual := refs[0] + + if string(actual.ref.RealPath) != c.resolvePath { + t.Errorf("bad resolve path: '%s'!='%s'", string(actual.ref.RealPath), c.resolvePath) + } + + if c.resolvePath != "" && string(actual.ref.RealPath) != actual.RealPath { + t.Errorf("we should always prefer real paths over ones with links") + } + + entry, err := img.FileCatalog.Get(actual.ref) + if err != nil { + t.Fatalf("failed to get metadata: %+v", err) + } + + if entry.Layer.Metadata.Index != c.resolveLayer { + t.Errorf("bad resolve layer: '%d'!='%d'", entry.Layer.Metadata.Index, c.resolveLayer) + } + }) + } +} + +func TestImageSquashResolver_FilesByGlob(t *testing.T) { + cases := []struct { + name string + glob string + resolveLayer uint + resolvePath string + }{ + { + name: "link with previous data", + glob: "**/link-1", + resolveLayer: 1, + resolvePath: "/file-1.txt", + }, + { + name: "link with in layer data", + glob: "**/link-within", + resolveLayer: 5, + resolvePath: "/file-3.txt", + }, + { + name: "link with overridden data", + glob: "**/link-2", + resolveLayer: 7, + resolvePath: "/file-2.txt", + }, + { + name: "indirect link (with overridden data)", + glob: "**/link-indirect", + resolveLayer: 7, + resolvePath: "/file-2.txt", + }, + { + name: "dead link", + glob: "**/link-dead", + // dead links are dead! they shouldn't match on globs + resolvePath: "", + }, + { + name: "ignore directories", + glob: "**/bin", + resolvePath: "", + }, + { + name: "parent without link", + glob: "**/parent/*.txt", + resolveLayer: 11, + resolvePath: "/parent/file-4.txt", + }, + { + name: "parent is a link (override)", + glob: "**/parent-link/file-4.txt", + resolveLayer: 11, + resolvePath: "/parent/file-4.txt", + }, + } + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", "image-symlinks") + + resolver, err := newImageSquashResolver(img) + if err != nil { + t.Fatalf("could not create resolver: %+v", err) + } + + refs, err := resolver.FilesByGlob(c.glob) + if err != nil { + t.Fatalf("could not use resolver: %+v", err) + } + + expectedRefs := 1 + if c.resolvePath == "" { + expectedRefs = 0 + } + + if len(refs) != expectedRefs { + t.Fatalf("unexpected number of resolutions: %d", len(refs)) + } + + if expectedRefs == 0 { + // nothing else to assert + return + } + + actual := refs[0] + + if string(actual.ref.RealPath) != c.resolvePath { + t.Errorf("bad resolve path: '%s'!='%s'", string(actual.ref.RealPath), c.resolvePath) + } + + if c.resolvePath != "" && string(actual.ref.RealPath) != actual.RealPath { + t.Errorf("we should always prefer real paths over ones with links") + } + + entry, err := img.FileCatalog.Get(actual.ref) + if err != nil { + t.Fatalf("failed to get metadata: %+v", err) + } + + if entry.Layer.Metadata.Index != c.resolveLayer { + t.Errorf("bad resolve layer: '%d'!='%d'", entry.Layer.Metadata.Index, c.resolveLayer) + } + }) + } +} + +func Test_imageSquashResolver_FilesByMIMEType(t *testing.T) { + + tests := []struct { + fixtureName string + mimeType string + expectedPaths *strset.Set + }{ + { + fixtureName: "image-simple", + mimeType: "text/plain", + expectedPaths: strset.New("/somefile-1.txt", "/somefile-2.txt", "/really/nested/file-3.txt"), + }, + } + + for _, test := range tests { + t.Run(test.fixtureName, func(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", test.fixtureName) + + resolver, err := newImageSquashResolver(img) + assert.NoError(t, err) + + locations, err := resolver.FilesByMIMEType(test.mimeType) + assert.NoError(t, err) + + assert.Len(t, locations, test.expectedPaths.Size()) + for _, l := range locations { + assert.True(t, test.expectedPaths.Has(l.RealPath), "does not have path %q", l.RealPath) + } + }) + } +} + +func Test_imageSquashResolver_hasFilesystemIDInLocation(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", "image-duplicate-path") + + resolver, err := newImageSquashResolver(img) + assert.NoError(t, err) + + locations, err := resolver.FilesByMIMEType("text/plain") + assert.NoError(t, err) + assert.NotEmpty(t, locations) + for _, location := range locations { + assert.NotEmpty(t, location.FileSystemID) + } + + locations, err = resolver.FilesByGlob("*.txt") + assert.NoError(t, err) + assert.NotEmpty(t, locations) + for _, location := range locations { + assert.NotEmpty(t, location.FileSystemID) + } + + locations, err = resolver.FilesByPath("/somefile-1.txt") + assert.NoError(t, err) + assert.NotEmpty(t, locations) + for _, location := range locations { + assert.NotEmpty(t, location.FileSystemID) + } + +} + +func TestSquashImageResolver_FilesContents(t *testing.T) { + + tests := []struct { + name string + fixture string + contents []string + }{ + { + name: "one degree", + fixture: "link-2", + contents: []string{ + "NEW file override!", // always from the squashed perspective + }, + }, + { + name: "two degrees", + fixture: "link-indirect", + contents: []string{ + "NEW file override!", // always from the squashed perspective + }, + }, + { + name: "dead link", + fixture: "link-dead", + contents: []string{}, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + img := imagetest.GetFixtureImage(t, "docker-archive", "image-symlinks") + + resolver, err := newImageSquashResolver(img) + assert.NoError(t, err) + + refs, err := resolver.FilesByPath(test.fixture) + require.NoError(t, err) + assert.Len(t, refs, len(test.contents)) + + for idx, loc := range refs { + + reader, err := resolver.FileContentsByLocation(loc) + require.NoError(t, err) + + actual, err := io.ReadAll(reader) + require.NoError(t, err) + + assert.Equal(t, test.contents[idx], string(actual)) + } + }) + } +} +func Test_imageSquashResolver_resolvesLinks(t *testing.T) { + tests := []struct { + name string + runner func(FileResolver) []Location + expected []Location + }{ + { + name: "by mimetype", + runner: func(resolver FileResolver) []Location { + // links should not show up when searching mimetype + actualLocations, err := resolver.FilesByMIMEType("text/plain") + assert.NoError(t, err) + return actualLocations + }, + expected: []Location{ + { + Coordinates: Coordinates{ + RealPath: "/etc/group", + }, + VirtualPath: "/etc/group", + }, + { + Coordinates: Coordinates{ + RealPath: "/etc/passwd", + }, + VirtualPath: "/etc/passwd", + }, + { + Coordinates: Coordinates{ + RealPath: "/etc/shadow", + }, + VirtualPath: "/etc/shadow", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-1.txt", + }, + VirtualPath: "/file-1.txt", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-3.txt", + }, + VirtualPath: "/file-3.txt", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/file-2.txt", + }, + { + Coordinates: Coordinates{ + RealPath: "/parent/file-4.txt", + }, + VirtualPath: "/parent/file-4.txt", + }, + }, + }, + { + name: "by glob", + runner: func(resolver FileResolver) []Location { + // links are searched, but resolve to the real files + actualLocations, err := resolver.FilesByGlob("*ink-*") + assert.NoError(t, err) + return actualLocations + }, + expected: []Location{ + { + Coordinates: Coordinates{ + RealPath: "/file-3.txt", + }, + VirtualPath: "/link-within", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-2", + }, + { + Coordinates: Coordinates{ + RealPath: "/file-1.txt", + }, + VirtualPath: "/link-1", + }, + }, + }, + { + name: "by path to degree 1 link", + runner: func(resolver FileResolver) []Location { + // links resolve to the final file + actualLocations, err := resolver.FilesByPath("/link-2") + assert.NoError(t, err) + return actualLocations + }, + expected: []Location{ + // we have multiple copies across layers + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-2", + }, + }, + }, + { + name: "by path to degree 2 link", + runner: func(resolver FileResolver) []Location { + // multiple links resolves to the final file + actualLocations, err := resolver.FilesByPath("/link-indirect") + assert.NoError(t, err) + return actualLocations + }, + expected: []Location{ + // we have multiple copies across layers + { + Coordinates: Coordinates{ + RealPath: "/file-2.txt", + }, + VirtualPath: "/link-indirect", + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + + img := imagetest.GetFixtureImage(t, "docker-archive", "image-symlinks") + + resolver, err := newImageSquashResolver(img) + assert.NoError(t, err) + + actualLocations := test.runner(resolver) + require.Len(t, actualLocations, len(test.expected)) + + // some operations on this resolver do not return stable results (order may be different across runs) + + expectedMap := make(map[string]string) + for _, e := range test.expected { + expectedMap[e.VirtualPath] = e.RealPath + } + + actualMap := make(map[string]string) + for _, a := range test.expected { + actualMap[a.VirtualPath] = a.RealPath + } + + assert.Equal(t, expectedMap, actualMap) + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/location.go b/ci/tools/openeuler-purl/syft-dev/syft/source/location.go new file mode 100644 index 0000000000000000000000000000000000000000..04acee9f526b79bd475b573150261c1037e9d651 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/location.go @@ -0,0 +1,117 @@ +package source + +import ( + "fmt" + + "github.com/anchore/stereoscope/pkg/file" + "github.com/anchore/stereoscope/pkg/image" + "github.com/anchore/syft/internal/log" +) + +// Location represents a path relative to a particular filesystem resolved to a specific file.Reference. This struct is used as a key +// in content fetching to uniquely identify a file relative to a request (the VirtualPath). +type Location struct { + Coordinates `cyclonedx:""` // Empty string here means there is no intermediate property name, e.g. syft:locations:0:path without "coordinates" + // note: it is IMPORTANT to ignore anything but the coordinates for a Location when considering the ID (hash value) + // since the coordinates are the minimally correct ID for a location (symlinks should not come into play) + VirtualPath string `hash:"ignore"` // The path to the file which may or may not have hardlinks / symlinks + ref file.Reference `hash:"ignore"` // The file reference relative to the stereoscope.FileCatalog that has more information about this location. +} + +// NewLocation creates a new Location representing a path without denoting a filesystem or FileCatalog reference. +func NewLocation(realPath string) Location { + return Location{ + Coordinates: Coordinates{ + RealPath: realPath, + }, + } +} + +// NewVirtualLocation creates a new location for a path accessed by a virtual path (a path with a symlink or hardlink somewhere in the path) +func NewVirtualLocation(realPath, virtualPath string) Location { + return Location{ + Coordinates: Coordinates{ + RealPath: realPath, + }, + VirtualPath: virtualPath, + } +} + +// NewLocationFromCoordinates creates a new location for the given Coordinates. +func NewLocationFromCoordinates(coordinates Coordinates) Location { + return Location{ + Coordinates: coordinates, + } +} + +// NewLocationFromImage creates a new Location representing the given path (extracted from the ref) relative to the given image. +func NewLocationFromImage(virtualPath string, ref file.Reference, img *image.Image) Location { + entry, err := img.FileCatalog.Get(ref) + if err != nil { + log.Warnf("unable to find file catalog entry for ref=%+v", ref) + return Location{ + Coordinates: Coordinates{ + RealPath: string(ref.RealPath), + }, + VirtualPath: virtualPath, + ref: ref, + } + } + + return Location{ + Coordinates: Coordinates{ + RealPath: string(ref.RealPath), + FileSystemID: entry.Layer.Metadata.Digest, + }, + VirtualPath: virtualPath, + ref: ref, + } +} + +// NewLocationFromDirectory creates a new Location representing the given path (extracted from the ref) relative to the given directory. +func NewLocationFromDirectory(responsePath string, ref file.Reference) Location { + return Location{ + Coordinates: Coordinates{ + RealPath: responsePath, + }, + ref: ref, + } +} + +// NewVirtualLocationFromDirectory creates a new Location representing the given path (extracted from the ref) relative to the given directory with a separate virtual access path. +func NewVirtualLocationFromDirectory(responsePath, virtualResponsePath string, ref file.Reference) Location { + if responsePath == virtualResponsePath { + return NewLocationFromDirectory(responsePath, ref) + } + return Location{ + Coordinates: Coordinates{ + RealPath: responsePath, + }, + VirtualPath: virtualResponsePath, + ref: ref, + } +} + +func (l Location) String() string { + str := "" + if l.ref.ID() != 0 { + str += fmt.Sprintf("id=%d ", l.ref.ID()) + } + + str += fmt.Sprintf("RealPath=%q", l.RealPath) + + if l.VirtualPath != "" { + str += fmt.Sprintf(" VirtualPath=%q", l.VirtualPath) + } + + if l.FileSystemID != "" { + str += fmt.Sprintf(" Layer=%q", l.FileSystemID) + } + return fmt.Sprintf("Location<%s>", str) +} + +func (l Location) Equals(other Location) bool { + return l.RealPath == other.RealPath && + l.VirtualPath == other.VirtualPath && + l.FileSystemID == other.FileSystemID +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/location_set.go b/ci/tools/openeuler-purl/syft-dev/syft/source/location_set.go new file mode 100644 index 0000000000000000000000000000000000000000..c2e915921b79e2767b8625998055902fcd474b2c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/location_set.go @@ -0,0 +1,78 @@ +package source + +import ( + "sort" + + "github.com/mitchellh/hashstructure/v2" +) + +type LocationSet struct { + set map[Location]struct{} +} + +func NewLocationSet(locations ...Location) (s LocationSet) { + for _, l := range locations { + s.Add(l) + } + + return s +} + +func (s *LocationSet) Add(locations ...Location) { + if s.set == nil { + s.set = make(map[Location]struct{}) + } + for _, l := range locations { + s.set[l] = struct{}{} + } +} + +func (s LocationSet) Remove(locations ...Location) { + if s.set == nil { + return + } + for _, l := range locations { + delete(s.set, l) + } +} + +func (s LocationSet) Contains(l Location) bool { + if s.set == nil { + return false + } + _, ok := s.set[l] + return ok +} + +func (s LocationSet) ToSlice() []Location { + if s.set == nil { + return nil + } + locations := make([]Location, len(s.set)) + idx := 0 + for v := range s.set { + locations[idx] = v + idx++ + } + sort.Sort(Locations(locations)) + return locations +} + +func (s *LocationSet) CoordinateSet() CoordinateSet { + if s.set == nil { + return NewCoordinateSet() + } + set := NewCoordinateSet() + for l := range s.set { + set.Add(l.Coordinates) + } + return set +} + +func (s LocationSet) Hash() (uint64, error) { + // access paths and filesystem IDs are not considered when hashing a location set, only the real paths + return hashstructure.Hash(s.CoordinateSet().Paths(), hashstructure.FormatV2, &hashstructure.HashOptions{ + ZeroNil: true, + SlicesAsSets: true, + }) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/location_set_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/location_set_test.go new file mode 100644 index 0000000000000000000000000000000000000000..dc80a4962ca5fa85109c50559ae4ac22250a60d4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/location_set_test.go @@ -0,0 +1,178 @@ +package source + +import ( + "github.com/anchore/syft/syft/artifact" + "github.com/stretchr/testify/require" + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestLocationSet(t *testing.T) { + + etcHostsLinkVar := Location{ + Coordinates: Coordinates{ + RealPath: "/etc/hosts", + FileSystemID: "a", + }, + VirtualPath: "/var/etc/hosts", + } + + etcHostsLinkHome := Location{ + Coordinates: Coordinates{ + RealPath: "/etc/hosts", + FileSystemID: "a", + }, + VirtualPath: "/home/wagoodman/hosts", + } + + binA := Location{ + Coordinates: Coordinates{ + RealPath: "/bin", + FileSystemID: "a", + }, + VirtualPath: "/usr/bin", + } + + binB := Location{ + Coordinates: Coordinates{ + RealPath: "/bin", + FileSystemID: "b", + }, + VirtualPath: "/usr/bin", + } + + tests := []struct { + name string + input []Location + expected []Location + }{ + { + name: "de-dup same location", + input: []Location{ + binA, binA, binA, + }, + expected: []Location{ + binA, + }, + }, + { + name: "dont de-dup different filesystem", + input: []Location{ + binB, binA, + }, + expected: []Location{ + binA, binB, + }, + }, + { + name: "dont de-dup different virtual paths", + input: []Location{ + etcHostsLinkVar, etcHostsLinkHome, + }, + expected: []Location{ + etcHostsLinkHome, etcHostsLinkVar, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + set := NewLocationSet(test.input...) + assert.Equal(t, test.expected, set.ToSlice()) + }) + } +} + +func TestLocationSet_Hash(t *testing.T) { + etcAlink := Location{ + Coordinates: Coordinates{ + RealPath: "/etc/hosts", + FileSystemID: "a", + }, + VirtualPath: "/var/etc/hosts", + } + + etcA := Location{ + Coordinates: Coordinates{ + RealPath: "/etc/hosts", + FileSystemID: "a", + }, + } + + etcB := Location{ + Coordinates: Coordinates{ + RealPath: "/etc/hosts", + FileSystemID: "b", + }, + } + + binA := Location{ + Coordinates: Coordinates{ + RealPath: "/bin", + FileSystemID: "a", + }, + VirtualPath: "/usr/bin", + } + + binB := Location{ + Coordinates: Coordinates{ + RealPath: "/bin", + FileSystemID: "b", + }, + VirtualPath: "/usr/bin", + } + + tests := []struct { + name string + setA LocationSet + setB LocationSet + want assert.ComparisonAssertionFunc + }{ + { + name: "empty sets have the same hash", + setA: NewLocationSet(), + setB: NewLocationSet(), + want: assert.Equal, + }, + { + name: "sets with same elements accessed through different paths have the same hash", + setA: NewLocationSet(binA, etcA), + setB: NewLocationSet(etcAlink, binA), + want: assert.Equal, + }, + { + name: "sets with same elements have the same hash", + setA: NewLocationSet(binA, etcA), + setB: NewLocationSet(etcA, binA), + want: assert.Equal, + }, + { + name: "sets with different element counts have different hashes", + setA: NewLocationSet(binA, etcA), + setB: NewLocationSet(binA), + want: assert.NotEqual, + }, + { + name: "sets with same path but different FS IDs have the same hash", + setA: NewLocationSet(binA), + setB: NewLocationSet(binB), + want: assert.Equal, + }, + { + name: "sets with same paths but different FS IDs have the same hash", + setA: NewLocationSet(etcA, binA), + setB: NewLocationSet(binB, etcB), + want: assert.Equal, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + gotA, err := artifact.IDByHash(tt.setA) + require.NoError(t, err) + gotB, err := artifact.IDByHash(tt.setB) + require.NoError(t, err) + tt.want(t, gotA, gotB) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/location_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/location_test.go new file mode 100644 index 0000000000000000000000000000000000000000..eb35320585536fb03ef9ad78d2fadd5dd2c86e53 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/location_test.go @@ -0,0 +1,47 @@ +package source + +import ( + "testing" + + "github.com/anchore/stereoscope/pkg/file" + "github.com/stretchr/testify/assert" +) + +func TestLocation_ID(t *testing.T) { + tests := []struct { + name string + coordinates Coordinates + virtualPath string + ref file.Reference + }{ + { + name: "coordinates should match location hash", + coordinates: Coordinates{ + RealPath: "path!", + FileSystemID: "filesystem!", + }, + }, + { + name: "coordinates should match location hash (with extra fields)", + coordinates: Coordinates{ + RealPath: "path!", + FileSystemID: "filesystem!", + }, + virtualPath: "virtualPath!", + ref: file.Reference{ + RealPath: "other-real-path!", + }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + l := Location{ + Coordinates: test.coordinates, + VirtualPath: test.virtualPath, + ref: test.ref, + } + assert.Equal(t, l.ID(), test.coordinates.ID()) + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/locations.go b/ci/tools/openeuler-purl/syft-dev/syft/source/locations.go new file mode 100644 index 0000000000000000000000000000000000000000..045d1ed9d3cd4dd0fc750c129074247ec66fa21d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/locations.go @@ -0,0 +1,21 @@ +package source + +type Locations []Location + +func (l Locations) Len() int { + return len(l) +} + +func (l Locations) Less(i, j int) bool { + if l[i].RealPath == l[j].RealPath { + if l[i].VirtualPath == l[j].VirtualPath { + return l[i].FileSystemID < l[j].FileSystemID + } + return l[i].VirtualPath < l[j].VirtualPath + } + return l[i].RealPath < l[j].RealPath +} + +func (l Locations) Swap(i, j int) { + l[i], l[j] = l[j], l[i] +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/metadata.go b/ci/tools/openeuler-purl/syft-dev/syft/source/metadata.go new file mode 100644 index 0000000000000000000000000000000000000000..b9747362e26bb691fd695825c67745b6df8bb434 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/metadata.go @@ -0,0 +1,8 @@ +package source + +// Metadata represents any static source data that helps describe "what" was cataloged. +type Metadata struct { + Scheme Scheme // the source data scheme type (directory or image) + ImageMetadata ImageMetadata // all image info (image only) + Path string // the root path to be cataloged (directory only) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/mock_resolver.go b/ci/tools/openeuler-purl/syft-dev/syft/source/mock_resolver.go new file mode 100644 index 0000000000000000000000000000000000000000..51d7edc494466d76e16c4861e4be51ae2714ccb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/mock_resolver.go @@ -0,0 +1,162 @@ +package source + +import ( + "fmt" + "io" + "os" + + "github.com/bmatcuk/doublestar/v4" +) + +var _ FileResolver = (*MockResolver)(nil) + +// MockResolver implements the FileResolver interface and is intended for use *only in test code*. +// It provides an implementation that can resolve local filesystem paths using only a provided discrete list of file +// paths, which are typically paths to test fixtures. +type MockResolver struct { + locations []Location + metadata map[Location]FileMetadata + mimeTypeIndex map[string][]Location +} + +// NewMockResolverForPaths creates a new MockResolver, where the only resolvable +// files are those specified by the supplied paths. +func NewMockResolverForPaths(paths ...string) *MockResolver { + var locations []Location + for _, p := range paths { + locations = append(locations, NewLocation(p)) + } + + return &MockResolver{ + locations: locations, + metadata: make(map[Location]FileMetadata), + } +} + +func NewMockResolverForPathsWithMetadata(metadata map[Location]FileMetadata) *MockResolver { + var locations []Location + var mimeTypeIndex = make(map[string][]Location) + for l, m := range metadata { + locations = append(locations, l) + mimeTypeIndex[m.MIMEType] = append(mimeTypeIndex[m.MIMEType], l) + } + + return &MockResolver{ + locations: locations, + metadata: metadata, + mimeTypeIndex: mimeTypeIndex, + } +} + +// HasPath indicates if the given path exists in the underlying source. +func (r MockResolver) HasPath(path string) bool { + for _, l := range r.locations { + if l.RealPath == path { + return true + } + } + return false +} + +// String returns the string representation of the MockResolver. +func (r MockResolver) String() string { + return fmt.Sprintf("mock:(%s,...)", r.locations[0].RealPath) +} + +// FileContentsByLocation fetches file contents for a single location. If the +// path does not exist, an error is returned. +func (r MockResolver) FileContentsByLocation(location Location) (io.ReadCloser, error) { + for _, l := range r.locations { + if l == location { + return os.Open(location.RealPath) + } + } + + return nil, fmt.Errorf("no file for location: %v", location) +} + +// FilesByPath returns all Locations that match the given paths. +func (r MockResolver) FilesByPath(paths ...string) ([]Location, error) { + var results []Location + for _, p := range paths { + for _, location := range r.locations { + if p == location.RealPath { + results = append(results, NewLocation(p)) + } + } + } + + return results, nil +} + +// FilesByGlob returns all Locations that match the given path glob pattern. +func (r MockResolver) FilesByGlob(patterns ...string) ([]Location, error) { + var results []Location + for _, pattern := range patterns { + for _, location := range r.locations { + matches, err := doublestar.Match(pattern, location.RealPath) + if err != nil { + return nil, err + } + if matches { + results = append(results, location) + } + } + } + + return results, nil +} + +// RelativeFileByPath returns a single Location for the given path. +func (r MockResolver) RelativeFileByPath(_ Location, path string) *Location { + paths, err := r.FilesByPath(path) + if err != nil { + return nil + } + + if len(paths) < 1 { + return nil + } + + return &paths[0] +} + +func (r MockResolver) AllLocations() <-chan Location { + results := make(chan Location) + go func() { + defer close(results) + for _, l := range r.locations { + results <- l + } + }() + return results +} + +func (r MockResolver) FileMetadataByLocation(l Location) (FileMetadata, error) { + info, err := os.Stat(l.RealPath) + if err != nil { + return FileMetadata{}, err + } + + // other types not supported + ty := RegularFile + if info.IsDir() { + ty = Directory + } + + return FileMetadata{ + Mode: info.Mode(), + Type: ty, + UserID: 0, // not supported + GroupID: 0, // not supported + Size: info.Size(), + }, nil +} + +func (r MockResolver) FilesByMIMEType(types ...string) ([]Location, error) { + var locations []Location + for _, ty := range types { + locations = append(r.mimeTypeIndex[ty], locations...) + } + return locations, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/scheme.go b/ci/tools/openeuler-purl/syft-dev/syft/source/scheme.go new file mode 100644 index 0000000000000000000000000000000000000000..1c90dba033a4fe35c7318e658b410f61489637ce --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/scheme.go @@ -0,0 +1,73 @@ +package source + +import ( + "fmt" + "strings" + + "github.com/anchore/stereoscope/pkg/image" + "github.com/mitchellh/go-homedir" + "github.com/spf13/afero" +) + +// Scheme represents the optional prefixed string at the beginning of a user request (e.g. "docker:"). +type Scheme string + +const ( + // UnknownScheme is the default scheme + UnknownScheme Scheme = "UnknownScheme" + // DirectoryScheme indicates the source being cataloged is a directory on the root filesystem + DirectoryScheme Scheme = "DirectoryScheme" + // ImageScheme indicates the source being cataloged is a container image + ImageScheme Scheme = "ImageScheme" + // FileScheme indicates the source being cataloged is a single file + FileScheme Scheme = "FileScheme" +) + +var AllSchemes = []Scheme{ + DirectoryScheme, + ImageScheme, + FileScheme, +} + +func DetectScheme(fs afero.Fs, imageDetector sourceDetector, userInput string) (Scheme, image.Source, string, error) { + switch { + case strings.HasPrefix(userInput, "dir:"): + dirLocation, err := homedir.Expand(strings.TrimPrefix(userInput, "dir:")) + if err != nil { + return UnknownScheme, image.UnknownSource, "", fmt.Errorf("unable to expand directory path: %w", err) + } + return DirectoryScheme, image.UnknownSource, dirLocation, nil + + case strings.HasPrefix(userInput, "file:"): + fileLocation, err := homedir.Expand(strings.TrimPrefix(userInput, "file:")) + if err != nil { + return UnknownScheme, image.UnknownSource, "", fmt.Errorf("unable to expand directory path: %w", err) + } + return FileScheme, image.UnknownSource, fileLocation, nil + } + + // try the most specific sources first and move out towards more generic sources. + + // first: let's try the image detector, which has more scheme parsing internal to stereoscope + source, imageSpec, err := imageDetector(userInput) + if err == nil && source != image.UnknownSource { + return ImageScheme, source, imageSpec, nil + } + + // next: let's try more generic sources (dir, file, etc.) + location, err := homedir.Expand(userInput) + if err != nil { + return UnknownScheme, image.UnknownSource, "", fmt.Errorf("unable to expand potential directory path: %w", err) + } + + fileMeta, err := fs.Stat(location) + if err != nil { + return UnknownScheme, source, "", nil + } + + if fileMeta.IsDir() { + return DirectoryScheme, source, location, nil + } + + return FileScheme, source, location, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/scheme_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/scheme_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4e94f602c37fc79bb63d27e50a33787099af7412 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/scheme_test.go @@ -0,0 +1,307 @@ +package source + +import ( + "os" + "testing" + + "github.com/anchore/stereoscope/pkg/image" + "github.com/mitchellh/go-homedir" + "github.com/spf13/afero" + "github.com/stretchr/testify/assert" +) + +func TestDetectScheme(t *testing.T) { + type detectorResult struct { + src image.Source + ref string + err error + } + + testCases := []struct { + name string + userInput string + dirs []string + files []string + detection detectorResult + expectedScheme Scheme + expectedLocation string + }{ + { + name: "docker-image-ref", + userInput: "wagoodman/dive:latest", + detection: detectorResult{ + src: image.DockerDaemonSource, + ref: "wagoodman/dive:latest", + }, + expectedScheme: ImageScheme, + expectedLocation: "wagoodman/dive:latest", + }, + { + name: "docker-image-ref-no-tag", + userInput: "wagoodman/dive", + detection: detectorResult{ + src: image.DockerDaemonSource, + ref: "wagoodman/dive", + }, + expectedScheme: ImageScheme, + expectedLocation: "wagoodman/dive", + }, + { + name: "registry-image-explicit-scheme", + userInput: "registry:wagoodman/dive:latest", + detection: detectorResult{ + src: image.OciRegistrySource, + ref: "wagoodman/dive:latest", + }, + expectedScheme: ImageScheme, + expectedLocation: "wagoodman/dive:latest", + }, + { + name: "docker-image-explicit-scheme", + userInput: "docker:wagoodman/dive:latest", + detection: detectorResult{ + src: image.DockerDaemonSource, + ref: "wagoodman/dive:latest", + }, + expectedScheme: ImageScheme, + expectedLocation: "wagoodman/dive:latest", + }, + { + name: "docker-image-explicit-scheme-no-tag", + userInput: "docker:wagoodman/dive", + detection: detectorResult{ + src: image.DockerDaemonSource, + ref: "wagoodman/dive", + }, + expectedScheme: ImageScheme, + expectedLocation: "wagoodman/dive", + }, + { + name: "docker-image-edge-case", + userInput: "docker:latest", + detection: detectorResult{ + src: image.DockerDaemonSource, + ref: "latest", + }, + expectedScheme: ImageScheme, + // we expected to be able to handle this case better, however, I don't see a way to do this + // the user will need to provide more explicit input (docker:docker:latest) + expectedLocation: "latest", + }, + { + name: "docker-image-edge-case-explicit", + userInput: "docker:docker:latest", + detection: detectorResult{ + src: image.DockerDaemonSource, + ref: "docker:latest", + }, + expectedScheme: ImageScheme, + // we expected to be able to handle this case better, however, I don't see a way to do this + // the user will need to provide more explicit input (docker:docker:latest) + expectedLocation: "docker:latest", + }, + { + name: "oci-tar", + userInput: "some/path-to-file", + detection: detectorResult{ + src: image.OciTarballSource, + ref: "some/path-to-file", + }, + expectedScheme: ImageScheme, + expectedLocation: "some/path-to-file", + }, + { + name: "oci-dir", + userInput: "some/path-to-dir", + detection: detectorResult{ + src: image.OciDirectorySource, + ref: "some/path-to-dir", + }, + dirs: []string{"some/path-to-dir"}, + expectedScheme: ImageScheme, + expectedLocation: "some/path-to-dir", + }, + { + name: "guess-dir", + userInput: "some/path-to-dir", + detection: detectorResult{ + src: image.UnknownSource, + ref: "", + }, + dirs: []string{"some/path-to-dir"}, + expectedScheme: DirectoryScheme, + expectedLocation: "some/path-to-dir", + }, + { + name: "generic-dir-does-not-exist", + userInput: "some/path-to-dir", + detection: detectorResult{ + src: image.DockerDaemonSource, + ref: "some/path-to-dir", + }, + expectedScheme: ImageScheme, + expectedLocation: "some/path-to-dir", + }, + { + name: "found-podman-image-scheme", + userInput: "podman:something:latest", + detection: detectorResult{ + src: image.PodmanDaemonSource, + ref: "something:latest", + }, + expectedScheme: ImageScheme, + expectedLocation: "something:latest", + }, + { + name: "explicit-dir", + userInput: "dir:some/path-to-dir", + detection: detectorResult{ + src: image.UnknownSource, + ref: "", + }, + dirs: []string{"some/path-to-dir"}, + expectedScheme: DirectoryScheme, + expectedLocation: "some/path-to-dir", + }, + { + name: "explicit-file", + userInput: "file:some/path-to-file", + detection: detectorResult{ + src: image.UnknownSource, + ref: "", + }, + files: []string{"some/path-to-file"}, + expectedScheme: FileScheme, + expectedLocation: "some/path-to-file", + }, + { + name: "implicit-file", + userInput: "some/path-to-file", + detection: detectorResult{ + src: image.UnknownSource, + ref: "", + }, + files: []string{"some/path-to-file"}, + expectedScheme: FileScheme, + expectedLocation: "some/path-to-file", + }, + { + name: "explicit-current-dir", + userInput: "dir:.", + detection: detectorResult{ + src: image.UnknownSource, + ref: "", + }, + expectedScheme: DirectoryScheme, + expectedLocation: ".", + }, + { + name: "current-dir", + userInput: ".", + detection: detectorResult{ + src: image.UnknownSource, + ref: "", + }, + expectedScheme: DirectoryScheme, + expectedLocation: ".", + }, + // we should support tilde expansion + { + name: "tilde-expansion-image-implicit", + userInput: "~/some-path", + detection: detectorResult{ + src: image.OciDirectorySource, + ref: "~/some-path", + }, + expectedScheme: ImageScheme, + expectedLocation: "~/some-path", + }, + { + name: "tilde-expansion-dir-implicit", + userInput: "~/some-path", + detection: detectorResult{ + src: image.UnknownSource, + ref: "", + }, + dirs: []string{"~/some-path"}, + expectedScheme: DirectoryScheme, + expectedLocation: "~/some-path", + }, + { + name: "tilde-expansion-dir-explicit-exists", + userInput: "dir:~/some-path", + dirs: []string{"~/some-path"}, + expectedScheme: DirectoryScheme, + expectedLocation: "~/some-path", + }, + { + name: "tilde-expansion-dir-explicit-dne", + userInput: "dir:~/some-path", + expectedScheme: DirectoryScheme, + expectedLocation: "~/some-path", + }, + { + name: "tilde-expansion-dir-implicit-dne", + userInput: "~/some-path", + expectedScheme: UnknownScheme, + expectedLocation: "", + }, + } + for _, test := range testCases { + t.Run(test.name, func(t *testing.T) { + fs := afero.NewMemMapFs() + + for _, p := range test.dirs { + expandedExpectedLocation, err := homedir.Expand(p) + if err != nil { + t.Fatalf("unable to expand path=%q: %+v", p, err) + } + err = fs.Mkdir(expandedExpectedLocation, os.ModePerm) + if err != nil { + t.Fatalf("failed to create dummy dir: %+v", err) + } + } + + for _, p := range test.files { + expandedExpectedLocation, err := homedir.Expand(p) + if err != nil { + t.Fatalf("unable to expand path=%q: %+v", p, err) + } + _, err = fs.Create(expandedExpectedLocation) + if err != nil { + t.Fatalf("failed to create dummy file: %+v", err) + } + } + + imageDetector := func(string) (image.Source, string, error) { + // lean on the users real home directory value + switch test.detection.src { + case image.OciDirectorySource, image.DockerTarballSource, image.OciTarballSource: + expandedExpectedLocation, err := homedir.Expand(test.expectedLocation) + if err != nil { + t.Fatalf("unable to expand path=%q: %+v", test.expectedLocation, err) + } + return test.detection.src, expandedExpectedLocation, test.detection.err + default: + return test.detection.src, test.detection.ref, test.detection.err + } + } + + actualScheme, actualSource, actualLocation, err := DetectScheme(fs, imageDetector, test.userInput) + if err != nil { + t.Fatalf("unexpected err : %+v", err) + } + + assert.Equal(t, test.detection.src, actualSource, "mismatched source") + assert.Equal(t, test.expectedScheme, actualScheme, "mismatched scheme") + + // lean on the users real home directory value + expandedExpectedLocation, err := homedir.Expand(test.expectedLocation) + if err != nil { + t.Fatalf("unable to expand path=%q: %+v", test.expectedLocation, err) + } + + assert.Equal(t, expandedExpectedLocation, actualLocation, "mismatched location") + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/scope.go b/ci/tools/openeuler-purl/syft-dev/syft/source/scope.go new file mode 100644 index 0000000000000000000000000000000000000000..e959d1a420f79b0665cc816f81ca11c612514b2c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/scope.go @@ -0,0 +1,36 @@ +package source + +import "strings" + +// Scope indicates "how" or from "which perspectives" the source object should be cataloged from. +type Scope string + +const ( + // UnknownScope is the default scope + UnknownScope Scope = "UnknownScope" + // SquashedScope indicates to only catalog content visible from the squashed filesystem representation (what can be seen only within the container at runtime) + SquashedScope Scope = "Squashed" + // AllLayersScope indicates to catalog content on all layers, irregardless if it is visible from the container at runtime. + AllLayersScope Scope = "AllLayers" +) + +// AllScopes is a slice containing all possible scope options +var AllScopes = []Scope{ + SquashedScope, + AllLayersScope, +} + +// ParseScope returns a scope as indicated from the given string. +func ParseScope(userStr string) Scope { + switch strings.ToLower(userStr) { + case strings.ToLower(SquashedScope.String()): + return SquashedScope + case "all-layers", strings.ToLower(AllLayersScope.String()): + return AllLayersScope + } + return UnknownScope +} + +func (o Scope) String() string { + return string(o) +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/source.go b/ci/tools/openeuler-purl/syft-dev/syft/source/source.go new file mode 100644 index 0000000000000000000000000000000000000000..daca5c4174e5f9a5bb9ca1a2e24c4f7f89750cdd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/source.go @@ -0,0 +1,494 @@ +/* +Package source provides an abstraction to allow a user to loosely define a data source to catalog and expose a common interface that +catalogers and use explore and analyze data from the data source. All valid (cataloggable) data sources are defined +within this package. +*/ +package source + +import ( + "context" + "fmt" + "github.com/bmatcuk/doublestar/v4" + "github.com/mholt/archiver/v3" + "github.com/sassoftware/go-rpmutils" + "io/ioutil" + "os" + "path/filepath" + "strings" + "sync" + + "github.com/anchore/stereoscope" + "github.com/anchore/stereoscope/pkg/image" + "github.com/anchore/syft/internal/log" + "github.com/spf13/afero" +) + +// Source is an object that captures the data source to be cataloged, configuration, and a specific resolver used +// in cataloging (based on the data source and configuration) +type Source struct { + Image *image.Image // the image object to be cataloged (image only) + Metadata Metadata + directoryResolver *directoryResolver + path string + mutex *sync.Mutex + Exclusions []string +} + +// Input is an object that captures the detected user input regarding source location, scheme, and provider type. +// It acts as a struct input for some source constructors. +type Input struct { + UserInput string + Scheme Scheme + ImageSource image.Source + Location string + Platform string + autoDetectAvailableImageSources bool +} + +// ParseInput generates a source Input that can be used as an argument to generate a new source +// from specific providers including a registry. +func ParseInput(userInput string, platform string, detectAvailableImageSources bool) (*Input, error) { + fs := afero.NewOsFs() + scheme, source, location, err := DetectScheme(fs, image.DetectSource, userInput) + if err != nil { + return nil, err + } + + if source == image.UnknownSource { + // only run for these two scheme + // only check on packages command, attest we automatically try to pull from userInput + switch scheme { + case ImageScheme, UnknownScheme: + if detectAvailableImageSources { + if imagePullSource := image.DetermineDefaultImagePullSource(userInput); imagePullSource != image.UnknownSource { + scheme = ImageScheme + source = imagePullSource + location = userInput + } + } + if location == "" { + location = userInput + } + default: + } + } + + if scheme != ImageScheme && platform != "" { + return nil, fmt.Errorf("cannot specify a platform for a non-image source") + } + + // collect user input for downstream consumption + return &Input{ + UserInput: userInput, + Scheme: scheme, + ImageSource: source, + Location: location, + Platform: platform, + autoDetectAvailableImageSources: detectAvailableImageSources, + }, nil +} + +type sourceDetector func(string) (image.Source, string, error) + +func NewFromRegistry(in Input, registryOptions *image.RegistryOptions, exclusions []string) (*Source, func(), error) { + source, cleanupFn, err := generateImageSource(in, registryOptions) + if source != nil { + source.Exclusions = exclusions + } + return source, cleanupFn, err +} + +// New produces a Source based on userInput like dir: or image:tag +func New(in Input, registryOptions *image.RegistryOptions, exclusions []string) (*Source, func(), error) { + var err error + fs := afero.NewOsFs() + var source *Source + cleanupFn := func() {} + + switch in.Scheme { + case FileScheme: + source, cleanupFn, err = generateFileSource(fs, in.Location) + case DirectoryScheme: + source, cleanupFn, err = generateDirectorySource(fs, in.Location) + case ImageScheme: + source, cleanupFn, err = generateImageSource(in, registryOptions) + default: + err = fmt.Errorf("unable to process input for scanning: %q", in.UserInput) + } + + if err == nil { + source.Exclusions = exclusions + } + + return source, cleanupFn, err +} + +func generateImageSource(in Input, registryOptions *image.RegistryOptions) (*Source, func(), error) { + img, cleanup, err := getImageWithRetryStrategy(in, registryOptions) + if err != nil || img == nil { + return nil, cleanup, fmt.Errorf("could not fetch image %q: %w", in.Location, err) + } + + s, err := NewFromImage(img, in.Location) + if err != nil { + return nil, cleanup, fmt.Errorf("could not populate source with image: %w", err) + } + + return &s, cleanup, nil +} + +func parseScheme(userInput string) string { + parts := strings.SplitN(userInput, ":", 2) + if len(parts) < 2 { + return "" + } + + return parts[0] +} + +func getImageWithRetryStrategy(in Input, registryOptions *image.RegistryOptions) (*image.Image, func(), error) { + ctx := context.TODO() + + var opts []stereoscope.Option + if registryOptions != nil { + opts = append(opts, stereoscope.WithRegistryOptions(*registryOptions)) + } + + if in.Platform != "" { + opts = append(opts, stereoscope.WithPlatform(in.Platform)) + } + + img, err := stereoscope.GetImageFromSource(ctx, in.Location, in.ImageSource, opts...) + cleanup := func() { + if err := img.Cleanup(); err != nil { + log.Warnf("unable to cleanup image=%q: %w", in.UserInput, err) + } + } + if err == nil { + // Success on the first try! + return img, cleanup, nil + } + + scheme := parseScheme(in.UserInput) + if !(scheme == "docker" || scheme == "registry") { + // Image retrieval failed, and we shouldn't retry it. It's most likely that the + // user _did_ intend the parsed scheme, but there was a legitimate failure with + // using the scheme to load the image. Alert the user to this failure, so they + // can fix the problem. + return nil, nil, err + } + + // Maybe the user wanted "docker" or "registry" to refer to an _image name_ + // (e.g. "docker:latest"), not a scheme. We'll retry image retrieval with this + // alternative interpretation, in an attempt to avoid unnecessary user friction. + + log.Warnf( + "scheme %q specified, but it coincides with a common image name; re-examining user input %q"+ + " without scheme parsing because image retrieval using scheme parsing was unsuccessful: %v", + scheme, + in.UserInput, + err, + ) + + // We need to determine the image source again, such that this determination + // doesn't take scheme parsing into account. + if in.autoDetectAvailableImageSources { + in.ImageSource = image.DetermineDefaultImagePullSource(in.UserInput) + } + img, err = stereoscope.GetImageFromSource(ctx, in.UserInput, in.ImageSource, opts...) + cleanup = func() { + if err := img.Cleanup(); err != nil { + log.Warnf("unable to cleanup image=%q: %w", in.UserInput, err) + } + } + return img, cleanup, err +} + +func generateDirectorySource(fs afero.Fs, location string) (*Source, func(), error) { + fileMeta, err := fs.Stat(location) + if err != nil { + return nil, func() {}, fmt.Errorf("unable to stat dir=%q: %w", location, err) + } + + if !fileMeta.IsDir() { + return nil, func() {}, fmt.Errorf("given path is not a directory (path=%q): %w", location, err) + } + + s, err := NewFromDirectory(location) + if err != nil { + return nil, func() {}, fmt.Errorf("could not populate source from path=%q: %w", location, err) + } + + return &s, func() {}, nil +} + +func generateFileSource(fs afero.Fs, location string) (*Source, func(), error) { + fileMeta, err := fs.Stat(location) + if err != nil { + return nil, func() {}, fmt.Errorf("unable to stat dir=%q: %w", location, err) + } + + if fileMeta.IsDir() { + return nil, func() {}, fmt.Errorf("given path is not a directory (path=%q): %w", location, err) + } + + s, cleanupFn := NewFromFile(location) + + return &s, cleanupFn, nil +} + +// NewFromDirectory creates a new source object tailored to catalog a given filesystem directory recursively. +func NewFromDirectory(path string) (Source, error) { + return Source{ + mutex: &sync.Mutex{}, + Metadata: Metadata{ + Scheme: DirectoryScheme, + Path: path, + }, + path: path, + }, nil +} + +// NewFromFile creates a new source object tailored to catalog a file. +func NewFromFile(path string) (Source, func()) { + analysisPath, cleanupFn := fileAnalysisPath(path) + + return Source{ + mutex: &sync.Mutex{}, + Metadata: Metadata{ + Scheme: FileScheme, + Path: path, + }, + path: analysisPath, + }, cleanupFn +} + +// fileAnalysisPath returns the path given, or in the case the path is an archive, the location where the archive +// contents have been made available. A cleanup function is provided for any temp files created (if any). +func fileAnalysisPath(path string) (string, func()) { + var analysisPath = path + var cleanupFn = func() {} + if filepath.Ext(path) == ".rpm" { + log.Debugf("to catalog a rpm source") + rpmAnalysisPath, tmpCleanup, err := getAnalysisPathInRpmSource(path) + if err == nil { + cleanupFn = tmpCleanup + return rpmAnalysisPath, cleanupFn + } + } + // if the given file is an archive (as indicated by the file extension and not MIME type) then unarchive it and + // use the contents as the source. Note: this does NOT recursively unarchive contents, only the given path is + // unarchived. + envelopedUnarchiver, err := archiver.ByExtension(path) + if unarchiver, ok := envelopedUnarchiver.(archiver.Unarchiver); err == nil && ok { + unarchivedPath, tmpCleanup, err := unarchiveToTmp(path, unarchiver) + if err != nil { + log.Warnf("file could not be unarchived: %+v", err) + } else { + log.Debugf("source path is an archive") + analysisPath = unarchivedPath + } + if tmpCleanup != nil { + cleanupFn = tmpCleanup + } + } + return analysisPath, cleanupFn +} + +// NewFromImage creates a new source object tailored to catalog a given container image, relative to the +// option given (e.g. all-layers, squashed, etc) +func NewFromImage(img *image.Image, userImageStr string) (Source, error) { + if img == nil { + return Source{}, fmt.Errorf("no image given") + } + + return Source{ + Image: img, + Metadata: Metadata{ + Scheme: ImageScheme, + ImageMetadata: NewImageMetadata(img, userImageStr), + }, + }, nil +} + +func (s *Source) FileResolver(scope Scope) (FileResolver, error) { + switch s.Metadata.Scheme { + case DirectoryScheme, FileScheme: + s.mutex.Lock() + defer s.mutex.Unlock() + if s.directoryResolver == nil { + exclusionFunctions, err := getDirectoryExclusionFunctions(s.path, s.Exclusions) + if err != nil { + return nil, err + } + resolver, err := newDirectoryResolver(s.path, exclusionFunctions...) + if err != nil { + return nil, fmt.Errorf("unable to create directory resolver: %w", err) + } + s.directoryResolver = resolver + } + return s.directoryResolver, nil + case ImageScheme: + var resolver FileResolver + var err error + switch scope { + case SquashedScope: + resolver, err = newImageSquashResolver(s.Image) + case AllLayersScope: + resolver, err = newAllLayersResolver(s.Image) + default: + return nil, fmt.Errorf("bad image scope provided: %+v", scope) + } + if err != nil { + return nil, err + } + // image tree contains all paths, so we filter out the excluded entries afterwards + if len(s.Exclusions) > 0 { + resolver = NewExcludingResolver(resolver, getImageExclusionFunction(s.Exclusions)) + } + return resolver, nil + } + return nil, fmt.Errorf("unable to determine FilePathResolver with current scheme=%q", s.Metadata.Scheme) +} + +func unarchiveToTmp(path string, unarchiver archiver.Unarchiver) (string, func(), error) { + tempDir, err := os.MkdirTemp("", "syft-archive-contents-") + if err != nil { + return "", func() {}, fmt.Errorf("unable to create tempdir for archive processing: %w", err) + } + + cleanupFn := func() { + if err := os.RemoveAll(tempDir); err != nil { + log.Warnf("unable to cleanup archive tempdir: %+v", err) + } + } + + return tempDir, cleanupFn, unarchiver.Unarchive(path, tempDir) +} + +func getAnalysisPathInRpmSource(path string) (string, func(), error) { + var cleanupRpmSourceFn = func() {} + + rpmTempDir, err := ioutil.TempDir("", "syft-rpm-source-contents-") + if err != nil { + return "", func() {}, fmt.Errorf("unable to create tempdir for rpm source unpack processing: %w", err) + } + + cleanupRpmSourceFn = func() { + if err := os.RemoveAll(rpmTempDir); err != nil { + log.Warnf("unable to cleanup rpm source tempdir: %+v", err) + } + } + fs, err := os.Open(path) + if err != nil { + return "", cleanupRpmSourceFn, err + } + rpmSourceFile, err := rpmutils.ReadRpm(fs) + if err != nil { + return "", cleanupRpmSourceFn, err + } + //Extracting payload + if err := rpmSourceFile.ExpandPayload(rpmTempDir); err != nil { + return "", cleanupRpmSourceFn, err + } + + files, err := os.ReadDir(rpmTempDir) + if err != nil { + return "", cleanupRpmSourceFn, err + } + + tempDir, err := ioutil.TempDir("", "syft-archive-contents-") + if err != nil { + return "", func() {}, fmt.Errorf("unable to create tempdir for archive processing: %w", err) + } + cleanupFn := func() { + cleanupRpmSourceFn() + if err := os.RemoveAll(tempDir); err != nil { + log.Warnf("unable to cleanup archive tempdir: %+v", err) + } + } + //find archiver files in unarchived rpm source dir + //then unarchived them + for _, file := range files { + filename := file.Name() + filePath := filepath.Join(rpmTempDir, filename) + tmpArchiver, err := archiver.ByExtension(filename) + if unarchiver, ok := tmpArchiver.(archiver.Unarchiver); err == nil && ok { + err = unarchiver.Unarchive(filePath, tempDir) + if err != nil { + log.Warnf("file could not be unarchived: %+v", err) + } else { + log.Debugf("%s has been unarchived", filename) + } + } + + } + return tempDir, cleanupFn, nil +} +func getImageExclusionFunction(exclusions []string) func(string) bool { + if len(exclusions) == 0 { + return nil + } + // add subpath exclusions + for _, exclusion := range exclusions { + exclusions = append(exclusions, exclusion+"/**") + } + return func(path string) bool { + for _, exclusion := range exclusions { + matches, err := doublestar.Match(exclusion, path) + if err != nil { + return false + } + if matches { + return true + } + } + return false + } +} + +func getDirectoryExclusionFunctions(root string, exclusions []string) ([]pathFilterFn, error) { + if len(exclusions) == 0 { + return nil, nil + } + + // this is what directoryResolver.indexTree is doing to get the absolute path: + root, err := filepath.Abs(root) + if err != nil { + return nil, err + } + + if !strings.HasSuffix(root, "/") { + root += "/" + } + + var errors []string + for idx, exclusion := range exclusions { + // check exclusions for supported paths, these are all relative to the "scan root" + if strings.HasPrefix(exclusion, "./") || strings.HasPrefix(exclusion, "*/") || strings.HasPrefix(exclusion, "**/") { + exclusion = strings.TrimPrefix(exclusion, "./") + exclusions[idx] = root + exclusion + } else { + errors = append(errors, exclusion) + } + } + + if errors != nil { + return nil, fmt.Errorf("invalid exclusion pattern(s): '%s' (must start with one of: './', '*/', or '**/')", strings.Join(errors, "', '")) + } + + return []pathFilterFn{ + func(path string, _ os.FileInfo) bool { + for _, exclusion := range exclusions { + matches, err := doublestar.Match(exclusion, path) + if err != nil { + return false + } + if matches { + return true + } + } + return false + }, + }, nil +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/source_test.go b/ci/tools/openeuler-purl/syft-dev/syft/source/source_test.go new file mode 100644 index 0000000000000000000000000000000000000000..8945e36cd4328bc209b08310fd27a4ed92daabb5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/source_test.go @@ -0,0 +1,662 @@ +//go:build !windows +// +build !windows + +package source + +import ( + "io/ioutil" + "os" + "os/exec" + "path" + "path/filepath" + "strings" + "syscall" + "testing" + + "github.com/anchore/stereoscope/pkg/imagetest" + + "github.com/stretchr/testify/require" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/stereoscope/pkg/image" +) + +func TestParseInput(t *testing.T) { + tests := []struct { + name string + input string + platform string + expected Scheme + errFn require.ErrorAssertionFunc + }{ + { + name: "ParseInput parses a file input", + input: "test-fixtures/image-simple/file-1.txt", + expected: FileScheme, + }, + { + name: "errors out when using platform for non-image scheme", + input: "test-fixtures/image-simple/file-1.txt", + platform: "arm64", + errFn: require.Error, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + if test.errFn == nil { + test.errFn = require.NoError + } + sourceInput, err := ParseInput(test.input, test.platform, true) + test.errFn(t, err) + if test.expected != "" { + require.NotNil(t, sourceInput) + assert.Equal(t, sourceInput.Scheme, test.expected) + } + }) + } +} + +func TestNewFromImageFails(t *testing.T) { + t.Run("no image given", func(t *testing.T) { + _, err := NewFromImage(nil, "") + if err == nil { + t.Errorf("expected an error condition but none was given") + } + }) +} + +func TestNewFromImage(t *testing.T) { + layer := image.NewLayer(nil) + img := image.Image{ + Layers: []*image.Layer{layer}, + } + + t.Run("create a new source object from image", func(t *testing.T) { + _, err := NewFromImage(&img, "") + if err != nil { + t.Errorf("unexpected error when creating a new Locations from img: %+v", err) + } + }) +} + +func TestNewFromDirectory(t *testing.T) { + testCases := []struct { + desc string + input string + expString string + inputPaths []string + expectedRefs int + expectedErr bool + }{ + { + desc: "no paths exist", + input: "foobar/", + inputPaths: []string{"/opt/", "/other"}, + expectedErr: true, + }, + { + desc: "path detected", + input: "test-fixtures", + inputPaths: []string{"path-detected/.vimrc"}, + expectedRefs: 1, + }, + { + desc: "directory ignored", + input: "test-fixtures", + inputPaths: []string{"path-detected"}, + expectedRefs: 0, + }, + { + desc: "no files-by-path detected", + input: "test-fixtures", + inputPaths: []string{"no-path-detected"}, + expectedRefs: 0, + }, + } + for _, test := range testCases { + t.Run(test.desc, func(t *testing.T) { + src, err := NewFromDirectory(test.input) + require.NoError(t, err) + assert.Equal(t, test.input, src.Metadata.Path) + + resolver, err := src.FileResolver(SquashedScope) + if test.expectedErr { + if err == nil { + t.Fatal("expected an error when making the resolver but got none") + } + return + } else { + require.NoError(t, err) + } + + refs, err := resolver.FilesByPath(test.inputPaths...) + if err != nil { + t.Errorf("FilesByPath call produced an error: %+v", err) + } + if len(refs) != test.expectedRefs { + t.Errorf("unexpected number of refs returned: %d != %d", len(refs), test.expectedRefs) + + } + + }) + } +} + +func TestNewFromFile(t *testing.T) { + testCases := []struct { + desc string + input string + expString string + inputPaths []string + expRefs int + }{ + { + desc: "path detected", + input: "test-fixtures/path-detected", + inputPaths: []string{"/.vimrc"}, + expRefs: 1, + }, + } + for _, test := range testCases { + t.Run(test.desc, func(t *testing.T) { + src, cleanup := NewFromFile(test.input) + if cleanup != nil { + t.Cleanup(cleanup) + } + + assert.Equal(t, test.input, src.Metadata.Path) + assert.Equal(t, src.Metadata.Path, src.path) + + resolver, err := src.FileResolver(SquashedScope) + require.NoError(t, err) + + refs, err := resolver.FilesByPath(test.inputPaths...) + require.NoError(t, err) + assert.Len(t, refs, test.expRefs) + + }) + } +} + +func TestNewFromFile_WithArchive(t *testing.T) { + testCases := []struct { + desc string + input string + expString string + inputPaths []string + expRefs int + }{ + { + desc: "path detected", + input: "test-fixtures/path-detected", + inputPaths: []string{"/.vimrc"}, + expRefs: 1, + }, + } + for _, test := range testCases { + t.Run(test.desc, func(t *testing.T) { + archivePath := setupArchiveTest(t, test.input) + + src, cleanup := NewFromFile(archivePath) + if cleanup != nil { + t.Cleanup(cleanup) + } + + assert.Equal(t, archivePath, src.Metadata.Path) + assert.NotEqual(t, src.Metadata.Path, src.path) + + resolver, err := src.FileResolver(SquashedScope) + require.NoError(t, err) + + refs, err := resolver.FilesByPath(test.inputPaths...) + require.NoError(t, err) + assert.Len(t, refs, test.expRefs) + + }) + } +} + +func TestNewFromDirectoryShared(t *testing.T) { + testCases := []struct { + desc string + input string + expString string + notExist string + inputPaths []string + expRefs int + }{ + { + desc: "path detected", + input: "test-fixtures", + notExist: "foobar/", + inputPaths: []string{"path-detected/.vimrc"}, + expRefs: 1, + }, + { + desc: "directory ignored", + input: "test-fixtures", + notExist: "foobar/", + inputPaths: []string{"path-detected"}, + expRefs: 0, + }, + { + desc: "no files-by-path detected", + input: "test-fixtures", + notExist: "foobar/", + inputPaths: []string{"no-path-detected"}, + expRefs: 0, + }, + } + for _, test := range testCases { + t.Run(test.desc, func(t *testing.T) { + src, err := NewFromDirectory(test.input) + + if err != nil { + t.Errorf("could not create NewDirScope: %+v", err) + } + if src.Metadata.Path != test.input { + t.Errorf("mismatched stringer: '%s' != '%s'", src.Metadata.Path, test.input) + } + + _, err = src.FileResolver(SquashedScope) + assert.NoError(t, err) + + src.Metadata.Path = test.notExist + resolver2, err := src.FileResolver(SquashedScope) + assert.NoError(t, err) + + refs, err := resolver2.FilesByPath(test.inputPaths...) + if err != nil { + t.Errorf("FilesByPath call produced an error: %+v", err) + } + if len(refs) != test.expRefs { + t.Errorf("unexpected number of refs returned: %d != %d", len(refs), test.expRefs) + + } + + }) + } +} + +func TestFilesByPathDoesNotExist(t *testing.T) { + testCases := []struct { + desc string + input string + path string + expected string + }{ + { + input: "test-fixtures/path-detected", + desc: "path does not exist", + path: "foo", + }, + } + for _, test := range testCases { + t.Run(test.desc, func(t *testing.T) { + src, err := NewFromDirectory(test.input) + if err != nil { + t.Errorf("could not create NewDirScope: %+v", err) + } + resolver, err := src.FileResolver(SquashedScope) + if err != nil { + t.Errorf("could not get resolver error: %+v", err) + } + refs, err := resolver.FilesByPath(test.path) + if err != nil { + t.Errorf("could not get file references from path: %s, %v", test.path, err) + } + + if len(refs) != 0 { + t.Errorf("didnt' expect a ref, but got: %d", len(refs)) + } + + }) + } +} + +func TestFilesByGlob(t *testing.T) { + testCases := []struct { + desc string + input string + glob string + expected int + }{ + { + input: "test-fixtures", + desc: "no matches", + glob: "bar/foo", + expected: 0, + }, + { + input: "test-fixtures/path-detected", + desc: "a single match", + glob: "**/*vimrc", + expected: 1, + }, + { + input: "test-fixtures/path-detected", + desc: "multiple matches", + glob: "**", + expected: 2, + }, + } + for _, test := range testCases { + t.Run(test.desc, func(t *testing.T) { + src, err := NewFromDirectory(test.input) + if err != nil { + t.Errorf("could not create NewDirScope: %+v", err) + } + resolver, err := src.FileResolver(SquashedScope) + if err != nil { + t.Errorf("could not get resolver error: %+v", err) + } + contents, err := resolver.FilesByGlob(test.glob) + if err != nil { + t.Errorf("could not get files by glob: %s+v", err) + } + if len(contents) != test.expected { + t.Errorf("unexpected number of files found by glob (%s): %d != %d", test.glob, len(contents), test.expected) + } + + }) + } +} + +func TestDirectoryExclusions(t *testing.T) { + testCases := []struct { + desc string + input string + glob string + expected int + exclusions []string + err bool + }{ + { + input: "test-fixtures/system_paths", + desc: "exclude everything", + glob: "**", + expected: 0, + exclusions: []string{"**/*"}, + }, + { + input: "test-fixtures/image-simple", + desc: "a single path excluded", + glob: "**", + expected: 3, + exclusions: []string{"**/target/**"}, + }, + { + input: "test-fixtures/image-simple", + desc: "exclude explicit directory relative to the root", + glob: "**", + expected: 3, + exclusions: []string{"./target"}, + }, + { + input: "test-fixtures/image-simple", + desc: "exclude explicit file relative to the root", + glob: "**", + expected: 3, + exclusions: []string{"./file-1.txt"}, + }, + { + input: "test-fixtures/image-simple", + desc: "exclude wildcard relative to the root", + glob: "**", + expected: 2, + exclusions: []string{"./*.txt"}, + }, + { + input: "test-fixtures/image-simple", + desc: "exclude files deeper", + glob: "**", + expected: 3, + exclusions: []string{"**/really/**"}, + }, + { + input: "test-fixtures/image-simple", + desc: "files excluded with extension", + glob: "**", + expected: 1, + exclusions: []string{"**/*.txt"}, + }, + { + input: "test-fixtures/image-simple", + desc: "keep files with different extensions", + glob: "**", + expected: 4, + exclusions: []string{"**/target/**/*.jar"}, + }, + { + input: "test-fixtures/path-detected", + desc: "file directly excluded", + glob: "**", + expected: 1, + exclusions: []string{"**/empty"}, + }, + { + input: "test-fixtures/path-detected", + desc: "pattern error containing **/", + glob: "**", + expected: 1, + exclusions: []string{"/**/empty"}, + err: true, + }, + { + input: "test-fixtures/path-detected", + desc: "pattern error incorrect start", + glob: "**", + expected: 1, + exclusions: []string{"empty"}, + err: true, + }, + { + input: "test-fixtures/path-detected", + desc: "pattern error starting with /", + glob: "**", + expected: 1, + exclusions: []string{"/empty"}, + err: true, + }, + } + registryOpts := &image.RegistryOptions{} + for _, test := range testCases { + t.Run(test.desc, func(t *testing.T) { + sourceInput, err := ParseInput("dir:"+test.input, "", false) + require.NoError(t, err) + src, fn, err := New(*sourceInput, registryOpts, test.exclusions) + defer fn() + + if test.err { + _, err = src.FileResolver(SquashedScope) + if err == nil { + t.Errorf("expected an error for patterns: %s", strings.Join(test.exclusions, " or ")) + } + return + } + + if err != nil { + t.Errorf("could not create NewDirScope: %+v", err) + } + resolver, err := src.FileResolver(SquashedScope) + if err != nil { + t.Errorf("could not get resolver error: %+v", err) + } + contents, err := resolver.FilesByGlob(test.glob) + if err != nil { + t.Errorf("could not get files by glob: %s+v", err) + } + if len(contents) != test.expected { + t.Errorf("wrong number of files after exclusions (%s): %d != %d", test.glob, len(contents), test.expected) + } + }) + } +} + +func TestImageExclusions(t *testing.T) { + testCases := []struct { + desc string + input string + glob string + expected int + exclusions []string + }{ + // NOTE: in the Dockerfile, /target is moved to /, which makes /really a top-level dir + { + input: "image-simple", + desc: "a single path excluded", + glob: "**", + expected: 2, + exclusions: []string{"/really/**"}, + }, + { + input: "image-simple", + desc: "a directly referenced directory is excluded", + glob: "**", + expected: 2, + exclusions: []string{"/really"}, + }, + { + input: "image-simple", + desc: "a partial directory is not excluded", + glob: "**", + expected: 3, + exclusions: []string{"/reall"}, + }, + { + input: "image-simple", + desc: "exclude files deeper", + glob: "**", + expected: 2, + exclusions: []string{"**/nested/**"}, + }, + { + input: "image-simple", + desc: "files excluded with extension", + glob: "**", + expected: 2, + exclusions: []string{"**/*1.txt"}, + }, + { + input: "image-simple", + desc: "keep files with different extensions", + glob: "**", + expected: 3, + exclusions: []string{"**/target/**/*.jar"}, + }, + { + input: "image-simple", + desc: "file directly excluded", + glob: "**", + expected: 2, + exclusions: []string{"**/somefile-1.txt"}, // file-1 renamed to somefile-1 in Dockerfile + }, + } + registryOpts := &image.RegistryOptions{} + for _, test := range testCases { + t.Run(test.desc, func(t *testing.T) { + archiveLocation := imagetest.PrepareFixtureImage(t, "docker-archive", test.input) + sourceInput, err := ParseInput(archiveLocation, "", false) + require.NoError(t, err) + src, fn, err := New(*sourceInput, registryOpts, test.exclusions) + defer fn() + + if err != nil { + t.Errorf("could not create NewDirScope: %+v", err) + } + resolver, err := src.FileResolver(SquashedScope) + if err != nil { + t.Errorf("could not get resolver error: %+v", err) + } + contents, err := resolver.FilesByGlob(test.glob) + if err != nil { + t.Errorf("could not get files by glob: %s+v", err) + } + if len(contents) != test.expected { + t.Errorf("wrong number of files after exclusions (%s): %d != %d", test.glob, len(contents), test.expected) + } + }) + } +} + +// createArchive creates a new archive file at destinationArchivePath based on the directory found at sourceDirPath. +func createArchive(t testing.TB, sourceDirPath, destinationArchivePath string) { + t.Helper() + + cwd, err := os.Getwd() + if err != nil { + t.Fatalf("unable to get cwd: %+v", err) + } + + cmd := exec.Command("./generate-tar-fixture-from-source-dir.sh", destinationArchivePath, path.Base(sourceDirPath)) + cmd.Dir = filepath.Join(cwd, "test-fixtures") + + if err := cmd.Start(); err != nil { + t.Fatalf("unable to start generate zip fixture script: %+v", err) + } + + if err := cmd.Wait(); err != nil { + if exiterr, ok := err.(*exec.ExitError); ok { + // The program has exited with an exit code != 0 + + // This works on both Unix and Windows. Although package + // syscall is generally platform dependent, WaitStatus is + // defined for both Unix and Windows and in both cases has + // an ExitStatus() method with the same signature. + if status, ok := exiterr.Sys().(syscall.WaitStatus); ok { + if status.ExitStatus() != 0 { + t.Fatalf("failed to generate fixture: rc=%d", status.ExitStatus()) + } + } + } else { + t.Fatalf("unable to get generate fixture script result: %+v", err) + } + } + +} + +// setupArchiveTest encapsulates common test setup work for tar file tests. It returns a cleanup function, +// which should be called (typically deferred) by the caller, the path of the created tar archive, and an error, +// which should trigger a fatal test failure in the consuming test. The returned cleanup function will never be nil +// (even if there's an error), and it should always be called. +func setupArchiveTest(t testing.TB, sourceDirPath string) string { + t.Helper() + + archivePrefix, err := ioutil.TempFile("", "syft-archive-TEST-") + require.NoError(t, err) + + t.Cleanup( + assertNoError(t, + func() error { + return os.Remove(archivePrefix.Name()) + }, + ), + ) + + destinationArchiveFilePath := archivePrefix.Name() + ".tar" + t.Logf("archive path: %s", destinationArchiveFilePath) + createArchive(t, sourceDirPath, destinationArchiveFilePath) + + t.Cleanup( + assertNoError(t, + func() error { + return os.Remove(destinationArchiveFilePath) + }, + ), + ) + + cwd, err := os.Getwd() + require.NoError(t, err) + + t.Logf("running from: %s", cwd) + + return destinationArchiveFilePath +} + +func assertNoError(t testing.TB, fn func() error) func() { + return func() { + assert.NoError(t, fn()) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/generate-tar-fixture-from-source-dir.sh b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/generate-tar-fixture-from-source-dir.sh new file mode 100755 index 0000000000000000000000000000000000000000..922941d36fbc3e9183ab706da4922d20fb37ef40 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/generate-tar-fixture-from-source-dir.sh @@ -0,0 +1,9 @@ +#!/usr/bin/env bash +set -eux + +# $1 —— absolute path to destination file, should end with .tar +# $2 —— absolute path to directory from which to add entries to the archive + +pushd "$2" + tar -cvf "$1" . +popd diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/Dockerfile b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..be7f1eacfc1b60d8a628265e7d3fda4e28c15bb9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/Dockerfile @@ -0,0 +1,4 @@ +# Note: changes to this file will result in updating several test values. Consider making a new image fixture instead of editing this one. +FROM scratch +ADD file-1.txt /somefile-1.txt +ADD file-2.txt /somefile-1.txt diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/file-1.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..985d3408e98cb9f41c01376c698451fdef0e4b32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/file-1.txt @@ -0,0 +1 @@ +this file has contents \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/file-2.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..396d08bbc72f810ec6d057d1713a84a75d1cd542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-duplicate-path/file-2.txt @@ -0,0 +1 @@ +file-2 contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/Dockerfile b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..62fb151e497330ffd3bd63f1780579e9b3f9a4dd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/Dockerfile @@ -0,0 +1,6 @@ +# Note: changes to this file will result in updating several test values. Consider making a new image fixture instead of editing this one. +FROM scratch +ADD file-1.txt /somefile-1.txt +ADD file-2.txt /somefile-2.txt +# note: adding a directory will behave differently on docker engine v18 vs v19 +ADD target / diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/file-1.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..985d3408e98cb9f41c01376c698451fdef0e4b32 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/file-1.txt @@ -0,0 +1 @@ +this file has contents \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/file-2.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..396d08bbc72f810ec6d057d1713a84a75d1cd542 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-simple/file-2.txt @@ -0,0 +1 @@ +file-2 contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/Dockerfile b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..edeabac9c1dd7e7496bd78a04a91356021058532 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/Dockerfile @@ -0,0 +1,34 @@ +# LAYER 0: +FROM busybox:latest + +# LAYER 1: +ADD file-1.txt . + +# LAYER 2: link with previous data +RUN ln -s ./file-1.txt link-1 + +# LAYER 3: link with future data +RUN ln -s ./file-2.txt link-2 +# LAYER 4: +ADD file-2.txt . + +# LAYER 5: link with current data +RUN echo "file 3" > file-3.txt && ln -s ./file-3.txt link-within + +# LAYER 6: multiple links (link-indirect > link-2 > file-2.txt) +RUN ln -s ./link-2 link-indirect + +# LAYER 7: override contents / resolution +ADD new-file-2.txt file-2.txt + +# LAYER 8: dead link +RUN ln -s ./i-dont-exist.txt link-dead + +# LAYER 9: add the parent dir +ADD parent /parent + +# LAYER 10: parent is a symlink +RUN ln -s /parent parent-link + +# LAYER 11: parent is a symlink and the child target is overridden +COPY new-file-4.txt /parent-link/file-4.txt \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/file-1.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/file-1.txt new file mode 100644 index 0000000000000000000000000000000000000000..d86db8155c35d08c4bcbdc95ed008e60fa8c489c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/file-1.txt @@ -0,0 +1 @@ +file 1! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/file-2.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..ad5f8c9a1e2e9e69fb9195ea21a7e3597e0eb9b6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/file-2.txt @@ -0,0 +1 @@ +file 2! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/nested/nested/file-3.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/nested/nested/file-3.txt new file mode 100644 index 0000000000000000000000000000000000000000..dc43ed8669d01ce53843e2fc282718ebe5d81232 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/nested/nested/file-3.txt @@ -0,0 +1 @@ +file 3 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/new-file-2.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/new-file-2.txt new file mode 100644 index 0000000000000000000000000000000000000000..3c00c215a8b10952e486567e97a2ed7d56c5a2b5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/new-file-2.txt @@ -0,0 +1 @@ +NEW file override! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/new-file-4.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/new-file-4.txt new file mode 100644 index 0000000000000000000000000000000000000000..6e6239258b8babe1044adebc32f47283fda196cd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/new-file-4.txt @@ -0,0 +1 @@ +override file 4! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/parent/file-4.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/parent/file-4.txt new file mode 100644 index 0000000000000000000000000000000000000000..75cda158838b01d1265abb7d533018306b6a9492 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/image-symlinks/parent/file-4.txt @@ -0,0 +1 @@ +the 4th file! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/path-detected/.vimrc b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/path-detected/.vimrc new file mode 100644 index 0000000000000000000000000000000000000000..93b07e21b93c731b338255332f3c6c0d4a7918af --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/path-detected/.vimrc @@ -0,0 +1 @@ +" A .vimrc file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/path-detected/empty b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/path-detected/empty new file mode 100644 index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/nested/link-root b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/nested/link-root new file mode 120000 index 0000000000000000000000000000000000000000..24659224aae89aa00d59a19886dc31bd1d138627 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/nested/link-root @@ -0,0 +1 @@ +../real-root \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/file1.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/file1.txt new file mode 100644 index 0000000000000000000000000000000000000000..5452844a2006748e4ccd60e6e8d66645eca691ed --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/file1.txt @@ -0,0 +1 @@ +contents! diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/nested/file2.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/nested/file2.txt new file mode 100644 index 0000000000000000000000000000000000000000..5f7e2f21348693e894f060e1990fe8b0903b2e84 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/nested/file2.txt @@ -0,0 +1 @@ +more contents! diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/nested/linked-file1.txt b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/nested/linked-file1.txt new file mode 120000 index 0000000000000000000000000000000000000000..4e7feb2d8cbafe940498ec9f6a4b46318167eb24 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinked-root/real-root/nested/linked-file1.txt @@ -0,0 +1 @@ +../file1.txt \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/README.md b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/README.md new file mode 100644 index 0000000000000000000000000000000000000000..71967bddd9604773af0336c21d06bc85582cb74a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/README.md @@ -0,0 +1 @@ +this mimics a partial layout on a linux system within /sys/devices/virtual to help with ensuring globbing for files does not end up in a infinite loop diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/block/loop0 b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/block/loop0 new file mode 120000 index 0000000000000000000000000000000000000000..3e5e8ddf7cf353e9a295a6601d5cfa87f5533043 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/block/loop0 @@ -0,0 +1 @@ +../devices/loop0 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/devices/loop0/file.target b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/devices/loop0/file.target new file mode 100644 index 0000000000000000000000000000000000000000..cb3e220336bd2ec7fcecd22de9433f4346e60ed1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/devices/loop0/file.target @@ -0,0 +1 @@ +contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/devices/loop0/subsystem b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/devices/loop0/subsystem new file mode 120000 index 0000000000000000000000000000000000000000..f33eb2721fd7717c39a2fd02120314e97e575a8e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-loop/devices/loop0/subsystem @@ -0,0 +1 @@ +../../block \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/outside/link_to_readme b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/outside/link_to_readme new file mode 120000 index 0000000000000000000000000000000000000000..0dae899c0a1ef91d3a82083b020a6dd337a142db --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/outside/link_to_readme @@ -0,0 +1 @@ +../root/readme \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/root/link_to_link_to_readme b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/root/link_to_link_to_readme new file mode 120000 index 0000000000000000000000000000000000000000..6c91014fdc9f5aff8950816b1ee36f3772f15f99 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/root/link_to_link_to_readme @@ -0,0 +1 @@ +../outside/link_to_readme \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/root/readme b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/root/readme new file mode 100644 index 0000000000000000000000000000000000000000..cb3e220336bd2ec7fcecd22de9433f4346e60ed1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-multiple-roots/root/readme @@ -0,0 +1 @@ +contents! \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/link_to_link_to_new_readme b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/link_to_link_to_new_readme new file mode 120000 index 0000000000000000000000000000000000000000..1ab249f74259dc7f604da30531bc8c88c616511d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/link_to_link_to_new_readme @@ -0,0 +1 @@ +./link_to_new_readme \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/link_to_new_readme b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/link_to_new_readme new file mode 120000 index 0000000000000000000000000000000000000000..c944df565d2a2a3b4749ccb3ba3e6c863ca91dfd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/link_to_new_readme @@ -0,0 +1 @@ +./readme \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/readme b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/readme new file mode 100644 index 0000000000000000000000000000000000000000..df85b76ad840711e88a5506d28ec95394016694c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/symlinks-simple/readme @@ -0,0 +1,2 @@ +this directory exists for unit tests on irregular files. You can't see other files here because they are removed after each test. +This readme is a better version of Russell's teapot. diff --git a/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/system_paths/outside_root/link_target/place b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/system_paths/outside_root/link_target/place new file mode 100644 index 0000000000000000000000000000000000000000..476e93d5714117cb50143dbe653f4b2b5a1d4b18 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/source/test-fixtures/system_paths/outside_root/link_target/place @@ -0,0 +1 @@ +good \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/syft/test-fixtures/alpine-syft.json b/ci/tools/openeuler-purl/syft-dev/syft/test-fixtures/alpine-syft.json new file mode 100644 index 0000000000000000000000000000000000000000..936f6d5150edb99b837e9c0a17243dc157cbb229 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/syft/test-fixtures/alpine-syft.json @@ -0,0 +1,1846 @@ +{ + "artifacts": [ + { + "id": "880965c7-95ff-483c-80bb-22799bbbee63", + "name": "alpine-baselayout", + "version": "3.2.0-r16", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "GPL-2.0-only" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:alpine-baselayout:alpine-baselayout:3.2.0-r16:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine-baselayout:alpine_baselayout:3.2.0-r16:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine_baselayout:alpine-baselayout:3.2.0-r16:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine_baselayout:alpine_baselayout:3.2.0-r16:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine:alpine-baselayout:3.2.0-r16:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine:alpine_baselayout:3.2.0-r16:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/alpine-baselayout@3.2.0-r16?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "alpine-baselayout", + "originPackage": "alpine-baselayout", + "maintainer": "Natanael Copa ", + "version": "3.2.0-r16", + "license": "GPL-2.0-only", + "architecture": "x86_64", + "url": "https://git.alpinelinux.org/cgit/aports/tree/main/alpine-baselayout", + "description": "Alpine base dir structure and init scripts", + "size": 20716, + "installedSize": 413696, + "pullDependencies": "/bin/sh so:libc.musl-x86_64.so.1", + "pullChecksum": "Q1UJtB9cNV4r+/VbxySkEei++qbho=", + "gitCommitOfApkPort": "8a8c96a0ea2fcd824c361aa4438763fa33ee8ca0", + "files": [ + { + "path": "/dev" + }, + { + "path": "/dev/pts" + }, + { + "path": "/dev/shm" + }, + { + "path": "/etc" + }, + { + "path": "/etc/fstab", + "digest": { + "algorithm": "sha1", + "value": "Q11Q7hNe8QpDS531guqCdrXBzoA/o=" + } + }, + { + "path": "/etc/group", + "digest": { + "algorithm": "sha1", + "value": "Q13K+olJg5ayzHSVNUkggZJXuB+9Y=" + } + }, + { + "path": "/etc/hostname", + "digest": { + "algorithm": "sha1", + "value": "Q16nVwYVXP/tChvUPdukVD2ifXOmc=" + } + }, + { + "path": "/etc/hosts", + "digest": { + "algorithm": "sha1", + "value": "Q1BD6zJKZTRWyqGnPi4tSfd3krsMU=" + } + }, + { + "path": "/etc/inittab", + "digest": { + "algorithm": "sha1", + "value": "Q1TsthbhW7QzWRe1E/NKwTOuD4pHc=" + } + }, + { + "path": "/etc/modules", + "digest": { + "algorithm": "sha1", + "value": "Q1toogjUipHGcMgECgPJX64SwUT1M=" + } + }, + { + "path": "/etc/motd", + "digest": { + "algorithm": "sha1", + "value": "Q1XmduVVNURHQ27TvYp1Lr5TMtFcA=" + } + }, + { + "path": "/etc/mtab", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1kiljhXXH1LlQroHsEJIkPZg2eiw=" + } + }, + { + "path": "/etc/passwd", + "digest": { + "algorithm": "sha1", + "value": "Q1TchuuLUfur0izvfZQZxgN/LJhB8=" + } + }, + { + "path": "/etc/profile", + "digest": { + "algorithm": "sha1", + "value": "Q1VmHPWPjjvz4oCsbmYCUB4uWpSkc=" + } + }, + { + "path": "/etc/protocols", + "digest": { + "algorithm": "sha1", + "value": "Q1omKlp3vgGq2ZqYzyD/KHNdo8rDc=" + } + }, + { + "path": "/etc/services", + "digest": { + "algorithm": "sha1", + "value": "Q19WLCv5ItKg4MH7RWfNRh1I7byQc=" + } + }, + { + "path": "/etc/shadow", + "ownerUid": "0", + "ownerGid": "42", + "permissions": "640", + "digest": { + "algorithm": "sha1", + "value": "Q1ltrPIAW2zHeDiajsex2Bdmq3uqA=" + } + }, + { + "path": "/etc/shells", + "digest": { + "algorithm": "sha1", + "value": "Q1ojm2YdpCJ6B/apGDaZ/Sdb2xJkA=" + } + }, + { + "path": "/etc/sysctl.conf", + "digest": { + "algorithm": "sha1", + "value": "Q14upz3tfnNxZkIEsUhWn7Xoiw96g=" + } + }, + { + "path": "/etc/apk" + }, + { + "path": "/etc/conf.d" + }, + { + "path": "/etc/crontabs" + }, + { + "path": "/etc/crontabs/root", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "600", + "digest": { + "algorithm": "sha1", + "value": "Q1vfk1apUWI4yLJGhhNRd0kJixfvY=" + } + }, + { + "path": "/etc/init.d" + }, + { + "path": "/etc/modprobe.d" + }, + { + "path": "/etc/modprobe.d/aliases.conf", + "digest": { + "algorithm": "sha1", + "value": "Q1WUbh6TBYNVK7e4Y+uUvLs/7viqk=" + } + }, + { + "path": "/etc/modprobe.d/blacklist.conf", + "digest": { + "algorithm": "sha1", + "value": "Q1xxYGU6S6TLQvb7ervPrWWwAWqMg=" + } + }, + { + "path": "/etc/modprobe.d/i386.conf", + "digest": { + "algorithm": "sha1", + "value": "Q1pnay/njn6ol9cCssL7KiZZ8etlc=" + } + }, + { + "path": "/etc/modprobe.d/kms.conf", + "digest": { + "algorithm": "sha1", + "value": "Q1ynbLn3GYDpvajba/ldp1niayeog=" + } + }, + { + "path": "/etc/modules-load.d" + }, + { + "path": "/etc/network" + }, + { + "path": "/etc/network/if-down.d" + }, + { + "path": "/etc/network/if-post-down.d" + }, + { + "path": "/etc/network/if-pre-up.d" + }, + { + "path": "/etc/network/if-up.d" + }, + { + "path": "/etc/opt" + }, + { + "path": "/etc/periodic" + }, + { + "path": "/etc/periodic/15min" + }, + { + "path": "/etc/periodic/daily" + }, + { + "path": "/etc/periodic/hourly" + }, + { + "path": "/etc/periodic/monthly" + }, + { + "path": "/etc/periodic/weekly" + }, + { + "path": "/etc/profile.d" + }, + { + "path": "/etc/profile.d/README", + "digest": { + "algorithm": "sha1", + "value": "Q135OWsCzzvnB2fmFx62kbqm1Ax1k=" + } + }, + { + "path": "/etc/profile.d/color_prompt.sh.disabled", + "digest": { + "algorithm": "sha1", + "value": "Q10wL23GuSCVfumMRgakabUI6EsSk=" + } + }, + { + "path": "/etc/profile.d/locale.sh", + "digest": { + "algorithm": "sha1", + "value": "Q1S8j+WW71mWxfVy8ythqU7HUVoBw=" + } + }, + { + "path": "/etc/sysctl.d" + }, + { + "path": "/home" + }, + { + "path": "/lib" + }, + { + "path": "/lib/firmware" + }, + { + "path": "/lib/mdev" + }, + { + "path": "/lib/modules-load.d" + }, + { + "path": "/lib/sysctl.d" + }, + { + "path": "/lib/sysctl.d/00-alpine.conf", + "digest": { + "algorithm": "sha1", + "value": "Q1HpElzW1xEgmKfERtTy7oommnq6c=" + } + }, + { + "path": "/media" + }, + { + "path": "/media/cdrom" + }, + { + "path": "/media/floppy" + }, + { + "path": "/media/usb" + }, + { + "path": "/mnt" + }, + { + "path": "/opt" + }, + { + "path": "/proc" + }, + { + "path": "/root", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "700" + }, + { + "path": "/run" + }, + { + "path": "/sbin" + }, + { + "path": "/sbin/mkmntdirs", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1VcFI6coRl6HWWVShMW+G5Sb3JH8=" + } + }, + { + "path": "/srv" + }, + { + "path": "/sys" + }, + { + "path": "/tmp", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "1777" + }, + { + "path": "/usr" + }, + { + "path": "/usr/lib" + }, + { + "path": "/usr/lib/modules-load.d" + }, + { + "path": "/usr/local" + }, + { + "path": "/usr/local/bin" + }, + { + "path": "/usr/local/lib" + }, + { + "path": "/usr/local/share" + }, + { + "path": "/usr/sbin" + }, + { + "path": "/usr/share" + }, + { + "path": "/usr/share/man" + }, + { + "path": "/usr/share/misc" + }, + { + "path": "/var" + }, + { + "path": "/var/run", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q11/SNZz/8cK2dSKK+cJpVrZIuF4Q=" + } + }, + { + "path": "/var/cache" + }, + { + "path": "/var/cache/misc" + }, + { + "path": "/var/empty", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "555" + }, + { + "path": "/var/lib" + }, + { + "path": "/var/lib/misc" + }, + { + "path": "/var/local" + }, + { + "path": "/var/lock" + }, + { + "path": "/var/lock/subsys" + }, + { + "path": "/var/log" + }, + { + "path": "/var/mail" + }, + { + "path": "/var/opt" + }, + { + "path": "/var/spool" + }, + { + "path": "/var/spool/mail", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1dzbdazYZA2nTzSIG3YyNw7d4Juc=" + } + }, + { + "path": "/var/spool/cron" + }, + { + "path": "/var/spool/cron/crontabs", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1OFZt+ZMp7j0Gny0rqSKuWJyqYmA=" + } + }, + { + "path": "/var/tmp", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "1777" + } + ] + } + }, + { + "id": "8dbd8f4d-c13f-4120-8c2b-4596e5c46fce", + "name": "alpine-keys", + "version": "2.3-r1", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "MIT" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:alpine-keys:alpine-keys:2.3-r1:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine-keys:alpine_keys:2.3-r1:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine_keys:alpine-keys:2.3-r1:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine_keys:alpine_keys:2.3-r1:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine:alpine-keys:2.3-r1:*:*:*:*:*:*:*", + "cpe:2.3:a:alpine:alpine_keys:2.3-r1:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/alpine-keys@2.3-r1?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "alpine-keys", + "originPackage": "alpine-keys", + "maintainer": "Natanael Copa ", + "version": "2.3-r1", + "license": "MIT", + "architecture": "x86_64", + "url": "https://alpinelinux.org", + "description": "Public keys for Alpine Linux packages", + "size": 5988, + "installedSize": 118784, + "pullDependencies": "", + "pullChecksum": "Q1ZV5wTtRXerQz0CBrwtKcvErpPeY=", + "gitCommitOfApkPort": "0972396a79fd723a429e518120fdf7ab48407468", + "files": [ + { + "path": "/etc" + }, + { + "path": "/etc/apk" + }, + { + "path": "/etc/apk/keys" + }, + { + "path": "/etc/apk/keys/alpine-devel@lists.alpinelinux.org-4a6a0840.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1OvCFSO94z97c80mIDCxqGkh2Og4=" + } + }, + { + "path": "/etc/apk/keys/alpine-devel@lists.alpinelinux.org-5243ef4b.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1v7YWZYzAWoclaLDI45jEguI7YN0=" + } + }, + { + "path": "/etc/apk/keys/alpine-devel@lists.alpinelinux.org-5261cecb.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1NnGuDsdQOx4ZNYfB3N97eLyGPkI=" + } + }, + { + "path": "/usr" + }, + { + "path": "/usr/share" + }, + { + "path": "/usr/share/apk" + }, + { + "path": "/usr/share/apk/keys" + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-4a6a0840.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1OvCFSO94z97c80mIDCxqGkh2Og4=" + } + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-5243ef4b.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1v7YWZYzAWoclaLDI45jEguI7YN0=" + } + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-524d27bb.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1BTqS+H/UUyhQuzHwiBl47+BTKuU=" + } + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-5261cecb.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1NnGuDsdQOx4ZNYfB3N97eLyGPkI=" + } + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-58199dcc.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1Oaxdcsa6AYoPdLi0U4lO3J2we18=" + } + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-58cbb476.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1yPq+su65ksNox3uXB+DR7P18+QU=" + } + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-58e4f17d.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1MpZDNX0LeLHvSOwVUyXiXx11NN0=" + } + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-5e69ca50.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1glCQ/eJbvA5xqcswdjFrWv5Fnk0=" + } + }, + { + "path": "/usr/share/apk/keys/alpine-devel@lists.alpinelinux.org-60ac2099.rsa.pub", + "digest": { + "algorithm": "sha1", + "value": "Q1XUdDEoNTtjlvrS+iunk6ziFgIpU=" + } + }, + { + "path": "/usr/share/apk/keys/aarch64" + }, + { + "path": "/usr/share/apk/keys/aarch64/alpine-devel@lists.alpinelinux.org-58199dcc.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q17j9nWJkQ+wfIuVQzIFrmFZ7fSOc=" + } + }, + { + "path": "/usr/share/apk/keys/armhf" + }, + { + "path": "/usr/share/apk/keys/armhf/alpine-devel@lists.alpinelinux.org-524d27bb.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1U9QtsdN+rYZ9Zh76EfXy00JZHMg=" + } + }, + { + "path": "/usr/share/apk/keys/armv7" + }, + { + "path": "/usr/share/apk/keys/armv7/alpine-devel@lists.alpinelinux.org-524d27bb.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1U9QtsdN+rYZ9Zh76EfXy00JZHMg=" + } + }, + { + "path": "/usr/share/apk/keys/mips64" + }, + { + "path": "/usr/share/apk/keys/mips64/alpine-devel@lists.alpinelinux.org-5e69ca50.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1hCZdFx+LvzbLtPs753je78gEEBQ=" + } + }, + { + "path": "/usr/share/apk/keys/ppc64le" + }, + { + "path": "/usr/share/apk/keys/ppc64le/alpine-devel@lists.alpinelinux.org-58cbb476.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1t21dhCLbTJmAHXSCeOMq/2vfSgo=" + } + }, + { + "path": "/usr/share/apk/keys/riscv64" + }, + { + "path": "/usr/share/apk/keys/riscv64/alpine-devel@lists.alpinelinux.org-60ac2099.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1NVPbZavaXpsItFwQYDWbpor7yYE=" + } + }, + { + "path": "/usr/share/apk/keys/s390x" + }, + { + "path": "/usr/share/apk/keys/s390x/alpine-devel@lists.alpinelinux.org-58e4f17d.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1sjbV2r2w0Ih2vwdzC4Jq6UI7cMQ=" + } + }, + { + "path": "/usr/share/apk/keys/x86" + }, + { + "path": "/usr/share/apk/keys/x86/alpine-devel@lists.alpinelinux.org-4a6a0840.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1Ii51i7Nrc4uft14HhqugaUqdH64=" + } + }, + { + "path": "/usr/share/apk/keys/x86/alpine-devel@lists.alpinelinux.org-5243ef4b.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1Y49eVxhpvftbQ3yAdvlLfcrPLTU=" + } + }, + { + "path": "/usr/share/apk/keys/x86_64" + }, + { + "path": "/usr/share/apk/keys/x86_64/alpine-devel@lists.alpinelinux.org-4a6a0840.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1Ii51i7Nrc4uft14HhqugaUqdH64=" + } + }, + { + "path": "/usr/share/apk/keys/x86_64/alpine-devel@lists.alpinelinux.org-5261cecb.rsa.pub", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1AUFY+fwSBTcrYetjT7NHvafrSQc=" + } + } + ] + } + }, + { + "id": "b03a5cd0-e8e4-4a0c-b283-86b4942b4cfc", + "name": "apk-tools", + "version": "2.12.7-r0", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "GPL-2.0-only" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:apk-tools:apk-tools:2.12.7-r0:*:*:*:*:*:*:*", + "cpe:2.3:a:apk-tools:apk_tools:2.12.7-r0:*:*:*:*:*:*:*", + "cpe:2.3:a:apk_tools:apk-tools:2.12.7-r0:*:*:*:*:*:*:*", + "cpe:2.3:a:apk_tools:apk_tools:2.12.7-r0:*:*:*:*:*:*:*", + "cpe:2.3:a:apk:apk-tools:2.12.7-r0:*:*:*:*:*:*:*", + "cpe:2.3:a:apk:apk_tools:2.12.7-r0:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/apk-tools@2.12.7-r0?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "apk-tools", + "originPackage": "apk-tools", + "maintainer": "Natanael Copa ", + "version": "2.12.7-r0", + "license": "GPL-2.0-only", + "architecture": "x86_64", + "url": "https://gitlab.alpinelinux.org/alpine/apk-tools", + "description": "Alpine Package Keeper - package manager for alpine", + "size": 119979, + "installedSize": 311296, + "pullDependencies": "musl>=1.2 so:libc.musl-x86_64.so.1 so:libcrypto.so.1.1 so:libssl.so.1.1 so:libz.so.1", + "pullChecksum": "Q1VnSoy5XasRtvFODOZ9P0pZG4Hxs=", + "gitCommitOfApkPort": "03c6b1b0ec20f417cee0f3c1d56795b27871b1c5", + "files": [ + { + "path": "/etc" + }, + { + "path": "/etc/apk" + }, + { + "path": "/etc/apk/keys" + }, + { + "path": "/etc/apk/protected_paths.d" + }, + { + "path": "/lib" + }, + { + "path": "/lib/libapk.so.3.12.0", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1fg+B1BJHpxBSS5dRPU+3zeeuFI4=" + } + }, + { + "path": "/sbin" + }, + { + "path": "/sbin/apk", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1LugZocafK9LifJwfELs3VqdEIxw=" + } + }, + { + "path": "/var" + }, + { + "path": "/var/cache" + }, + { + "path": "/var/cache/misc" + }, + { + "path": "/var/lib" + }, + { + "path": "/var/lib/apk" + } + ] + } + }, + { + "id": "cb3f3296-98d8-4e88-bf0a-3bdc53f817fb", + "name": "busybox", + "version": "1.33.1-r3", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "GPL-2.0-only" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:busybox:busybox:1.33.1-r3:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/busybox@1.33.1-r3?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "busybox", + "originPackage": "busybox", + "maintainer": "Natanael Copa ", + "version": "1.33.1-r3", + "license": "GPL-2.0-only", + "architecture": "x86_64", + "url": "https://busybox.net/", + "description": "Size optimized toolbox of many common UNIX utilities", + "size": 499368, + "installedSize": 950272, + "pullDependencies": "so:libc.musl-x86_64.so.1", + "pullChecksum": "Q1rGvmeXEbASEg01DqEqMbxV0fts4=", + "gitCommitOfApkPort": "98710256acf90e670e79f32f1f0350b830979d24", + "files": [ + { + "path": "/bin" + }, + { + "path": "/bin/busybox", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q135CE+2ocG61L7La8CI3kfLURucU=" + } + }, + { + "path": "/bin/sh", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1pcfTfDNEbNKQc2s1tia7da05M8Q=" + } + }, + { + "path": "/etc" + }, + { + "path": "/etc/securetty", + "digest": { + "algorithm": "sha1", + "value": "Q1mB95Hq2NUTZ599RDiSsj9w5FrOU=" + } + }, + { + "path": "/etc/udhcpd.conf", + "digest": { + "algorithm": "sha1", + "value": "Q1UAiPZcDIW1ClRzobfggcCQ77V28=" + } + }, + { + "path": "/etc/logrotate.d" + }, + { + "path": "/etc/logrotate.d/acpid", + "digest": { + "algorithm": "sha1", + "value": "Q1TylyCINVmnS+A/Tead4vZhE7Bks=" + } + }, + { + "path": "/etc/network" + }, + { + "path": "/etc/network/if-down.d" + }, + { + "path": "/etc/network/if-post-down.d" + }, + { + "path": "/etc/network/if-post-up.d" + }, + { + "path": "/etc/network/if-pre-down.d" + }, + { + "path": "/etc/network/if-pre-up.d" + }, + { + "path": "/etc/network/if-up.d" + }, + { + "path": "/etc/network/if-up.d/dad", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "775", + "digest": { + "algorithm": "sha1", + "value": "Q1ORf+lPRKuYgdkBBcKoevR1t60Q4=" + } + }, + { + "path": "/sbin" + }, + { + "path": "/tmp", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "1777" + }, + { + "path": "/usr" + }, + { + "path": "/usr/sbin" + }, + { + "path": "/usr/share" + }, + { + "path": "/usr/share/udhcpc" + }, + { + "path": "/usr/share/udhcpc/default.script", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1t9vir/ZrX3nbSIYT9BDLWZenkVQ=" + } + }, + { + "path": "/var" + }, + { + "path": "/var/cache" + }, + { + "path": "/var/cache/misc" + }, + { + "path": "/var/lib" + }, + { + "path": "/var/lib/udhcpd" + } + ] + } + }, + { + "id": "bdac28cf-4448-43d1-bdb6-1b6e8df0a2d3", + "name": "ca-certificates-bundle", + "version": "20191127-r5", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "MPL-2.0", + "AND", + "MIT" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:ca-certificates-bundle:ca-certificates-bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca-certificates-bundle:ca_certificates_bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca_certificates_bundle:ca-certificates-bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca_certificates_bundle:ca_certificates_bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca-certificates:ca-certificates-bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca-certificates:ca_certificates_bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca_certificates:ca-certificates-bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca_certificates:ca_certificates_bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca:ca-certificates-bundle:20191127-r5:*:*:*:*:*:*:*", + "cpe:2.3:a:ca:ca_certificates_bundle:20191127-r5:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/ca-certificates-bundle@20191127-r5?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "ca-certificates-bundle", + "originPackage": "ca-certificates", + "maintainer": "Natanael Copa ", + "version": "20191127-r5", + "license": "MPL-2.0 AND MIT", + "architecture": "x86_64", + "url": "https://www.mozilla.org/en-US/about/governance/policies/security-group/certs/", + "description": "Pre generated bundle of Mozilla certificates", + "size": 124473, + "installedSize": 233472, + "pullDependencies": "", + "pullChecksum": "Q1bQ4InxwFIUUNl11tjOwqrqAeAIA=", + "gitCommitOfApkPort": "51999ab9304ec11c68c4ea9e99350ac7570e7f21", + "files": [ + { + "path": "/etc" + }, + { + "path": "/etc/ssl" + }, + { + "path": "/etc/ssl/cert.pem", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1Nj6gTBdkZpTFW/obJGdpfvK0StA=" + } + }, + { + "path": "/etc/ssl/certs" + }, + { + "path": "/etc/ssl/certs/ca-certificates.crt", + "digest": { + "algorithm": "sha1", + "value": "Q1yxhc/Gjt/YEWliIZBXQz/RBrszU=" + } + } + ] + } + }, + { + "id": "ef75a96d-f7be-45fa-abf0-a66c2779cfee", + "name": "libc-utils", + "version": "0.7.2-r3", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "BSD-2-Clause", + "AND", + "BSD-3-Clause" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:libc-utils:libc-utils:0.7.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:libc-utils:libc_utils:0.7.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:libc_utils:libc-utils:0.7.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:libc_utils:libc_utils:0.7.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:libc:libc-utils:0.7.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:libc:libc_utils:0.7.2-r3:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/libc-utils@0.7.2-r3?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "libc-utils", + "originPackage": "libc-dev", + "maintainer": "Natanael Copa ", + "version": "0.7.2-r3", + "license": "BSD-2-Clause AND BSD-3-Clause", + "architecture": "x86_64", + "url": "https://alpinelinux.org", + "description": "Meta package to pull in correct libc", + "size": 1228, + "installedSize": 4096, + "pullDependencies": "musl-utils", + "pullChecksum": "Q1UsLZaz0/Go44hd4Vw49UCt40Vp8=", + "gitCommitOfApkPort": "60424133be2e79bbfeff3d58147a22886f817ce2", + "files": [] + } + }, + { + "id": "bb1fd421-fb64-499b-bc59-fe67b8553c1d", + "name": "libcrypto1.1", + "version": "1.1.1l-r0", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "OpenSSL" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:libcrypto1.1:libcrypto1.1:1.1.1l-r0:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/libcrypto1.1@1.1.1l-r0?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "libcrypto1.1", + "originPackage": "openssl", + "maintainer": "Timo Teras ", + "version": "1.1.1l-r0", + "license": "OpenSSL", + "architecture": "x86_64", + "url": "https://www.openssl.org/", + "description": "Crypto library from openssl", + "size": 1211998, + "installedSize": 2768896, + "pullDependencies": "so:libc.musl-x86_64.so.1", + "pullChecksum": "Q1Sywj1TEYEdvX0+MuqC+ea+zXxR0=", + "gitCommitOfApkPort": "3ef1965150d5b1de4af88dc51cf407e11b20b848", + "files": [ + { + "path": "/etc" + }, + { + "path": "/etc/ssl" + }, + { + "path": "/etc/ssl/ct_log_list.cnf", + "digest": { + "algorithm": "sha1", + "value": "Q1olh8TpdAi2QnTl4FK3TjdUiSwTo=" + } + }, + { + "path": "/etc/ssl/ct_log_list.cnf.dist", + "digest": { + "algorithm": "sha1", + "value": "Q1olh8TpdAi2QnTl4FK3TjdUiSwTo=" + } + }, + { + "path": "/etc/ssl/openssl.cnf", + "digest": { + "algorithm": "sha1", + "value": "Q1wGuxVEOK9iGLj1i8D3BSBnT7MJA=" + } + }, + { + "path": "/etc/ssl/openssl.cnf.dist", + "digest": { + "algorithm": "sha1", + "value": "Q1wGuxVEOK9iGLj1i8D3BSBnT7MJA=" + } + }, + { + "path": "/etc/ssl/certs" + }, + { + "path": "/etc/ssl/misc" + }, + { + "path": "/etc/ssl/misc/CA.pl", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1IACevKhK93GYBHp96Ie26jgZ17s=" + } + }, + { + "path": "/etc/ssl/misc/tsget", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q13NVgfr7dQUuGYxur0tNalH6EIjU=" + } + }, + { + "path": "/etc/ssl/misc/tsget.pl", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1ufKVrFftKLv8K/vullp/2reEDdo=" + } + }, + { + "path": "/etc/ssl/private" + }, + { + "path": "/lib" + }, + { + "path": "/lib/libcrypto.so.1.1", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1p0rHZXV1yOM1jGs0zuNSpi951t8=" + } + }, + { + "path": "/usr" + }, + { + "path": "/usr/lib" + }, + { + "path": "/usr/lib/libcrypto.so.1.1", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1T2si+c7ts7sgDxQYve4B3i1Dgo0=" + } + }, + { + "path": "/usr/lib/engines-1.1" + }, + { + "path": "/usr/lib/engines-1.1/afalg.so", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q13GvceRRzjQ6bnB5laIGCkDOHTM0=" + } + }, + { + "path": "/usr/lib/engines-1.1/capi.so", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1h8YLf+3MhbqdHUhGNEabdH5MooA=" + } + }, + { + "path": "/usr/lib/engines-1.1/padlock.so", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1TzNLJ3/GEmO9XW9XuZ/Izoy7zPk=" + } + } + ] + } + }, + { + "id": "114e7b49-1001-4d72-9f2e-086e0aa5a8b7", + "name": "libretls", + "version": "3.3.3p1-r2", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "ISC", + "AND", + "(BSD-3-Clause", + "OR", + "MIT)" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:libretls:libretls:3.3.3p1-r2:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/libretls@3.3.3p1-r2?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "libretls", + "originPackage": "libretls", + "maintainer": "Ariadne Conill ", + "version": "3.3.3p1-r2", + "license": "ISC AND (BSD-3-Clause OR MIT)", + "architecture": "x86_64", + "url": "https://git.causal.agency/libretls/", + "description": "port of libtls from libressl to openssl", + "size": 28872, + "installedSize": 86016, + "pullDependencies": "ca-certificates-bundle so:libc.musl-x86_64.so.1 so:libcrypto.so.1.1 so:libssl.so.1.1", + "pullChecksum": "Q1mKL75PNQ3352oQUtXLS8GfI+37M=", + "gitCommitOfApkPort": "161d02ee8c48f3c3cae1d2b4b5d008fa318da0e1", + "files": [ + { + "path": "/usr" + }, + { + "path": "/usr/lib" + }, + { + "path": "/usr/lib/libtls.so.2", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1nNEC9T/t6W+Ecm0DxqMUnRvcT6k=" + } + }, + { + "path": "/usr/lib/libtls.so.2.0.3", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1t1MtXTHs0kMZ9+GCPJLriysmtA8=" + } + } + ] + } + }, + { + "id": "ed01e864-9235-4b28-b69a-4c95a3c0457b", + "name": "libssl1.1", + "version": "1.1.1l-r0", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "OpenSSL" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:libssl1.1:libssl1.1:1.1.1l-r0:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/libssl1.1@1.1.1l-r0?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "libssl1.1", + "originPackage": "openssl", + "maintainer": "Timo Teras ", + "version": "1.1.1l-r0", + "license": "OpenSSL", + "architecture": "x86_64", + "url": "https://www.openssl.org/", + "description": "SSL shared libraries", + "size": 212918, + "installedSize": 540672, + "pullDependencies": "so:libc.musl-x86_64.so.1 so:libcrypto.so.1.1", + "pullChecksum": "Q1Fgsc0DiapwjaJHbihB9ZrLQhr7Q=", + "gitCommitOfApkPort": "3ef1965150d5b1de4af88dc51cf407e11b20b848", + "files": [ + { + "path": "/lib" + }, + { + "path": "/lib/libssl.so.1.1", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1qaeh6oI3hVHuFty7JD5ASOu8S8k=" + } + }, + { + "path": "/usr" + }, + { + "path": "/usr/lib" + }, + { + "path": "/usr/lib/libssl.so.1.1", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q18j35pe3yp6HOgMih1wlGP1/mm2c=" + } + } + ] + } + }, + { + "id": "2df82ce2-fc7f-40ce-a39b-6bac545cbba8", + "name": "musl", + "version": "1.2.2-r3", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "MIT" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:musl:musl:1.2.2-r3:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/musl@1.2.2-r3?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "musl", + "originPackage": "musl", + "maintainer": "Timo Teräs ", + "version": "1.2.2-r3", + "license": "MIT", + "architecture": "x86_64", + "url": "https://musl.libc.org/", + "description": "the musl c library (libc) implementation", + "size": 382765, + "installedSize": 622592, + "pullDependencies": "", + "pullChecksum": "Q1n4yypJ4tpU5g+jxI7oHT0Bm4Xjo=", + "gitCommitOfApkPort": "1e9cba35059e3bb4635f12ee7e10dfe687df31ad", + "files": [ + { + "path": "/lib" + }, + { + "path": "/lib/ld-musl-x86_64.so.1", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1cZei2MQS2nixN1UwDj0FT9qWO4U=" + } + }, + { + "path": "/lib/libc.musl-x86_64.so.1", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q17yJ3JFNypA4mxhJJr0ou6CzsJVI=" + } + } + ] + } + }, + { + "id": "d8ed04e1-eccd-4441-b937-e960bfffe114", + "name": "musl-utils", + "version": "1.2.2-r3", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "MIT", + "BSD", + "GPL2+" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:musl-utils:musl-utils:1.2.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:musl-utils:musl_utils:1.2.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:musl_utils:musl-utils:1.2.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:musl_utils:musl_utils:1.2.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:musl:musl-utils:1.2.2-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:musl:musl_utils:1.2.2-r3:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/musl-utils@1.2.2-r3?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "musl-utils", + "originPackage": "musl", + "maintainer": "Timo Teräs ", + "version": "1.2.2-r3", + "license": "MIT BSD GPL2+", + "architecture": "x86_64", + "url": "https://musl.libc.org/", + "description": "the musl c library (libc) implementation", + "size": 36662, + "installedSize": 147456, + "pullDependencies": "scanelf so:libc.musl-x86_64.so.1", + "pullChecksum": "Q1WNvvoHVxRySUmjgvqQie71lLRd8=", + "gitCommitOfApkPort": "1e9cba35059e3bb4635f12ee7e10dfe687df31ad", + "files": [ + { + "path": "/sbin" + }, + { + "path": "/sbin/ldconfig", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1Kja2+POZKxEkUOZqwSjC6kmaED4=" + } + }, + { + "path": "/usr" + }, + { + "path": "/usr/bin" + }, + { + "path": "/usr/bin/getconf", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1ENetcQcXKEGU2b0TD1S+WDuwAOE=" + } + }, + { + "path": "/usr/bin/getent", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1AtbzfYTO6GHhaimM7wXWuLGcECI=" + } + }, + { + "path": "/usr/bin/iconv", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1y+KPYlKOaOdDtMOapc2sTDsPKSU=" + } + }, + { + "path": "/usr/bin/ldd", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1yFAhGggmL7ERgbIA7KQxyTzf3ks=" + } + } + ] + } + }, + { + "id": "96bf3afe-d927-4daa-91c5-7178e9462ac5", + "name": "scanelf", + "version": "1.3.2-r0", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "GPL-2.0-only" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:scanelf:scanelf:1.3.2-r0:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/scanelf@1.3.2-r0?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "scanelf", + "originPackage": "pax-utils", + "maintainer": "Natanael Copa ", + "version": "1.3.2-r0", + "license": "GPL-2.0-only", + "architecture": "x86_64", + "url": "https://wiki.gentoo.org/wiki/Hardened/PaX_Utilities", + "description": "Scan ELF binaries for stuff", + "size": 36511, + "installedSize": 94208, + "pullDependencies": "so:libc.musl-x86_64.so.1", + "pullChecksum": "Q1OWKo0fmUbClrhW0CPNjwA8AMLWo=", + "gitCommitOfApkPort": "4c7f72840f5052bc63af1796c3ad0021f97949f2", + "files": [ + { + "path": "/usr" + }, + { + "path": "/usr/bin" + }, + { + "path": "/usr/bin/scanelf", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1LhDyQrsweSqYTuRcjhG2d0pxhrE=" + } + } + ] + } + }, + { + "id": "562ec670-5625-4c25-b8a7-ebaacf04d06c", + "name": "ssl_client", + "version": "1.33.1-r3", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "GPL-2.0-only" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:ssl-client:ssl-client:1.33.1-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:ssl-client:ssl_client:1.33.1-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:ssl_client:ssl-client:1.33.1-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:ssl_client:ssl_client:1.33.1-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:ssl:ssl-client:1.33.1-r3:*:*:*:*:*:*:*", + "cpe:2.3:a:ssl:ssl_client:1.33.1-r3:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/ssl_client@1.33.1-r3?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "ssl_client", + "originPackage": "busybox", + "maintainer": "Natanael Copa ", + "version": "1.33.1-r3", + "license": "GPL-2.0-only", + "architecture": "x86_64", + "url": "https://busybox.net/", + "description": "EXternal ssl_client for busybox wget", + "size": 4381, + "installedSize": 28672, + "pullDependencies": "so:libc.musl-x86_64.so.1 so:libtls.so.2", + "pullChecksum": "Q1d7WkMOIKXIk3qxexUxSo60HOofY=", + "gitCommitOfApkPort": "98710256acf90e670e79f32f1f0350b830979d24", + "files": [ + { + "path": "/usr" + }, + { + "path": "/usr/bin" + }, + { + "path": "/usr/bin/ssl_client", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q1gPKQTCzC1isM7R89HFwb+A1XmM4=" + } + } + ] + } + }, + { + "id": "52382e1a-320b-4e62-8103-39baa39d85b3", + "name": "zlib", + "version": "1.2.11-r3", + "type": "apk", + "foundBy": "apkdb-cataloger", + "locations": [ + { + "path": "/lib/apk/db/installed", + "layerID": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68" + } + ], + "licenses": [ + "Zlib" + ], + "language": "", + "cpes": [ + "cpe:2.3:a:zlib:zlib:1.2.11-r3:*:*:*:*:*:*:*" + ], + "purl": "pkg:alpine/zlib@1.2.11-r3?arch=x86_64", + "metadataType": "ApkMetadata", + "metadata": { + "package": "zlib", + "originPackage": "zlib", + "maintainer": "Natanael Copa ", + "version": "1.2.11-r3", + "license": "Zlib", + "architecture": "x86_64", + "url": "https://zlib.net/", + "description": "A compression/decompression Library", + "size": 51398, + "installedSize": 110592, + "pullDependencies": "so:libc.musl-x86_64.so.1", + "pullChecksum": "Q1Sc/5gG4ey/zvnyPPQ/Au7bXqc08=", + "gitCommitOfApkPort": "388a4fb3640f8ccbd18e105df3ad741dca4247e1", + "files": [ + { + "path": "/lib" + }, + { + "path": "/lib/libz.so.1", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "777", + "digest": { + "algorithm": "sha1", + "value": "Q1a2H8hP24ryCAGf8fnc1Nha9IIHc=" + } + }, + { + "path": "/lib/libz.so.1.2.11", + "ownerUid": "0", + "ownerGid": "0", + "permissions": "755", + "digest": { + "algorithm": "sha1", + "value": "Q19Iml1N+v08tnk1ZtqGEVIEtIFJI=" + } + } + ] + } + } + ], + "artifactRelationships": [], + "source": { + "type": "image", + "target": { + "userInput": "alpine:latest", + "imageID": "sha256:14119a10abf4669e8cdbdff324a9f9605d99697215a0d21c360fe8dfa8471bab", + "manifestDigest": "sha256:69704ef328d05a9f806b6b8502915e6a0a4faa4d72018dc42343f511490daf8a", + "mediaType": "application/vnd.docker.distribution.manifest.v2+json", + "tags": [], + "imageSize": 5590942, + "layers": [ + { + "mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip", + "digest": "sha256:e2eb06d8af8218cfec8210147357a68b7e13f7c485b991c288c2d01dc228bb68", + "size": 5590942 + } + ], + "manifest": "ewogICAic2NoZW1hVmVyc2lvbiI6IDIsCiAgICJtZWRpYVR5cGUiOiAiYXBwbGljYXRpb24vdm5kLmRvY2tlci5kaXN0cmlidXRpb24ubWFuaWZlc3QudjIranNvbiIsCiAgICJjb25maWciOiB7CiAgICAgICJtZWRpYVR5cGUiOiAiYXBwbGljYXRpb24vdm5kLmRvY2tlci5jb250YWluZXIuaW1hZ2UudjEranNvbiIsCiAgICAgICJzaXplIjogMTQ3MSwKICAgICAgImRpZ2VzdCI6ICJzaGEyNTY6MTQxMTlhMTBhYmY0NjY5ZThjZGJkZmYzMjRhOWY5NjA1ZDk5Njk3MjE1YTBkMjFjMzYwZmU4ZGZhODQ3MWJhYiIKICAgfSwKICAgImxheWVycyI6IFsKICAgICAgewogICAgICAgICAibWVkaWFUeXBlIjogImFwcGxpY2F0aW9uL3ZuZC5kb2NrZXIuaW1hZ2Uucm9vdGZzLmRpZmYudGFyLmd6aXAiLAogICAgICAgICAic2l6ZSI6IDI4MTQ0NDYsCiAgICAgICAgICJkaWdlc3QiOiAic2hhMjU2OmEwZDBhMGQ0NmY4YjUyNDczOTgyYTNjNDY2MzE4ZjQ3OTc2NzU3NzU1MWE1M2ZmYzkwNzRjOWZhNzAzNTk4MmUiCiAgICAgIH0KICAgXQp9", + "config": "eyJhcmNoaXRlY3R1cmUiOiJhbWQ2NCIsImNvbmZpZyI6eyJIb3N0bmFtZSI6IiIsIkRvbWFpbm5hbWUiOiIiLCJVc2VyIjoiIiwiQXR0YWNoU3RkaW4iOmZhbHNlLCJBdHRhY2hTdGRvdXQiOmZhbHNlLCJBdHRhY2hTdGRlcnIiOmZhbHNlLCJUdHkiOmZhbHNlLCJPcGVuU3RkaW4iOmZhbHNlLCJTdGRpbk9uY2UiOmZhbHNlLCJFbnYiOlsiUEFUSD0vdXNyL2xvY2FsL3NiaW46L3Vzci9sb2NhbC9iaW46L3Vzci9zYmluOi91c3IvYmluOi9zYmluOi9iaW4iXSwiQ21kIjpbIi9iaW4vc2giXSwiSW1hZ2UiOiJzaGEyNTY6ZDNlMGI2MjU4ZWMyZjcyNWMxOTY2OGYxMWFlNTMyM2MzYjAyNDVlMTk3ZWM0Nzg0MjRlYzZhODc5MzU2OTBlYiIsIlZvbHVtZXMiOm51bGwsIldvcmtpbmdEaXIiOiIiLCJFbnRyeXBvaW50IjpudWxsLCJPbkJ1aWxkIjpudWxsLCJMYWJlbHMiOm51bGx9LCJjb250YWluZXIiOiIzMzAyODljNjQ5ZGI4NmY1ZmIxYWU1YmZlZjE4NTAxMDEyYjU1MGFkYjA2MzhiOTE5M2Q0YTNhNGI2NWEyZjliIiwiY29udGFpbmVyX2NvbmZpZyI6eyJIb3N0bmFtZSI6IjMzMDI4OWM2NDlkYiIsIkRvbWFpbm5hbWUiOiIiLCJVc2VyIjoiIiwiQXR0YWNoU3RkaW4iOmZhbHNlLCJBdHRhY2hTdGRvdXQiOmZhbHNlLCJBdHRhY2hTdGRlcnIiOmZhbHNlLCJUdHkiOmZhbHNlLCJPcGVuU3RkaW4iOmZhbHNlLCJTdGRpbk9uY2UiOmZhbHNlLCJFbnYiOlsiUEFUSD0vdXNyL2xvY2FsL3NiaW46L3Vzci9sb2NhbC9iaW46L3Vzci9zYmluOi91c3IvYmluOi9zYmluOi9iaW4iXSwiQ21kIjpbIi9iaW4vc2giLCItYyIsIiMobm9wKSAiLCJDTUQgW1wiL2Jpbi9zaFwiXSJdLCJJbWFnZSI6InNoYTI1NjpkM2UwYjYyNThlYzJmNzI1YzE5NjY4ZjExYWU1MzIzYzNiMDI0NWUxOTdlYzQ3ODQyNGVjNmE4NzkzNTY5MGViIiwiVm9sdW1lcyI6bnVsbCwiV29ya2luZ0RpciI6IiIsIkVudHJ5cG9pbnQiOm51bGwsIk9uQnVpbGQiOm51bGwsIkxhYmVscyI6e319LCJjcmVhdGVkIjoiMjAyMS0wOC0yN1QxNzoxOTo0NS43NTg2MTE1MjNaIiwiZG9ja2VyX3ZlcnNpb24iOiIyMC4xMC43IiwiaGlzdG9yeSI6W3siY3JlYXRlZCI6IjIwMjEtMDgtMjdUMTc6MTk6NDUuNTUzMDkyMzYzWiIsImNyZWF0ZWRfYnkiOiIvYmluL3NoIC1jICMobm9wKSBBREQgZmlsZTphYWQ0MjkwZDI3NTgwY2MxYTA5NGZmYWY5OGMzY2EyZmM1ZDY5OWZlNjk1ZGZiOGU2ZTlmYWMyMGYxMTI5NDUwIGluIC8gIn0seyJjcmVhdGVkIjoiMjAyMS0wOC0yN1QxNzoxOTo0NS43NTg2MTE1MjNaIiwiY3JlYXRlZF9ieSI6Ii9iaW4vc2ggLWMgIyhub3ApICBDTUQgW1wiL2Jpbi9zaFwiXSIsImVtcHR5X2xheWVyIjp0cnVlfV0sIm9zIjoibGludXgiLCJyb290ZnMiOnsidHlwZSI6ImxheWVycyIsImRpZmZfaWRzIjpbInNoYTI1NjplMmViMDZkOGFmODIxOGNmZWM4MjEwMTQ3MzU3YTY4YjdlMTNmN2M0ODViOTkxYzI4OGMyZDAxZGMyMjhiYjY4Il19fQ==", + "repoDigests": [ + "index.docker.io/library/alpine@sha256:e1c082e3d3c45cccac829840a25941e679c25d438cc8412c2fa221cf1a824e6a" + ] + } + }, + "distro": { + "name": "alpine", + "version": "3.14.2", + "idLike": "" + }, + "descriptor": { + "name": "syft", + "version": "[not provided]" + }, + "schema": { + "version": "1.1.0", + "url": "https://raw.githubusercontent.com/anchore/syft/main/schema/json/schema-1.1.0.json" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/all_formats_convertible_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/all_formats_convertible_test.go new file mode 100644 index 0000000000000000000000000000000000000000..fa38f32670dae01bedfc1c6db9ec6219512954b6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/all_formats_convertible_test.go @@ -0,0 +1,78 @@ +package cli + +import ( + "os" + "path/filepath" + "strings" + "testing" + + "github.com/stretchr/testify/require" +) + +type conversion struct { + To string + From string +} + +func TestConvertCmdFlags(t *testing.T) { + commonAssertions := []traitAssertion{ + func(tb testing.TB, stdout, _ string, _ int) { + tb.Helper() + if len(stdout) < 1000 { + tb.Errorf("there may not be any report output (len=%d)", len(stdout)) + } + }, + assertSuccessfulReturnCode, + } + + tests := []struct { + name string + conversions []conversion + env map[string]string + assertions []traitAssertion + }{ + { + name: "syft-format convertable to spdx-json", + conversions: []conversion{ + {To: "syft-json", From: "spdx-json"}, + {To: "syft-json", From: "cyclonedx-json"}, + {To: "spdx-json", From: "syft-json"}, + {To: "spdx-json", From: "cyclonedx-json"}, + {To: "cyclonedx-json", From: "syft-json"}, + {To: "cyclonedx-json", From: "spdx-json"}, + }, + assertions: commonAssertions, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + for _, c := range test.conversions { + sbomArgs := []string{"dir:./test-fixtures/image-pkg-coverage", "-o", c.From} + cmd, stdout, stderr := runSyft(t, test.env, sbomArgs...) + if cmd.ProcessState.ExitCode() != 0 { + t.Fatalf("failure executing syft creating an sbom") + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + return + } + + tempDir := t.TempDir() + sbomFile := filepath.Join(tempDir, "sbom.json") + require.NoError(t, os.WriteFile(sbomFile, []byte(stdout), 0666)) + + convertArgs := []string{"convert", sbomFile, "-o", c.To} + cmd, stdout, stderr = runSyft(t, test.env, convertArgs...) + for _, traitFn := range test.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/all_formats_expressible_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/all_formats_expressible_test.go new file mode 100644 index 0000000000000000000000000000000000000000..a48639d765fa50ad92a10c82b0e8436ce9705f73 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/all_formats_expressible_test.go @@ -0,0 +1,44 @@ +package cli + +import ( + "fmt" + "strings" + "testing" + + "github.com/stretchr/testify/require" + + "github.com/anchore/syft/internal/formats/template" + "github.com/anchore/syft/syft" +) + +func TestAllFormatsExpressible(t *testing.T) { + commonAssertions := []traitAssertion{ + func(tb testing.TB, stdout, _ string, _ int) { + tb.Helper() + if len(stdout) < 1000 { + tb.Errorf("there may not be any report output (len=%d)", len(stdout)) + } + }, + assertSuccessfulReturnCode, + } + formats := syft.FormatIDs() + require.NotEmpty(t, formats) + for _, o := range formats { + t.Run(fmt.Sprintf("format:%s", o), func(t *testing.T) { + args := []string{"dir:./test-fixtures/image-pkg-coverage", "-o", string(o)} + if o == template.ID { + args = append(args, "-t", "test-fixtures/csv.template") + } + + cmd, stdout, stderr := runSyft(t, nil, args...) + for _, traitFn := range commonAssertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/attest_cmd_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/attest_cmd_test.go new file mode 100644 index 0000000000000000000000000000000000000000..43a1d0404502f9bcfa865bada2e360b20ea30502 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/attest_cmd_test.go @@ -0,0 +1,60 @@ +package cli + +import ( + "strings" + "testing" +) + +func TestAttestCmd(t *testing.T) { + img := "registry:busybox:latest" + tests := []struct { + name string + args []string + env map[string]string + assertions []traitAssertion + pw string + }{ + { + name: "no-args-shows-help", + args: []string{"attest"}, + assertions: []traitAssertion{ + assertInOutput("an image/directory argument is required"), // specific error that should be shown + assertInOutput("from a container image as the predicate of an in-toto attestation"), // excerpt from help description + assertFailingReturnCode, + }, + pw: "", + }, + { + name: "can encode syft.json as the predicate given a password", + args: []string{"attest", "-o", "json", "--key", "cosign.key", img}, + assertions: []traitAssertion{ + assertSuccessfulReturnCode, + }, + pw: "test", + }, + { + name: "can encode syft.json as the predicate given a blank password", + args: []string{"attest", "-o", "json", "--key", "cosign.key", img}, + assertions: []traitAssertion{ + assertSuccessfulReturnCode, + }, + pw: "", + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + cleanup := setupPKI(t, test.pw) + defer cleanup() + cmd, stdout, stderr := runSyft(t, test.env, test.args...) + for _, traitFn := range test.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/cosign_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/cosign_test.go new file mode 100644 index 0000000000000000000000000000000000000000..283d36b6e8978fddd28fba66bdd0cb77c3d5c6fb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/cosign_test.go @@ -0,0 +1,177 @@ +package cli + +import ( + "bufio" + "io" + "net/http" + "os" + "os/exec" + "path/filepath" + "strings" + "testing" + "time" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func runAndShow(t *testing.T, cmd *exec.Cmd) { + t.Helper() + + stderr, err := cmd.StderrPipe() + require.NoErrorf(t, err, "could not get stderr: +v", err) + + stdout, err := cmd.StdoutPipe() + require.NoErrorf(t, err, "could not get stdout: +v", err) + + err = cmd.Start() + require.NoErrorf(t, err, "failed to start cmd: %+v", err) + + show := func(label string, reader io.ReadCloser) { + scanner := bufio.NewScanner(reader) + scanner.Split(bufio.ScanLines) + for scanner.Scan() { + t.Logf("%s: %s", label, scanner.Text()) + } + } + + show("out", stdout) + show("err", stderr) +} + +func TestCosignWorkflow(t *testing.T) { + // found under test-fixtures/registry/Makefile + img := "localhost:5000/attest:latest" + attestationFile := "attestation.json" + tests := []struct { + name string + syftArgs []string + cosignAttachArgs []string + cosignVerifyArgs []string + env map[string]string + assertions []traitAssertion + setup func(*testing.T) + cleanup func() + }{ + { + name: "cosign verify syft attest", + syftArgs: []string{ + "attest", + "-o", + "json", + "--key", + "cosign.key", + img, + }, + // cosign attach attestation + cosignAttachArgs: []string{ + "attach", + "attestation", + "--attestation", + attestationFile, + img, + }, + // cosign verify-attestation + cosignVerifyArgs: []string{ + "verify-attestation", + "-key", + "cosign.pub", + img, + }, + assertions: []traitAssertion{ + assertSuccessfulReturnCode, + }, + setup: func(t *testing.T) { + cwd, err := os.Getwd() + require.NoErrorf(t, err, "unable to get cwd: %+v", err) + + // get working directory for local registry + fixturesPath := filepath.Join(cwd, "test-fixtures", "registry") + makeTask := filepath.Join(fixturesPath, "Makefile") + t.Logf("Generating Fixture from 'make %s'", makeTask) + + cmd := exec.Command("make") + cmd.Dir = fixturesPath + runAndShow(t, cmd) + + var done = make(chan struct{}) + defer close(done) + for interval := range testRetryIntervals(done) { + resp, err := http.Get("http://127.0.0.1:5000/v2/") + if err != nil { + t.Logf("waiting for registry err=%+v", err) + } else { + if resp.StatusCode == http.StatusOK { + break + } + t.Logf("waiting for registry code=%+v", resp.StatusCode) + } + + time.Sleep(interval) + } + + cmd = exec.Command("make", "push") + cmd.Dir = fixturesPath + runAndShow(t, cmd) + + }, + cleanup: func() { + cwd, err := os.Getwd() + assert.NoErrorf(t, err, "unable to get cwd: %+v", err) + + fixturesPath := filepath.Join(cwd, "test-fixtures", "registry") + makeTask := filepath.Join(fixturesPath, "Makefile") + t.Logf("Generating Fixture from 'make %s'", makeTask) + + // delete attestation file + os.Remove(attestationFile) + + cmd := exec.Command("make", "stop") + cmd.Dir = fixturesPath + + runAndShow(t, cmd) + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + t.Cleanup(tt.cleanup) + tt.setup(t) + pkiCleanup := setupPKI(t, "") // blank password + defer pkiCleanup() + + // attest + cmd, stdout, stderr := runSyft(t, tt.env, tt.syftArgs...) + for _, traitFn := range tt.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + checkCmdFailure(t, stdout, stderr, cmd) + require.NoError(t, os.WriteFile(attestationFile, []byte(stdout), 0666)) + + // attach + cmd, stdout, stderr = runCosign(t, tt.env, tt.cosignAttachArgs...) + for _, traitFn := range tt.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + checkCmdFailure(t, stdout, stderr, cmd) + + // attest + cmd, stdout, stderr = runCosign(t, tt.env, tt.cosignAttachArgs...) + for _, traitFn := range tt.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + checkCmdFailure(t, stdout, stderr, cmd) + + }) + } +} + +func checkCmdFailure(t testing.TB, stdout, stderr string, cmd *exec.Cmd) { + require.Falsef(t, t.Failed(), "%s %s trait assertion failed", cmd.Path, strings.Join(cmd.Args, " ")) + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/cyclonedx_valid_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/cyclonedx_valid_test.go new file mode 100644 index 0000000000000000000000000000000000000000..f72a18a80ebfb965124bf9dc28447233f2ecabc7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/cyclonedx_valid_test.go @@ -0,0 +1,142 @@ +package cli + +import ( + "os" + "strings" + "testing" + + "github.com/anchore/stereoscope/pkg/imagetest" +) + +// We have schema validation mechanims in schema/cyclonedx/ +// This test allows us to double check that validation against the cyclonedx-cli tool +func TestValidCycloneDX(t *testing.T) { + imageFixture := func(t *testing.T) string { + fixtureImageName := "image-pkg-coverage" + imagetest.GetFixtureImage(t, "docker-archive", fixtureImageName) + tarPath := imagetest.GetFixtureImageTarPath(t, fixtureImageName) + return "docker-archive:" + tarPath + } + + // TODO update image to exercise entire cyclonedx schema + tests := []struct { + name string + subcommand string + args []string + fixture func(*testing.T) string + assertions []traitAssertion + }{ + { + name: "validate cyclonedx output", + subcommand: "packages", + args: []string{"-o", "cyclonedx-json"}, + fixture: imageFixture, + assertions: []traitAssertion{ + assertSuccessfulReturnCode, + assertValidCycloneDX, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + fixtureRef := test.fixture(t) + args := []string{ + test.subcommand, fixtureRef, "-q", + } + for _, a := range test.args { + args = append(args, a) + } + + cmd, stdout, stderr := runSyft(t, nil, args...) + for _, traitFn := range test.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + + validateCycloneDXJSON(t, stdout) + }) + } +} + +func assertValidCycloneDX(tb testing.TB, stdout, stderr string, rc int) { + tb.Helper() + f, err := os.CreateTemp("", "tmpfile-") + if err != nil { + tb.Fatal(err) + } + + // close and remove the temporary file at the end of the program + defer f.Close() + defer os.Remove(f.Name()) + + data := []byte(stdout) + + if _, err := f.Write(data); err != nil { + tb.Fatal(err) + } + + args := []string{ + "validate", + "--input-format", + "json", + "--input-version", + "v1_4", + "--input-file", + "/sbom", + } + + cmd, stdout, stderr := runCycloneDXInDocker(tb, nil, "cyclonedx/cyclonedx-cli", f, args...) + if cmd.ProcessState.ExitCode() != 0 { + tb.Errorf("expected no validation failures for cyclonedx-cli but got rc=%d", rc) + } + + if tb.Failed() { + tb.Log("STDOUT:\n", stdout) + tb.Log("STDERR:\n", stderr) + tb.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } +} + +// validate --input-format json --input-version v1_4 --input-file bom.json +func validateCycloneDXJSON(t *testing.T, stdout string) { + f, err := os.CreateTemp("", "tmpfile-") + if err != nil { + t.Fatal(err) + } + + // close and remove the temporary file at the end of the program + defer f.Close() + defer os.Remove(f.Name()) + + data := []byte(stdout) + + if _, err := f.Write(data); err != nil { + t.Fatal(err) + } + + args := []string{ + "validate", + "--input-format", + "json", + "--input-version", + "v1_4", + "--input-file", + "/sbom", + } + + cmd, stdout, stderr := runCycloneDXInDocker(t, nil, "cyclonedx/cyclonedx-cli", f, args...) + if strings.Contains(stdout, "BOM is not valid") { + t.Errorf("expected no validation failures for cyclonedx-cli but found invalid BOM") + } + + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/dir_root_scan_regression_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/dir_root_scan_regression_test.go new file mode 100644 index 0000000000000000000000000000000000000000..88d5ce0d55198529bdf732ba4e967215f6c79f00 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/dir_root_scan_regression_test.go @@ -0,0 +1,46 @@ +package cli + +import ( + "os/exec" + "strings" + "testing" + "time" +) + +func TestDirectoryScanCompletesWithinTimeout(t *testing.T) { + image := "alpine:latest" + + // we want to pull the image ahead of the test as to not affect the timeout value + pullDockerImage(t, image) + + var cmd *exec.Cmd + var stdout, stderr string + done := make(chan struct{}) + go func() { + defer close(done) + cmd, stdout, stderr = runSyftInDocker(t, nil, image, "dir:/", "-vv") + }() + + select { + case <-done: + break + case <-time.After(10 * time.Second): + t.Fatalf("directory scan is taking too long") + } + + assertions := []traitAssertion{ + assertTableReport, + assertSuccessfulReturnCode, + } + + for _, traitFn := range assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/json_schema_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/json_schema_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d4ea995df7f3acec459291d91c4254223e8c82c1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/json_schema_test.go @@ -0,0 +1,91 @@ +package cli + +import ( + "fmt" + "path" + "strings" + "testing" + + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/anchore/syft/internal" + "github.com/xeipuuv/gojsonschema" +) + +// this is the path to the json schema directory relative to the root of the repo +const jsonSchemaPath = "schema/json" + +func TestJSONSchema(t *testing.T) { + + imageFixture := func(t *testing.T) string { + fixtureImageName := "image-pkg-coverage" + imagetest.GetFixtureImage(t, "docker-archive", fixtureImageName) + tarPath := imagetest.GetFixtureImageTarPath(t, fixtureImageName) + return "docker-archive:" + tarPath + } + + tests := []struct { + name string + subcommand string + args []string + fixture func(*testing.T) string + }{ + { + name: "packages:image:docker-archive:pkg-coverage", + subcommand: "packages", + args: []string{"-o", "json"}, + fixture: imageFixture, + }, + { + name: "power-user:image:docker-archive:pkg-coverage", + subcommand: "power-user", + fixture: imageFixture, + }, + { + name: "packages:dir:pkg-coverage", + subcommand: "packages", + args: []string{"-o", "json"}, + fixture: func(t *testing.T) string { + return "dir:test-fixtures/image-pkg-coverage" + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + fixtureRef := test.fixture(t) + args := []string{ + test.subcommand, fixtureRef, "-q", + } + for _, a := range test.args { + args = append(args, a) + } + + _, stdout, stderr := runSyft(t, nil, args...) + + if len(strings.Trim(stdout, "\n ")) < 100 { + t.Fatalf("bad syft run:\noutput: %q\n:error: %q", stdout, stderr) + } + + validateJsonAgainstSchema(t, stdout) + }) + } +} + +func validateJsonAgainstSchema(t testing.TB, json string) { + fullSchemaPath := path.Join(repoRoot(t), jsonSchemaPath, fmt.Sprintf("schema-%s.json", internal.JSONSchemaVersion)) + schemaLoader := gojsonschema.NewReferenceLoader(fmt.Sprintf("file://%s", fullSchemaPath)) + documentLoader := gojsonschema.NewStringLoader(json) + + result, err := gojsonschema.Validate(schemaLoader, documentLoader) + if err != nil { + t.Fatal("unable to validate json schema:", err.Error()) + } + + if !result.Valid() { + t.Errorf("failed json schema validation:") + t.Errorf("JSON:\n%s\n", json) + for _, desc := range result.Errors() { + t.Errorf(" - %s\n", desc) + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/packages_cmd_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/packages_cmd_test.go new file mode 100644 index 0000000000000000000000000000000000000000..abd3d8e2e7ca5707beb8906c297f63caf8fdd630 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/packages_cmd_test.go @@ -0,0 +1,340 @@ +package cli + +import ( + "fmt" + "path/filepath" + "strings" + "testing" +) + +func TestPackagesCmdFlags(t *testing.T) { + hiddenPackagesImage := "docker-archive:" + getFixtureImage(t, "image-hidden-packages") + coverageImage := "docker-archive:" + getFixtureImage(t, "image-pkg-coverage") + //badBinariesImage := "docker-archive:" + getFixtureImage(t, "image-bad-binaries") + tmp := t.TempDir() + "/" + + tests := []struct { + name string + args []string + env map[string]string + assertions []traitAssertion + }{ + { + name: "no-args-shows-help", + args: []string{"packages"}, + assertions: []traitAssertion{ + assertInOutput("an image/directory argument is required"), // specific error that should be shown + assertInOutput("Generate a packaged-based Software Bill Of Materials"), // excerpt from help description + assertFailingReturnCode, + }, + }, + { + name: "json-output-flag", + args: []string{"packages", "-o", "json", coverageImage}, + assertions: []traitAssertion{ + assertJsonReport, + assertSuccessfulReturnCode, + }, + }, + { + name: "multiple-output-flags", + args: []string{"packages", "-o", "table", "-o", "json=" + tmp + ".tmp/multiple-output-flag-test.json", coverageImage}, + assertions: []traitAssertion{ + assertTableReport, + assertFileExists(tmp + ".tmp/multiple-output-flag-test.json"), + assertSuccessfulReturnCode, + }, + }, + // I haven't been able to reproduce locally yet, but in CI this has proven to be unstable: + // For the same commit: + // pass: https://github.com/anchore/syft/runs/4611344142?check_suite_focus=true + // fail: https://github.com/anchore/syft/runs/4611343586?check_suite_focus=true + // For the meantime this test will be commented out, but should be added back in as soon as possible. + // + //{ + // name: "regression-survive-bad-binaries", + // // this image has all sorts of rich binaries from the clang-13 test suite that should do pretty bad things + // // to the go cataloger binary path. We should NEVER let a panic stop the cataloging process for these + // // specific cases. + // + // // this is more of an integration test, however, to assert the output we want to see from the application + // // a CLI test is much easier. + // args: []string{"packages", "-vv", badBinariesImage}, + // assertions: []traitAssertion{ + // assertInOutput("could not parse possible go binary"), + // assertSuccessfulReturnCode, + // }, + //}, + { + name: "output-env-binding", + env: map[string]string{ + "SYFT_OUTPUT": "json", + }, + args: []string{"packages", coverageImage}, + assertions: []traitAssertion{ + assertJsonReport, + assertSuccessfulReturnCode, + }, + }, + { + name: "table-output-flag", + args: []string{"packages", "-o", "table", coverageImage}, + assertions: []traitAssertion{ + assertTableReport, + assertSuccessfulReturnCode, + }, + }, + { + name: "default-output-flag", + args: []string{"packages", coverageImage}, + assertions: []traitAssertion{ + assertTableReport, + assertSuccessfulReturnCode, + }, + }, + { + name: "squashed-scope-flag", + args: []string{"packages", "-o", "json", "-s", "squashed", coverageImage}, + assertions: []traitAssertion{ + assertPackageCount(34), + assertSuccessfulReturnCode, + }, + }, + { + name: "squashed-scope-flag-hidden-packages", + args: []string{"packages", "-o", "json", "-s", "squashed", hiddenPackagesImage}, + assertions: []traitAssertion{ + assertPackageCount(162), + assertNotInOutput("vsftpd"), // hidden package + assertSuccessfulReturnCode, + }, + }, + { + name: "all-layers-scope-flag", + args: []string{"packages", "-o", "json", "-s", "all-layers", hiddenPackagesImage}, + assertions: []traitAssertion{ + assertPackageCount(163), // packages are now deduplicated for this case + assertInOutput("all-layers"), + assertInOutput("vsftpd"), // hidden package + assertSuccessfulReturnCode, + }, + }, + { + name: "all-layers-scope-flag-by-env", + args: []string{"packages", "-o", "json", hiddenPackagesImage}, + env: map[string]string{ + "SYFT_PACKAGE_CATALOGER_SCOPE": "all-layers", + }, + assertions: []traitAssertion{ + assertPackageCount(163), // packages are now deduplicated for this case + assertInOutput("all-layers"), + assertInOutput("vsftpd"), // hidden package + assertSuccessfulReturnCode, + }, + }, + { + name: "attempt-upload-on-cli-switches", + args: []string{"packages", "-vv", "-H", "localhost:8080", "-u", "the-username", "-d", "test-fixtures/image-pkg-coverage/Dockerfile", "--overwrite-existing-image", coverageImage}, + env: map[string]string{ + "SYFT_ANCHORE_PATH": "path/to/api", + "SYFT_ANCHORE_PASSWORD": "the-password", + }, + assertions: []traitAssertion{ + // we cannot easily assert a successful upload behavior, so instead we are doing the next best thing + // and asserting that the parsed configuration has the expected values and we see log entries + // indicating an upload attempt. + assertNotInOutput("the-username"), + assertNotInOutput("the-password"), + assertInOutput("uploading results to localhost:8080"), + assertInOutput(`dockerfile: test-fixtures/image-pkg-coverage/Dockerfile`), + assertInOutput(`overwrite-existing-image: true`), + assertInOutput(`path: path/to/api`), + assertInOutput(`host: localhost:8080`), + assertFailingReturnCode, // upload can't go anywhere, so if this passes that would be surprising + }, + }, + { + name: "dockerfile-without-upload-is-invalid", + args: []string{"packages", "-vv", "-d", "test-fixtures/image-pkg-coverage/Dockerfile", coverageImage}, + assertions: []traitAssertion{ + + assertNotInOutput("uploading results to localhost:8080"), + assertInOutput("invalid application config: cannot provide dockerfile option without enabling upload"), + assertFailingReturnCode, + }, + }, + { + name: "attempt-upload-with-env-host-set", + args: []string{"packages", "-vv", coverageImage}, + env: map[string]string{ + "SYFT_ANCHORE_HOST": "localhost:8080", + }, + assertions: []traitAssertion{ + assertInOutput("uploading results to localhost:8080"), + assertFailingReturnCode, // upload can't go anywhere, so if this passes that would be surprising + }, + }, + { + // we want to make certain that syft can catalog a single go binary and get a SBOM report that is not empty + name: "catalog-single-go-binary", + args: []string{"packages", "-o", "json", getSyftBinaryLocation(t)}, + assertions: []traitAssertion{ + assertJsonReport, + assertStdoutLengthGreaterThan(1000), + assertSuccessfulReturnCode, + }, + }, + { + name: "responds-to-package-cataloger-search-options", + args: []string{"packages", "-vv"}, + env: map[string]string{ + "SYFT_PACKAGE_SEARCH_UNINDEXED_ARCHIVES": "true", + "SYFT_PACKAGE_SEARCH_INDEXED_ARCHIVES": "false", + }, + assertions: []traitAssertion{ + // the application config in the log matches that of what we expect to have been configured. Note: + // we are not testing further wiring of this option, only that the config responds to + // package-cataloger-level options. + assertInOutput("search-unindexed-archives: true"), + assertInOutput("search-indexed-archives: false"), + }, + }, + { + name: "platform-option-wired-up", + args: []string{"packages", "--platform", "arm64", "-o", "json", "registry:busybox:1.31"}, + assertions: []traitAssertion{ + assertInOutput("sha256:1ee006886991ad4689838d3a288e0dd3fd29b70e276622f16b67a8922831a853"), // linux/arm64 image digest + assertSuccessfulReturnCode, + }, + }, + { + name: "json-file-flag", + args: []string{"packages", "-o", "json", "--file", filepath.Join(tmp, "output-1.json"), coverageImage}, + assertions: []traitAssertion{ + assertSuccessfulReturnCode, + assertFileOutput(t, filepath.Join(tmp, "output-1.json"), + assertJsonReport, + ), + }, + }, + { + name: "json-output-flag-to-file", + args: []string{"packages", "-o", fmt.Sprintf("json=%s", filepath.Join(tmp, "output-2.json")), coverageImage}, + assertions: []traitAssertion{ + assertSuccessfulReturnCode, + assertFileOutput(t, filepath.Join(tmp, "output-2.json"), + assertJsonReport, + ), + }, + }, + { + name: "catalogers-option", + // This will detect enable python-index-cataloger, python-package-cataloger and ruby-gemspec cataloger + args: []string{"packages", "-o", "json", "--catalogers", "python,ruby-gemspec", coverageImage}, + assertions: []traitAssertion{ + assertPackageCount(13), + assertSuccessfulReturnCode, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + cmd, stdout, stderr := runSyft(t, test.env, test.args...) + for _, traitFn := range test.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + }) + } +} + +func TestRegistryAuth(t *testing.T) { + host := "localhost:17" + image := fmt.Sprintf("%s/something:latest", host) + args := []string{"packages", "-vv", fmt.Sprintf("registry:%s", image)} + + tests := []struct { + name string + args []string + env map[string]string + assertions []traitAssertion + }{ + { + name: "fallback to keychain", + args: args, + assertions: []traitAssertion{ + assertInOutput("source=OciRegistry"), + assertInOutput(image), + assertInOutput("no registry credentials configured, using the default keychain"), + }, + }, + { + name: "use creds", + args: args, + env: map[string]string{ + "SYFT_REGISTRY_AUTH_AUTHORITY": host, + "SYFT_REGISTRY_AUTH_USERNAME": "username", + "SYFT_REGISTRY_AUTH_PASSWORD": "password", + }, + assertions: []traitAssertion{ + assertInOutput("source=OciRegistry"), + assertInOutput(image), + assertInOutput(fmt.Sprintf(`using basic auth for registry "%s"`, host)), + }, + }, + { + name: "use token", + args: args, + env: map[string]string{ + "SYFT_REGISTRY_AUTH_AUTHORITY": host, + "SYFT_REGISTRY_AUTH_TOKEN": "token", + }, + assertions: []traitAssertion{ + assertInOutput("source=OciRegistry"), + assertInOutput(image), + assertInOutput(fmt.Sprintf(`using token for registry "%s"`, host)), + }, + }, + { + name: "not enough info fallsback to keychain", + args: args, + env: map[string]string{ + "SYFT_REGISTRY_AUTH_AUTHORITY": host, + }, + assertions: []traitAssertion{ + assertInOutput("source=OciRegistry"), + assertInOutput(image), + assertInOutput(`no registry credentials configured, using the default keychain`), + }, + }, + { + name: "allows insecure http flag", + args: args, + env: map[string]string{ + "SYFT_REGISTRY_INSECURE_USE_HTTP": "true", + }, + assertions: []traitAssertion{ + assertInOutput("insecure-use-http: true"), + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + cmd, stdout, stderr := runSyft(t, test.env, test.args...) + for _, traitAssertionFn := range test.assertions { + traitAssertionFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/power_user_cmd_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/power_user_cmd_test.go new file mode 100644 index 0000000000000000000000000000000000000000..ac48ff150183ddf9100038c556a6a4e760a6b0dc --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/power_user_cmd_test.go @@ -0,0 +1,106 @@ +package cli + +import ( + "strings" + "testing" +) + +func TestPowerUserCmdFlags(t *testing.T) { + secretsFixture := getFixtureImage(t, "image-secrets") + tests := []struct { + name string + args []string + env map[string]string + assertions []traitAssertion + }{ + { + name: "no-args-shows-help", + args: []string{"power-user"}, + assertions: []traitAssertion{ + assertInOutput("an image/directory argument is required"), // specific error that should be shown + assertInOutput("Run bulk operations on container images"), // excerpt from help description + assertFailingReturnCode, + }, + }, + { + name: "default-results-w-pkg-coverage", + args: []string{"power-user", "docker-archive:" + getFixtureImage(t, "image-pkg-coverage")}, + assertions: []traitAssertion{ + assertNotInOutput(" command is deprecated"), // only the root command should be deprecated + assertInOutput(`"type": "RegularFile"`), // proof of file-metadata data + assertInOutput(`"algorithm": "sha256"`), // proof of file-metadata default digest algorithm of sha256 + assertInOutput(`"metadataType": "ApkMetadata"`), // proof of package artifacts data + assertSuccessfulReturnCode, + }, + }, + { + name: "content-cataloger-wired-up", + args: []string{"power-user", "docker-archive:" + secretsFixture}, + env: map[string]string{ + "SYFT_FILE_CONTENTS_GLOBS": "/api-key.txt", + }, + assertions: []traitAssertion{ + assertInOutput(`"contents": "c29tZV9BcEkta0V5ID0gIjEyMzQ1QTdhOTAxYjM0NTY3ODkwMTIzNDU2Nzg5MDEyMzQ1Njc4OTAxMjM0NTY3ODkwMTIzNDU2Nzg5MCIK"`), // proof of the content cataloger + assertSuccessfulReturnCode, + }, + }, + { + name: "default-dir-results-w-pkg-coverage", + args: []string{"power-user", "dir:test-fixtures/image-pkg-coverage"}, + assertions: []traitAssertion{ + assertNotInOutput(" command is deprecated"), // only the root command should be deprecated + assertInOutput(`"type": "RegularFile"`), // proof of file-metadata data + assertInOutput(`"algorithm": "sha256"`), // proof of file-metadata default digest algorithm of sha256 + assertInOutput(`"metadataType": "ApkMetadata"`), // proof of package artifacts data + assertSuccessfulReturnCode, + }, + }, + { + name: "default-secrets-results-w-reveal-values", + env: map[string]string{ + "SYFT_SECRETS_REVEAL_VALUES": "true", + }, + args: []string{"power-user", "docker-archive:" + secretsFixture}, + assertions: []traitAssertion{ + assertInOutput(`"classification": "generic-api-key"`), // proof of the secrets cataloger finding something + assertInOutput(`"12345A7a901b345678901234567890123456789012345678901234567890"`), // proof of the secrets cataloger finding the api key + assertSuccessfulReturnCode, + }, + }, + { + name: "default-secret-results-dont-reveal-values", + args: []string{"power-user", "docker-archive:" + secretsFixture}, + assertions: []traitAssertion{ + assertInOutput(`"classification": "generic-api-key"`), // proof of the secrets cataloger finding something + assertNotInOutput(`"12345A7a901b345678901234567890123456789012345678901234567890"`), // proof of the secrets cataloger finding the api key + assertSuccessfulReturnCode, + }, + }, + { + name: "default-secrets-dir-results-w-reveal-values", + env: map[string]string{ + "SYFT_SECRETS_REVEAL_VALUES": "true", + }, + args: []string{"power-user", "dir:test-fixtures/image-secrets-dir"}, + assertions: []traitAssertion{ + assertInOutput(`"classification": "generic-api-key"`), // proof of the secrets cataloger finding something + assertInOutput(`"12345A7a901b345678901234567890123456789012345678901234567890"`), // proof of the secrets cataloger finding the api key + assertSuccessfulReturnCode, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + cmd, stdout, stderr := runSyftSafe(t, test.env, test.args...) + for _, traitFn := range test.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/root_cmd_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/root_cmd_test.go new file mode 100644 index 0000000000000000000000000000000000000000..468fc927c2cefb74608377a13101cf9873efd107 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/root_cmd_test.go @@ -0,0 +1,161 @@ +package cli + +import ( + "os" + "path/filepath" + "strings" + "testing" + + "github.com/sergi/go-diff/diffmatchpatch" + "github.com/stretchr/testify/assert" +) + +func TestRootCmdAliasesToPackagesSubcommand(t *testing.T) { + request := "docker-archive:" + getFixtureImage(t, "image-pkg-coverage") + + tests := []struct { + name string + env map[string]string + assertions []traitAssertion + }{ + { + name: "go-case", + assertions: []traitAssertion{ + assertTableReport, + assertSuccessfulReturnCode, + }, + }, + { + name: "respond-to-output-binding", + env: map[string]string{ + "SYFT_OUTPUT": "text", + }, + assertions: []traitAssertion{ + assertInOutput("[Image]"), + assertSuccessfulReturnCode, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + aliasCmd, aliasStdout, aliasStderr := runSyft(t, test.env, request) + for _, traitFn := range test.assertions { + traitFn(t, aliasStdout, aliasStderr, aliasCmd.ProcessState.ExitCode()) + } + + pkgCmd, pkgsStdout, pkgsStderr := runSyft(t, test.env, "packages", request) + for _, traitFn := range test.assertions { + traitFn(t, pkgsStdout, pkgsStderr, pkgCmd.ProcessState.ExitCode()) + } + + if aliasStdout != pkgsStdout { + t.Errorf("packages and root command should have same report output but do not!") + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(aliasStdout, pkgsStdout, true) + t.Error(dmp.DiffPrettyText(diffs)) + } + }) + } +} + +func TestPersistentFlags(t *testing.T) { + request := "docker-archive:" + getFixtureImage(t, "image-pkg-coverage") + + tests := []struct { + name string + args []string + env map[string]string + assertions []traitAssertion + }{ + { + name: "quiet-flag", + // note: the root command will always show the deprecation warning, so the packages command is used instead + args: []string{"packages", "-q", request}, + assertions: []traitAssertion{ + func(tb testing.TB, stdout, stderr string, rc int) { + // ensure there is no status + if len(stderr) != 0 { + tb.Errorf("should have seen no stderr output, got %d bytes", len(stderr)) + } + // ensure there is still a report + if len(stdout) == 0 { + tb.Errorf("should have seen a report on stdout, got nothing") + } + }, + }, + }, + { + name: "info-log-flag", + args: []string{"-v", request}, + assertions: []traitAssertion{ + assertLoggingLevel("info"), + assertSuccessfulReturnCode, + }, + }, + { + name: "debug-log-flag", + args: []string{"-vv", request}, + assertions: []traitAssertion{ + assertLoggingLevel("debug"), + assertSuccessfulReturnCode, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + cmd, stdout, stderr := runSyft(t, test.env, test.args...) + for _, traitFn := range test.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + }) + } +} + +func TestLogFile(t *testing.T) { + request := "docker-archive:" + getFixtureImage(t, "image-pkg-coverage") + + envLogFile := filepath.Join(os.TempDir(), "a-pretty-log-file.log") + tests := []struct { + name string + args []string + env map[string]string + assertions []traitAssertion + cleanup func() + }{ + { + name: "env-var-log-file-name", + args: []string{"-vv", request}, + env: map[string]string{"SYFT_LOG_FILE": envLogFile}, + assertions: []traitAssertion{ + func(tb testing.TB, stdout, stderr string, rc int) { + tb.Helper() + _, err := os.Stat(envLogFile) + assert.NoError(t, err) + }, + }, + cleanup: func() { assert.NoError(t, os.Remove(envLogFile)) }, + }, + } + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + t.Cleanup(test.cleanup) + + cmd, stdout, stderr := runSyft(t, test.env, test.args...) + for _, traitFn := range test.assertions { + traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode()) + } + if t.Failed() { + t.Log("STDOUT:\n", stdout) + t.Log("STDERR:\n", stderr) + t.Log("COMMAND:", strings.Join(cmd.Args, " ")) + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/spdx_json_schema_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/spdx_json_schema_test.go new file mode 100644 index 0000000000000000000000000000000000000000..f9d036c0518bd6a98ff34410aa8f193ac73aa2d1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/spdx_json_schema_test.go @@ -0,0 +1,90 @@ +package cli + +import ( + "fmt" + "path" + "strings" + "testing" + + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/xeipuuv/gojsonschema" +) + +// this is the path to the json schema directory relative to the root of the repo +const spdxJsonSchemaPath = "schema/spdx-json" + +func TestSPDXJSONSchema(t *testing.T) { + + imageFixture := func(t *testing.T) string { + fixtureImageName := "image-pkg-coverage" + imagetest.GetFixtureImage(t, "docker-archive", fixtureImageName) + tarPath := imagetest.GetFixtureImageTarPath(t, fixtureImageName) + return "docker-archive:" + tarPath + } + + tests := []struct { + name string + subcommand string + args []string + fixture func(*testing.T) string + }{ + { + name: "packages:image:docker-archive:pkg-coverage", + subcommand: "packages", + args: []string{"-o", "spdx-json"}, + fixture: imageFixture, + }, + { + name: "power-user:image:docker-archive:pkg-coverage", + subcommand: "power-user", + fixture: imageFixture, + }, + { + name: "packages:dir:pkg-coverage", + subcommand: "packages", + args: []string{"-o", "spdx-json"}, + fixture: func(t *testing.T) string { + return "dir:test-fixtures/image-pkg-coverage" + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + fixtureRef := test.fixture(t) + args := []string{ + test.subcommand, fixtureRef, "-q", + } + for _, a := range test.args { + args = append(args, a) + } + + _, stdout, _ := runSyft(t, nil, args...) + + if len(strings.Trim(stdout, "\n ")) < 100 { + t.Fatalf("bad syft output: %q", stdout) + } + + validateSpdxJsonAgainstSchema(t, stdout) + }) + } +} + +func validateSpdxJsonAgainstSchema(t testing.TB, json string) { + fullSchemaPath := path.Join(repoRoot(t), spdxJsonSchemaPath, fmt.Sprintf("spdx-schema-2.2.json")) + schemaLoader := gojsonschema.NewReferenceLoader(fmt.Sprintf("file://%s", fullSchemaPath)) + documentLoader := gojsonschema.NewStringLoader(json) + + result, err := gojsonschema.Validate(schemaLoader, documentLoader) + if err != nil { + t.Fatal("unable to validate json schema:", err.Error()) + } + + if !result.Valid() { + t.Errorf("failed json schema validation:") + t.Errorf("JSON:\n%s\n", json) + for _, desc := range result.Errors() { + t.Errorf(" - %s\n", desc) + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/Dockerfile.ctfe_init b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/Dockerfile.ctfe_init new file mode 100644 index 0000000000000000000000000000000000000000..5b131e03bfeb12145b11ca5a2dd5bc1431b49dae --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/Dockerfile.ctfe_init @@ -0,0 +1,10 @@ +FROM golang:1.17.8@sha256:c7c94588b6445f5254fbc34df941afa10de04706deb330e62831740c9f0f2030 AS builder + +WORKDIR /root/ + +RUN go install github.com/google/trillian/cmd/createtree@v1.3.10 +ADD ./config/logid.sh /root/ +ADD ./config/ctfe /root/ctfe +RUN chmod +x /root/logid.sh + +CMD /root/logid.sh diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/config.json b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/config.json new file mode 100644 index 0000000000000000000000000000000000000000..92ef253623f657135762d9f9b6e3f55d6c1b81ba --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/config.json @@ -0,0 +1,9 @@ +{ + "OIDCIssuers": { + "http://dex-idp:8888/auth": { + "IssuerURL": "http://dex-idp:8888/auth", + "ClientID": "fulcio", + "Type": "email" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/ct_server.cfg b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/ct_server.cfg new file mode 100644 index 0000000000000000000000000000000000000000..7ef4ebae06fa91176d726df3e426fd9f5fd6beb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/ct_server.cfg @@ -0,0 +1,11 @@ +config { + log_id: %LOGID% + prefix: "test" + roots_pem_file: "/etc/config/root.pem" + private_key: { + [type.googleapis.com/keyspb.PEMKeyFile] { + path: "/etc/config/privkey.pem" + password: "foobar" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/privkey.pem b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/privkey.pem new file mode 100644 index 0000000000000000000000000000000000000000..64b1950a5baffe827c4c27ed50e4fa4057fc1c75 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/privkey.pem @@ -0,0 +1,8 @@ +-----BEGIN EC PRIVATE KEY----- +Proc-Type: 4,ENCRYPTED +DEK-Info: DES-CBC,05BAAA9143C46320 + +AttbquLclNy7ZEnlDFpReZvV2PZKuv89YMWqDvGGtnBVw+3eXYIa54Xli1CyXEPn +qNGvibjIxj+Q19+VhA3n42SE2fHyULHKPZHebSL5qcVvZTqmbtAe/dZNH1SiGG2f +bWauIw0oeHhXW5i9isxrLggPMRmPA65Ii3W7gyWFmjE= +-----END EC PRIVATE KEY----- diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/pubkey.pem b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/pubkey.pem new file mode 100644 index 0000000000000000000000000000000000000000..8a3e7b56c956454f34b0247e38455ed789dd6c2d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/ctfe/pubkey.pem @@ -0,0 +1,4 @@ +-----BEGIN PUBLIC KEY----- +MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEbbQiLx6GKy6ivhc11wJGbQjc2VX/ +mnuk5d670MTXR3p+LIAcxd5MhqIHpLmyYJ5mDKLEoZ/pC0nPuje3JueBcA== +-----END PUBLIC KEY----- diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/dex/docker-compose-config.yaml b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/dex/docker-compose-config.yaml new file mode 100644 index 0000000000000000000000000000000000000000..e04402909fbc46f829e95e9d826ed5bd39e30b1d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/dex/docker-compose-config.yaml @@ -0,0 +1,48 @@ +# +# Copyright 2021 The Sigstore Authors. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +issuer: http://dex-idp:8888/auth + +storage: + type: memory + +web: + http: dex-idp:8888 + +frontend: + issuer: Fulcio in Docker Compose + +expiry: + signingKeys: "24h" + idTokens: "1m" + authRequests: "24h" + +oauth2: + responseTypes: [ "code" ] + alwaysShowLoginScreen: false + skipApprovalScreen: true + +connectors: +- type: mockCallback + id: approved + name: AlwaysApprovesOIDCProvider + +staticClients: + - id: fulcio + public: true + name: 'Fulcio in Docker Compose' + +# Dex's issuer URL + "/callback" +redirectURI: http://dex-idp:8888/auth/callback diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/logid.sh b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/logid.sh new file mode 100644 index 0000000000000000000000000000000000000000..1e54f40f4de64d4fe89f49d23bc6fcf1063bbe83 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/config/logid.sh @@ -0,0 +1,54 @@ +#!/bin/bash +# +# Copyright 2021 The Sigstore Authors. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + + +function get_log_id() { + curl -s --retry-connrefused --retry 10 http://trillian-log-server:8095/metrics |grep "^quota_acquired_tokens{spec=\"trees"|head -1|awk ' { print $1 } '|sed -e 's/[^0-9]*//g' > /tmp/logid +} + +function get_ephemeral_ca() { + curl -s --retry-connrefused --retry 10 http://fulcio-server:5555/api/v1/rootCert > /etc/config/root.pem +} + +function create_log () { + /go/bin/createtree -admin_server trillian-log-server:8096 > /tmp/logid + echo -n "Created log ID " && cat /tmp/logid +} + +function update_config() { + cat /root/ctfe/ct_server.cfg | sed -e "s/%LOGID%/"`cat /tmp/logid`"/g" > /etc/config/ct_server.cfg + cp /root/ctfe/*.pem /etc/config/ +} + +# check to see if log id exists; if so, use that +echo -n "Checking for existing configuration..." +echo "Checking for preexisting logs..." +get_log_id +# else create one +if ! [[ -s /tmp/logid ]]; then + echo "No log found; let's create one..." + create_log +fi +echo "Updating config with current log" +update_config + +configid=`cat /etc/config/ct_server.cfg|grep log_id|awk ' { print $2 } '` +echo "Exisiting configuration uses log ID $configid, exiting" + +echo "Grabing fulcio root pem file" +get_ephemeral_ca + +echo "Finished ct_server configuration" diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/docker-compose-config.yaml b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/docker-compose-config.yaml new file mode 100644 index 0000000000000000000000000000000000000000..f0e01b5668d9f5406e3d2d43cb6df39237c88491 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/docker-compose-config.yaml @@ -0,0 +1,48 @@ +# +# Copyright 2021 The Sigstore Authors. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +issuer: http://dex-idp:8888/auth + +storage: + type: memory + +web: + http: 0.0.0.0:8888 + +frontend: + issuer: Fulcio in Docker Compose + +expiry: + signingKeys: "24h" + idTokens: "1m" + authRequests: "24h" + +oauth2: + responseTypes: [ "code" ] + alwaysShowLoginScreen: true + skipApprovalScreen: true + +connectors: +- type: mockCallback + id: https://any.valid.url/ + name: AlwaysApprovesOIDCProvider + +staticClients: + - id: fulcio + public: true + name: 'Fulcio in Docker Compose' + +# Dex's issuer URL + "/callback" +redirectURI: http://dex-idp:8888/auth/callback diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/docker-compose.yaml b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/docker-compose.yaml new file mode 100644 index 0000000000000000000000000000000000000000..fa2b8da4d78dd730612fb520c1da7a85afa0e903 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/attestation/docker-compose.yaml @@ -0,0 +1,116 @@ +version: '3.2' +services: + fulcio-server: + image: fulcio_fulcio-server + command: [ + "fulcio-server", + "serve", + "--host=0.0.0.0", + "--port=5555", + "--ca=ephemeralca", + "--ct-log-url=http://ct_server:6962/test", + ] + restart: always # keep the server running + ports: + - "5555:5555" + volumes: + - ./config/config.json:/etc/fulcio-config/config.json:z + healthcheck: + test: ["CMD", "curl", "-f", "http://localhost:5555/ping"] + interval: 10s + timeout: 3s + retries: 3 + start_period: 5s + depends_on: + - dex-idp + mysql: + image: gcr.io/trillian-opensource-ci/db_server:3c8193ebb2d7fedb44d18e9c810d0d2e4dbb7e4d + environment: + - MYSQL_ROOT_PASSWORD=password + - MYSQL_DATABASE=test + - MYSQL_USER=test + - MYSQL_PASSWORD=password + restart: always # keep the MySQL server running + healthcheck: + test: ["CMD", "/etc/init.d/mysql", "status"] + interval: 30s + timeout: 3s + retries: 3 + start_period: 10s + ctfe_init: + build: + context: . + dockerfile: Dockerfile.ctfe_init + depends_on: + - trillian-log-server + - fulcio-server + volumes: + - ctfeConfig:/etc/config/:rw + ct_server: + image: gcr.io/trillian-opensource-ci/ctfe + volumes: + - ctfeConfig:/etc/config/:rw + command: [ + "--log_config" ,"/etc/config/ct_server.cfg", + "--log_rpc_server", "trillian-log-server:8096", + "--http_endpoint", "0.0.0.0:6962", + "--alsologtostderr", + ] + restart: always # retry while ctfe_init is running + depends_on: + - trillian-log-server + - trillian-log-signer + - ctfe_init + ports: + - "6962:6962" + dex-idp: + image: dexidp/dex:v2.30.0 + user: root + command: [ + "dex", + "serve", + "/etc/config/docker-compose-config.yaml", + ] + restart: always # keep the server running + ports: + - "8888:8888" + volumes: + - ./config/dex:/etc/config/:ro + healthcheck: + test: ["CMD", "curl", "-f", "http://localhost:8888/auth/healthz"] + interval: 10s + timeout: 3s + retries: 3 + start_period: 5s + trillian-log-server: + image: gcr.io/trillian-opensource-ci/log_server + command: [ + "--storage_system=mysql", + "--mysql_uri=test:password@tcp(mysql:3306)/test", + "--rpc_endpoint=0.0.0.0:8096", + "--http_endpoint=0.0.0.0:8095", + "--alsologtostderr", + ] + restart: always # retry while mysql is starting up + ports: + - "8096:8096" + - "8095:8095" + depends_on: + - mysql + trillian-log-signer: + image: gcr.io/trillian-opensource-ci/log_signer + command: [ + "--storage_system=mysql", + "--mysql_uri=test:password@tcp(mysql:3306)/test", + "--rpc_endpoint=0.0.0.0:8095", + "--http_endpoint=0.0.0.0:8097", + "--force_master", + "--alsologtostderr", + ] + restart: always # retry while mysql is starting up + ports: + - "8097:8097" + depends_on: + - mysql +volumes: + ctfeConfig: {} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/csv.template b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/csv.template new file mode 100644 index 0000000000000000000000000000000000000000..8474271adb2946bce1063fa37ca4d440df2a8fa6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/csv.template @@ -0,0 +1,4 @@ +"Package","Version Installed", "Found by" +{{- range .Artifacts}} +"{{.Name}}","{{.Version}}","{{.FoundBy}}" +{{- end}} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-bad-binaries/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-bad-binaries/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..7851a945b41a76776b867fbce1b631ee41242e87 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-bad-binaries/Dockerfile @@ -0,0 +1,5 @@ +FROM debian:sid +ADD sources.list /etc/apt/sources.list.d/sources.list +RUN apt update -y && apt install -y dpkg-dev +# this as a "macho-invalid" directory which is useful for testing +RUN apt-get source -y clang-13 diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-bad-binaries/sources.list b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-bad-binaries/sources.list new file mode 100644 index 0000000000000000000000000000000000000000..65c201e37b0302fcbe4ccaf330d6d644a318671c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-bad-binaries/sources.list @@ -0,0 +1 @@ +deb-src http://deb.debian.org/debian sid main diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-hidden-packages/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-hidden-packages/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..cf8ea3bfa0e3aa68edef01c6afe7df0384c76219 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-hidden-packages/Dockerfile @@ -0,0 +1,4 @@ +FROM centos:7.9.2009 +# all-layers scope should pickup on vsftpd +RUN yum install -y vsftpd +RUN yum remove -y vsftpd \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-pkg-coverage b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-pkg-coverage new file mode 120000 index 0000000000000000000000000000000000000000..155332274bcc7afad40e4e65d0382ef68752eda3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-pkg-coverage @@ -0,0 +1 @@ +../../integration/test-fixtures/image-pkg-coverage \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets-dir/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets-dir/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..28a283a0bb36595738503dac1ba5dceeac81c2c3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets-dir/Dockerfile @@ -0,0 +1,2 @@ +FROM scratch +ADD api-key.txt . \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets-dir/api-key.txt b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets-dir/api-key.txt new file mode 100644 index 0000000000000000000000000000000000000000..6cbbd99e3e8a08cf6ccfd65b7905de7e27fe1c78 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets-dir/api-key.txt @@ -0,0 +1 @@ +some_ApI-kEy = "12345A7a901b345678901234567890123456789012345678901234567890" diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..28a283a0bb36595738503dac1ba5dceeac81c2c3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets/Dockerfile @@ -0,0 +1,2 @@ +FROM scratch +ADD api-key.txt . \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets/api-key.txt b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets/api-key.txt new file mode 100644 index 0000000000000000000000000000000000000000..6cbbd99e3e8a08cf6ccfd65b7905de7e27fe1c78 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/image-secrets/api-key.txt @@ -0,0 +1 @@ +some_ApI-kEy = "12345A7a901b345678901234567890123456789012345678901234567890" diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/.dockerignore b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/.dockerignore new file mode 100644 index 0000000000000000000000000000000000000000..91224e5de82917e9ddd2a315abc9d70c5d07b711 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/.dockerignore @@ -0,0 +1 @@ +**/* diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..b09b037ca229e61329248e89bc2f9d8c4dc77b79 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/Dockerfile @@ -0,0 +1 @@ +FROM alpine:latest diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/Makefile b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..4a55e2aaa9890d7ff1885bd8a82f539eb0ab7fcd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/test-fixtures/registry/Makefile @@ -0,0 +1,23 @@ +all: build start + +.PHONY: stop +stop: + docker kill registry + +.PHONY: build +build: + docker build -t localhost:5000/attest:latest . + +.PHONY: start +start: + docker run --rm \ + -d \ + --name registry \ + -it \ + --privileged \ + -p 5000:5000 \ + registry:2.8 + +.PHONY: push +push: + docker push localhost:5000/attest:latest diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/trait_assertions_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/trait_assertions_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d14dfca739ee938adf73bc8c8e0d664376d033ab --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/trait_assertions_test.go @@ -0,0 +1,184 @@ +package cli + +import ( + "encoding/json" + "os" + "os/exec" + "path/filepath" + "regexp" + "strings" + "testing" + + "github.com/acarl005/stripansi" + "github.com/stretchr/testify/require" +) + +type traitAssertion func(tb testing.TB, stdout, stderr string, rc int) + +func assertFileOutput(tb testing.TB, path string, assertions ...traitAssertion) traitAssertion { + tb.Helper() + + return func(tb testing.TB, _, stderr string, rc int) { + content, err := os.ReadFile(path) + require.NoError(tb, err) + contentStr := string(content) + + for _, assertion := range assertions { + // treat the file content as stdout + assertion(tb, contentStr, stderr, rc) + } + } +} + +func assertJsonReport(tb testing.TB, stdout, _ string, _ int) { + tb.Helper() + var data interface{} + + if err := json.Unmarshal([]byte(stdout), &data); err != nil { + tb.Errorf("expected to find a JSON report, but was unmarshalable: %+v", err) + } +} + +func assertTableReport(tb testing.TB, stdout, _ string, _ int) { + tb.Helper() + if !strings.Contains(stdout, "NAME") || !strings.Contains(stdout, "VERSION") || !strings.Contains(stdout, "TYPE") { + tb.Errorf("expected to find a table report, but did not") + } +} + +//func assertScope(scope source.Scope) traitAssertion { +// return func(tb testing.TB, stdout, stderr string, rc int) { +// tb.Helper() +// // we can only verify source with the json report +// assertJsonReport(tb, stdout, stderr, rc) +// +// if !strings.Contains(stdout, fmt.Sprintf(`"scope": "%s"`, scope.String())) { +// tb.Errorf("JSON report did not indicate the %q scope", scope) +// } +// } +//} + +func assertLoggingLevel(level string) traitAssertion { + // match examples: + // "[0000] INFO" + // "[0012] DEBUG" + logPattern := regexp.MustCompile(`(?m)^\[\d\d\d\d\]\s+` + strings.ToUpper(level)) + return func(tb testing.TB, _, stderr string, _ int) { + tb.Helper() + if !logPattern.MatchString(stripansi.Strip(stderr)) { + tb.Errorf("output did not indicate the %q logging level", level) + } + } +} + +func assertNotInOutput(data string) traitAssertion { + return func(tb testing.TB, stdout, stderr string, _ int) { + tb.Helper() + if strings.Contains(stripansi.Strip(stderr), data) { + tb.Errorf("data=%q was found in stderr, but should not have been there", data) + } + if strings.Contains(stripansi.Strip(stdout), data) { + tb.Errorf("data=%q was found in stdout, but should not have been there", data) + } + } +} + +func assertInOutput(data string) traitAssertion { + return func(tb testing.TB, stdout, stderr string, _ int) { + tb.Helper() + if !strings.Contains(stripansi.Strip(stderr), data) && !strings.Contains(stripansi.Strip(stdout), data) { + tb.Errorf("data=%q was NOT found in any output, but should have been there", data) + } + } +} + +func assertStdoutLengthGreaterThan(length uint) traitAssertion { + return func(tb testing.TB, stdout, _ string, _ int) { + tb.Helper() + if uint(len(stdout)) < length { + tb.Errorf("not enough output (expected at least %d, got %d)", length, len(stdout)) + } + } +} + +func assertPackageCount(length uint) traitAssertion { + return func(tb testing.TB, stdout, _ string, _ int) { + tb.Helper() + type partial struct { + Artifacts []interface{} `json:"artifacts"` + } + var data partial + + if err := json.Unmarshal([]byte(stdout), &data); err != nil { + tb.Errorf("expected to find a JSON report, but was unmarshalable: %+v", err) + } + + if uint(len(data.Artifacts)) != length { + tb.Errorf("expected package count of %d, but found %d", length, len(data.Artifacts)) + + } + } +} + +func assertFailingReturnCode(tb testing.TB, _, _ string, rc int) { + tb.Helper() + if rc == 0 { + tb.Errorf("expected a failure but got rc=%d", rc) + } +} + +func assertSuccessfulReturnCode(tb testing.TB, _, _ string, rc int) { + tb.Helper() + if rc != 0 { + tb.Errorf("expected no failure but got rc=%d", rc) + } +} + +func assertVerifyAttestation(coverageImage string) traitAssertion { + return func(tb testing.TB, stdout, _ string, _ int) { + tb.Helper() + cosignPath := filepath.Join(repoRoot(tb), ".tmp/cosign") + err := os.WriteFile("attestation.json", []byte(stdout), 0664) + if err != nil { + tb.Errorf("could not write attestation to disk") + } + defer os.Remove("attestation.json") + attachCmd := exec.Command( + cosignPath, + "attach", + "attestation", + "--attestation", + "attestation.json", + coverageImage, // TODO which remote image to use? + ) + + stdout, stderr, _ := runCommand(attachCmd, nil) + if attachCmd.ProcessState.ExitCode() != 0 { + tb.Log("STDOUT", stdout) + tb.Log("STDERR", stderr) + tb.Fatalf("could not attach image") + } + + verifyCmd := exec.Command( + cosignPath, + "verify-attestation", + coverageImage, // TODO which remote image to use? + ) + + stdout, stderr, _ = runCommand(verifyCmd, nil) + if attachCmd.ProcessState.ExitCode() != 0 { + tb.Log("STDOUT", stdout) + tb.Log("STDERR", stderr) + tb.Fatalf("could not verify attestation") + } + } +} + +func assertFileExists(file string) traitAssertion { + return func(tb testing.TB, _, _ string, _ int) { + tb.Helper() + if _, err := os.Stat(file); err != nil { + tb.Errorf("expected file to exist %s", file) + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/cli/utils_test.go b/ci/tools/openeuler-purl/syft-dev/test/cli/utils_test.go new file mode 100644 index 0000000000000000000000000000000000000000..5751dea66b5da272f59a53c93f5ed1a22c568f02 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/cli/utils_test.go @@ -0,0 +1,289 @@ +package cli + +import ( + "bytes" + "fmt" + "math" + "os" + "os/exec" + "path" + "path/filepath" + "runtime" + "strings" + "syscall" + "testing" + "time" + + "github.com/anchore/stereoscope/pkg/imagetest" +) + +func setupPKI(t *testing.T, pw string) func() { + err := os.Setenv("COSIGN_PASSWORD", pw) + if err != nil { + t.Fatal(err) + } + + cosignPath := filepath.Join(repoRoot(t), ".tmp/cosign") + cmd := exec.Command(cosignPath, "generate-key-pair") + stdout, stderr, _ := runCommand(cmd, nil) + if cmd.ProcessState.ExitCode() != 0 { + t.Log("STDOUT", stdout) + t.Log("STDERR", stderr) + t.Fatalf("could not generate keypair") + } + + return func() { + err := os.Unsetenv("COSIGN_PASSWORD") + if err != nil { + t.Fatal(err) + } + + err = os.Remove("cosign.key") + if err != nil { + t.Fatalf("could not cleanup cosign.key") + } + + err = os.Remove("cosign.pub") + if err != nil { + t.Fatalf("could not cleanup cosign.key") + } + } +} + +func getFixtureImage(t testing.TB, fixtureImageName string) string { + t.Logf("obtaining fixture image for %s", fixtureImageName) + imagetest.GetFixtureImage(t, "docker-archive", fixtureImageName) + return imagetest.GetFixtureImageTarPath(t, fixtureImageName) +} + +func pullDockerImage(t testing.TB, image string) { + cmd := exec.Command("docker", "pull", image) + stdout, stderr, _ := runCommand(cmd, nil) + if cmd.ProcessState.ExitCode() != 0 { + t.Log("STDOUT", stdout) + t.Log("STDERR", stderr) + t.Fatalf("could not pull docker image") + } +} + +// docker run -v $(pwd)/sbom:/sbom cyclonedx/cyclonedx-cli:latest validate --input-format json --input-version v1_4 --input-file /sbom +func runCycloneDXInDocker(t testing.TB, env map[string]string, image string, f *os.File, args ...string) (*exec.Cmd, string, string) { + allArgs := append( + []string{ + "run", + "-t", + "-v", + fmt.Sprintf("%s:/sbom", f.Name()), + image, + }, + args..., + ) + cmd := exec.Command("docker", allArgs...) + stdout, stderr, _ := runCommand(cmd, env) + return cmd, stdout, stderr +} + +func runSyftInDocker(t testing.TB, env map[string]string, image string, args ...string) (*exec.Cmd, string, string) { + allArgs := append( + []string{ + "run", + "-t", + "-e", + "SYFT_CHECK_FOR_APP_UPDATE=false", + "-v", + fmt.Sprintf("%s:/syft", getSyftBinaryLocationByOS(t, "linux")), + image, + "/syft", + }, + args..., + ) + cmd := exec.Command("docker", allArgs...) + stdout, stderr, _ := runCommand(cmd, env) + return cmd, stdout, stderr +} + +func runSyft(t testing.TB, env map[string]string, args ...string) (*exec.Cmd, string, string) { + return runSyftCommand(t, env, true, args...) +} + +func runSyftSafe(t testing.TB, env map[string]string, args ...string) (*exec.Cmd, string, string) { + return runSyftCommand(t, env, false, args...) +} + +func runSyftCommand(t testing.TB, env map[string]string, expectError bool, args ...string) (*exec.Cmd, string, string) { + cancel := make(chan bool, 1) + defer func() { + cancel <- true + }() + + cmd := getSyftCommand(t, args...) + if env == nil { + env = make(map[string]string) + } + + // we should not have tests reaching out for app update checks + env["SYFT_CHECK_FOR_APP_UPDATE"] = "false" + + timeout := func() { + select { + case <-cancel: + return + case <-time.After(60 * time.Second): + } + + if cmd != nil && cmd.Process != nil { + // get a stack trace printed + err := cmd.Process.Signal(syscall.SIGABRT) + if err != nil { + t.Errorf("error aborting: %+v", err) + } + } + } + + go timeout() + + stdout, stderr, err := runCommand(cmd, env) + + if !expectError && err != nil && stdout == "" { + t.Errorf("error running syft: %+v", err) + t.Errorf("STDOUT: %s", stdout) + t.Errorf("STDERR: %s", stderr) + + // this probably indicates a timeout + args = append(args, "-vv") + cmd = getSyftCommand(t, args...) + + go timeout() + stdout, stderr, err = runCommand(cmd, env) + + if err != nil { + t.Errorf("error rerunning syft: %+v", err) + t.Errorf("STDOUT: %s", stdout) + t.Errorf("STDERR: %s", stderr) + } + } + + return cmd, stdout, stderr +} + +func runCosign(t testing.TB, env map[string]string, args ...string) (*exec.Cmd, string, string) { + cmd := getCommand(t, ".tmp/cosign", args...) + if env == nil { + env = make(map[string]string) + } + + stdout, stderr, err := runCommand(cmd, env) + + if err != nil { + t.Errorf("error running cosign: %+v", err) + } + + return cmd, stdout, stderr +} + +func getCommand(t testing.TB, location string, args ...string) *exec.Cmd { + return exec.Command(filepath.Join(repoRoot(t), location), args...) +} + +func runCommand(cmd *exec.Cmd, env map[string]string) (string, string, error) { + if env != nil { + cmd.Env = append(os.Environ(), envMapToSlice(env)...) + } + var stdout, stderr bytes.Buffer + cmd.Stdout = &stdout + cmd.Stderr = &stderr + + // ignore errors since this may be what the test expects + err := cmd.Run() + + return stdout.String(), stderr.String(), err +} + +func envMapToSlice(env map[string]string) (envList []string) { + for key, val := range env { + if key == "" { + continue + } + envList = append(envList, fmt.Sprintf("%s=%s", key, val)) + } + return +} + +func getSyftCommand(t testing.TB, args ...string) *exec.Cmd { + return exec.Command(getSyftBinaryLocation(t), args...) +} + +func getSyftBinaryLocation(t testing.TB) string { + if os.Getenv("SYFT_BINARY_LOCATION") != "" { + // SYFT_BINARY_LOCATION is the absolute path to the snapshot binary + return os.Getenv("SYFT_BINARY_LOCATION") + } + return getSyftBinaryLocationByOS(t, runtime.GOOS) +} + +func getSyftBinaryLocationByOS(t testing.TB, goOS string) string { + // note: for amd64 we need to update the snapshot location with the v1 suffix + // see : https://goreleaser.com/customization/build/#why-is-there-a-_v1-suffix-on-amd64-builds + archPath := runtime.GOARCH + if runtime.GOARCH == "amd64" { + archPath = fmt.Sprintf("%s_v1", archPath) + } + // note: there is a subtle - vs _ difference between these versions + switch goOS { + case "darwin", "linux": + return path.Join(repoRoot(t), fmt.Sprintf("snapshot/%s-build_%s_%s/syft", goOS, goOS, archPath)) + default: + t.Fatalf("unsupported OS: %s", runtime.GOOS) + } + return "" +} + +func repoRoot(t testing.TB) string { + t.Helper() + root, err := exec.Command("git", "rev-parse", "--show-toplevel").Output() + if err != nil { + t.Fatalf("unable to find repo root dir: %+v", err) + } + absRepoRoot, err := filepath.Abs(strings.TrimSpace(string(root))) + if err != nil { + t.Fatal("unable to get abs path to repo root:", err) + } + return absRepoRoot +} + +func testRetryIntervals(done <-chan struct{}) <-chan time.Duration { + return exponentialBackoffDurations(250*time.Millisecond, 4*time.Second, 2, done) +} + +func exponentialBackoffDurations(minDuration, maxDuration time.Duration, step float64, done <-chan struct{}) <-chan time.Duration { + sleepDurations := make(chan time.Duration) + go func() { + defer close(sleepDurations) + retryLoop: + for attempt := 0; ; attempt++ { + duration := exponentialBackoffDuration(minDuration, maxDuration, step, attempt) + + select { + case sleepDurations <- duration: + break + case <-done: + break retryLoop + } + + if duration == maxDuration { + break + } + } + }() + return sleepDurations +} + +func exponentialBackoffDuration(minDuration, maxDuration time.Duration, step float64, attempt int) time.Duration { + duration := time.Duration(float64(minDuration) * math.Pow(step, float64(attempt))) + if duration < minDuration { + return minDuration + } else if duration > maxDuration { + return maxDuration + } + return duration +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/compare/compare.py b/ci/tools/openeuler-purl/syft-dev/test/compare/compare.py new file mode 100755 index 0000000000000000000000000000000000000000..3f1bc0e71aa192a243877e4d0a09b82b259b8be9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/compare/compare.py @@ -0,0 +1,164 @@ +#!/usr/bin/env python3 +import sys +import json +import collections + +INDENT = " " + + +Metadata = collections.namedtuple("Metadata", "metadata sources") +Package = collections.namedtuple("Package", "name type version") + + +class Syft: + def __init__(self, report_path): + self.report_path = report_path + + def _enumerate_section(self, section): + with open(self.report_path) as json_file: + data = json.load(json_file) + for entry in data[section]: + yield entry + + def packages(self): + packages = set() + metadata = collections.defaultdict(dict) + for entry in self._enumerate_section(section="artifacts"): + package = Package( + name=entry["name"], type=entry["type"], version=entry["version"] + ) + + packages.add(package) + metadata[package.type][package] = Metadata( + # note: the metadata entry is optional + metadata=repr(entry.get("metadata", "")), sources=repr(entry["locations"]) + ) + return packages, metadata + + +def print_rows(rows): + if not rows: + return + widths = [] + for col, _ in enumerate(rows[0]): + width = max(len(row[col]) for row in rows) + 2 # padding + widths.append(width) + for row in rows: + print("".join(word.ljust(widths[col_idx]) for col_idx, word in enumerate(row))) + + +def main(baseline_report, new_report): + report1_obj = Syft(report_path=baseline_report) + report1_packages, report1_metadata = report1_obj.packages() + + report2_obj = Syft(report_path=new_report) + report2_packages, report2_metadata = report2_obj.packages() + + if len(report2_packages) == 0 or len(report1_packages) == 0: + # we are purposefully selecting test images that are guaranteed to have packages, so this should never happen + print(colors.bold + colors.fg.red + "no packages found!", colors.reset) + return 1 + + same_packages = report2_packages & report1_packages + percent_overlap_packages = ( + float(len(same_packages)) / float(len(report1_packages)) + ) * 100.0 + + extra_packages = report2_packages - report1_packages + missing_packages = report1_packages - report2_packages + + report1_metadata_set = set() + for package in report1_packages: + metadata = report1_metadata[package.type][package] + report1_metadata_set.add((package, metadata)) + + report2_metadata_set = set() + for package in report2_packages: + metadata = report2_metadata[package.type][package] + report2_metadata_set.add((package, metadata)) + + same_metadata = report2_metadata_set & report1_metadata_set + percent_overlap_metadata = 0 + if len(report1_metadata_set) > 0: + percent_overlap_metadata = ( + float(len(same_metadata)) / float(len(report1_metadata_set)) + ) * 100.0 + + if extra_packages: + rows = [] + print(colors.bold + "Extra packages:", colors.reset) + for package in sorted(list(extra_packages)): + rows.append([INDENT, repr(package)]) + print_rows(rows) + print() + + if missing_packages: + rows = [] + print(colors.bold + "Missing packages:", colors.reset) + for package in sorted(list(missing_packages)): + rows.append([INDENT, repr(package)]) + print_rows(rows) + print() + + print(colors.bold+"Summary:", colors.reset) + print(" Baseline Packages: %d" % len(report1_packages)) + print(" New Packages: %d" % len(report2_packages)) + print( + " Baseline Packages Matched: %.2f %% (%d/%d packages)" + % (percent_overlap_packages, len(same_packages), len(report1_packages)) + ) + print( + " Baseline Metadata Matched: %.2f %% (%d/%d metadata)" + % (percent_overlap_metadata, len(same_metadata), len(report1_metadata_set)) + ) + + if len(report1_packages) != len(report2_packages): + print(colors.bold + " Quality Gate: " + colors.fg.red + "FAILED (requires exact name & version match)\n", colors.reset) + return 1 + else: + print(colors.bold + " Quality Gate: " + colors.fg.green + "pass\n", colors.reset) + return 0 + + +class colors: + reset='\033[0m' + bold='\033[01m' + disable='\033[02m' + underline='\033[04m' + reverse='\033[07m' + strikethrough='\033[09m' + invisible='\033[08m' + class fg: + black='\033[30m' + red='\033[31m' + green='\033[32m' + orange='\033[33m' + blue='\033[34m' + purple='\033[35m' + cyan='\033[36m' + lightgrey='\033[37m' + darkgrey='\033[90m' + lightred='\033[91m' + lightgreen='\033[92m' + yellow='\033[93m' + lightblue='\033[94m' + pink='\033[95m' + lightcyan='\033[96m' + class bg: + black='\033[40m' + red='\033[41m' + green='\033[42m' + orange='\033[43m' + blue='\033[44m' + purple='\033[45m' + cyan='\033[46m' + lightgrey='\033[47m' + + +if __name__ == "__main__": + print("\nComparing two Syft reports...\n") + if len(sys.argv) != 3: + sys.exit("please provide two Syft json files") + + rc = main(sys.argv[1], sys.argv[2]) + sys.exit(rc) diff --git a/ci/tools/openeuler-purl/syft-dev/test/compare/deb.sh b/ci/tools/openeuler-purl/syft-dev/test/compare/deb.sh new file mode 100755 index 0000000000000000000000000000000000000000..46793472d353c62fcdc6edb2263045d06d3014ce --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/compare/deb.sh @@ -0,0 +1,55 @@ +#!/usr/bin/env bash +set -eux +set -o pipefail + +DISTDIR=$1 +ACC_DIR=$2 +TEST_IMAGE=$3 +RESULTSDIR=$4 + +TEST_TYPE=deb +WORK_DIR=`mktemp -d -t "syft-acceptance-test-${TEST_TYPE}-XXXXXX"` +NORMAL_TEST_IMAGE=$(echo ${TEST_IMAGE} | tr ':' '-' ) +REPORT=${WORK_DIR}/acceptance-${TEST_TYPE}-${NORMAL_TEST_IMAGE}.json +GOLDEN_REPORT=${ACC_DIR}/test-fixtures/acceptance-${NORMAL_TEST_IMAGE}.json + +# check if tmp dir was created +if [[ ! "${WORK_DIR}" || ! -d "${WORK_DIR}" ]]; then + echo "Could not create temp dir" + exit 1 +fi + +function cleanup { + # we should still preserve previous failures + exit_code=$? + rm -rf "${WORK_DIR}" + exit ${exit_code} +} + +trap cleanup EXIT + +# fetch test image +docker pull ${TEST_IMAGE} + +# install and run syft +docker run --rm \ + -v /var/run/docker.sock://var/run/docker.sock \ + -v /${PWD}:/src \ + -v ${WORK_DIR}:${WORK_DIR} \ + -e SYFT_CHECK_FOR_APP_UPDATE=0 \ + -w /src \ + ubuntu:latest \ + /bin/bash -x -c "\ + DEBIAN_FRONTEND=noninteractive apt install ${DISTDIR}/syft_*_linux_amd64.deb -y && \ + syft version && \ + syft packages ${TEST_IMAGE} -vv -o json > ${REPORT} \ + " + +# keep the generated report around +mkdir -p ${RESULTSDIR} +cp ${REPORT} ${RESULTSDIR} + +# compare the results to a known good output +${ACC_DIR}/compare.py \ + ${GOLDEN_REPORT} \ + ${REPORT} | tee ${RESULTSDIR}/acceptance-${TEST_TYPE}.txt diff --git a/ci/tools/openeuler-purl/syft-dev/test/compare/mac.sh b/ci/tools/openeuler-purl/syft-dev/test/compare/mac.sh new file mode 100755 index 0000000000000000000000000000000000000000..3aadab2e2a0e5cd68e9e6f67b1a300aead6293f2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/compare/mac.sh @@ -0,0 +1,54 @@ +#!/usr/bin/env bash +set -eux +set -o pipefail + +DISTDIR=$1 +ACC_DIR=$2 +TEST_IMAGE=$3 +RESULTSDIR=$4 + +TEST_IMAGE_TAR=image.tar +TEST_TYPE=mac +WORK_DIR=`mktemp -d -t "syft-acceptance-test-${TEST_TYPE}-XXXXXX"` +NORMAL_TEST_IMAGE=$(echo ${TEST_IMAGE} | tr ':' '-' ) +REPORT=${WORK_DIR}/acceptance-${TEST_TYPE}-${NORMAL_TEST_IMAGE}.json +GOLDEN_REPORT=${ACC_DIR}/test-fixtures/acceptance-${NORMAL_TEST_IMAGE}.json + +# check if tmp dir was created +if [[ ! "${WORK_DIR}" || ! -d "${WORK_DIR}" ]]; then + echo "Could not create temp dir" + exit 1 +fi + +function cleanup { + # we should still preserve previous failures + exit_code=$? + rm -rf "${WORK_DIR}" + exit ${exit_code} +} + +trap cleanup EXIT + +# fetch test image +if [[ -f ${TEST_IMAGE_TAR} ]] +then + echo "using existing image" +else + skopeo --version || brew install skopeo + skopeo --override-os linux copy "docker://docker.io/${TEST_IMAGE}" "docker-archive:${TEST_IMAGE_TAR}" +fi + +# run syft +SYFT_PATH="${DISTDIR}/darwin-build_darwin_amd64_v1/syft" +chmod 755 "${SYFT_PATH}" +"${SYFT_PATH}" version +SYFT_CHECK_FOR_APP_UPDATE=0 "${SYFT_PATH}" packages docker-archive:${TEST_IMAGE_TAR} -vv -o json > "${REPORT}" + +# keep the generated report around +mkdir -p ${RESULTSDIR} +cp ${REPORT} ${RESULTSDIR} + +# compare the results to a known good output +${ACC_DIR}/compare.py \ + ${GOLDEN_REPORT} \ + ${REPORT} | tee ${RESULTSDIR}/acceptance-${TEST_TYPE}.txt diff --git a/ci/tools/openeuler-purl/syft-dev/test/compare/rpm.sh b/ci/tools/openeuler-purl/syft-dev/test/compare/rpm.sh new file mode 100755 index 0000000000000000000000000000000000000000..d84ff6df19188750f55489dc11110115121a6be2 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/compare/rpm.sh @@ -0,0 +1,56 @@ +#!/usr/bin/env bash +set -eux +set -o pipefail + +DISTDIR=$1 +ACC_DIR=$2 +TEST_IMAGE=$3 +RESULTSDIR=$4 + +EXIT_CODE=1 +TEST_TYPE=rpm +WORK_DIR=`mktemp -d -t "syft-acceptance-test-${TEST_TYPE}-XXXXXX"` +NORMAL_TEST_IMAGE=$(echo ${TEST_IMAGE} | tr ':' '-' ) +REPORT=${WORK_DIR}/acceptance-${TEST_TYPE}-${NORMAL_TEST_IMAGE}.json +GOLDEN_REPORT=${ACC_DIR}/test-fixtures/acceptance-${NORMAL_TEST_IMAGE}.json + +# check if tmp dir was created +if [[ ! "${WORK_DIR}" || ! -d "${WORK_DIR}" ]]; then + echo "Could not create temp dir" + exit 1 +fi + +function cleanup { + rm -rf "${WORK_DIR}" + exit ${EXIT_CODE} +} + +trap cleanup EXIT + +# fetch test image +docker pull ${TEST_IMAGE} + +# install and run syft +docker run --rm \ + -v /var/run/docker.sock://var/run/docker.sock \ + -v /${PWD}:/src \ + -v ${WORK_DIR}:${WORK_DIR} \ + -e SYFT_CHECK_FOR_APP_UPDATE=0 \ + -w /src \ + centos:latest \ + /bin/bash -x -c "\ + rpm -ivh ${DISTDIR}/syft_*_linux_amd64.rpm && \ + syft version && \ + syft packages ${TEST_IMAGE} -vv -o json > ${REPORT} \ + " + +# keep the generated report around +mkdir -p ${RESULTSDIR} +cp ${REPORT} ${RESULTSDIR} + +# compare the results to a known good output +${ACC_DIR}/compare.py \ + ${GOLDEN_REPORT} \ + ${REPORT} | tee ${RESULTSDIR}/acceptance-${TEST_TYPE}.txt + +EXIT_CODE=0 diff --git a/ci/tools/openeuler-purl/syft-dev/test/compare/test-fixtures/acceptance-centos-8.2.2004.json b/ci/tools/openeuler-purl/syft-dev/test/compare/test-fixtures/acceptance-centos-8.2.2004.json new file mode 100644 index 0000000000000000000000000000000000000000..da8c8b86e65eb7561981a8387dd93f7ffea42284 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/compare/test-fixtures/acceptance-centos-8.2.2004.json @@ -0,0 +1 @@ +{"artifacts":[{"name":"acl","version":"2.2.53-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:acl:acl:2.2.53-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:acl:2.2.53-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/acl@0:2.2.53-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"acl","version":"2.2.53","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"acl-2.2.53-1.el8.src.rpm","size":205740,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/chacl","mode":33261,"size":17488,"sha256":"4166ad78974742bf94031a0ae6dec78422a5c4d1f385e77ca4f763f01ab4e63a"},{"path":"/usr/bin/getfacl","mode":33261,"size":28664,"sha256":"cb3a0f064d2c342e81ce7cefcf2b17a0168c4b6ac44febd97fa72dd3d0b08b58"},{"path":"/usr/bin/setfacl","mode":33261,"size":42472,"sha256":"1fd707e2de514632c687932c710eac52ed80b1279565eae376f6fd2e7c53e860"},{"path":"/usr/lib/.build-id/52/6aa76cbaf89308b25c7a2fdd6b743b9956a69a","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/57/b40394d1514816d39c8366582bac402b86cbf0","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/d7/5f66cdfce347bb0d912d2d9772b96fd477fa74","mode":41471,"size":27,"sha256":""},{"path":"/usr/share/licenses/acl/COPYING","mode":33188,"size":18311,"sha256":"a45a845012742796534f7e91fe623262ccfb99460a2bd04015bd28d66fba95b8"},{"path":"/usr/share/licenses/acl/COPYING.LGPL","mode":33188,"size":26762,"sha256":"01b1f9f2c8ee648a7a596a1abe8aa4ed7899b1c9e5551bda06da6e422b04aa55"}]}},{"name":"audit-libs","version":"3.0-0.17.20191104git1c2f876.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:audit-libs:audit-libs:3.0-0.17.20191104git1c2f876.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:audit-libs:3.0-0.17.20191104git1c2f876.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/audit-libs@0:3.0-0.17.20191104git1c2f876.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"audit-libs","version":"3.0","epoch":0,"architecture":"x86_64","release":"0.17.20191104git1c2f876.el8","sourceRpm":"audit-3.0-0.17.20191104git1c2f876.el8.src.rpm","size":283708,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/etc/libaudit.conf","mode":33184,"size":191,"sha256":"d48318c90620fde96cb6a8e6eb1eb64663b21200f9d1d053f9e3b4fce24a2543"},{"path":"/usr/lib/.build-id/c6/24ac9e2f0ab806f46f0824a99d7b276881c52a","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/f2/4c660a5b7a8ce9bd6ca2c05e3fbf801ea13e7a","mode":41471,"size":37,"sha256":""},{"path":"/usr/share/licenses/audit-libs/lgpl-2.1.txt","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"basesystem","version":"11-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:basesystem:basesystem:11-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:basesystem:11-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/basesystem@0:11-5.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"basesystem","version":"11","epoch":0,"architecture":"noarch","release":"5.el8","sourceRpm":"basesystem-11-5.el8.src.rpm","size":0,"license":"Public Domain","vendor":"CentOS","files":[]}},{"name":"bash","version":"4.4.19-10.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:bash:bash:4.4.19-10.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:bash:4.4.19-10.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/bash@0:4.4.19-10.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"bash","version":"4.4.19","epoch":0,"architecture":"x86_64","release":"10.el8","sourceRpm":"bash-4.4.19-10.el8.src.rpm","size":6930068,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/etc/skel/.bash_logout","mode":33188,"size":18,"sha256":"2584c4ba8b0d2a52d94023f420b7e356a1b1a3f2291ad5eba06683d58c48570d"},{"path":"/etc/skel/.bash_profile","mode":33188,"size":141,"sha256":"28bc81aadfd6e6639675760dc11dddd4ed1fcbd08f423224a93c09802552b87e"},{"path":"/etc/skel/.bashrc","mode":33188,"size":312,"sha256":"30a80bfce3d108d6878cf13dfb1f3a1ea15b141dbdc5bc5803f4ab40a2a39f9c"},{"path":"/usr/bin/alias","mode":33261,"size":29,"sha256":"c9e358c5012c2cf9171ec4f7692ac3a1cbc280617b610d77d813653a1d0dfeb8"},{"path":"/usr/bin/bash","mode":33261,"size":1219248,"sha256":"4613c2eb7267def2782667cbf381499535cf1c750617e117dd66ba678e3d55d0"},{"path":"/usr/bin/bashbug","mode":41471,"size":10,"sha256":""},{"path":"/usr/bin/bashbug-64","mode":33261,"size":7348,"sha256":"d237f71cc1c5c49634d83927375fafe230ba9624350ebce5aeb0fc2696764776"},{"path":"/usr/bin/bg","mode":33261,"size":26,"sha256":"6eb427fec008b7f3443dc0d3d374979fec87a7d8c27093512bc0b2d52c4e65ec"},{"path":"/usr/bin/cd","mode":33261,"size":26,"sha256":"efe0fc3df889d7046ebba2d60b7f0f1290be4d4874ffd6cd31372b183fc093b4"},{"path":"/usr/bin/command","mode":33261,"size":31,"sha256":"c92ce8c379784b9593fb98a54666cfd84aedab93004df8b8396abe11f7f62077"},{"path":"/usr/bin/fc","mode":33261,"size":26,"sha256":"c39aec5916a27223773952cc38f3e8ccfc83c74315d130ea8a80a36577df7d7a"},{"path":"/usr/bin/fg","mode":33261,"size":26,"sha256":"c1e5f55cb58aee22036e5553bc221f75416fb4ef5dc54ec3d6b62c89ae88e1b1"},{"path":"/usr/bin/getopts","mode":33261,"size":31,"sha256":"6f9c9454233a6c5666933c99bed545c72b9af1c835c94b6e6baf28d7cb86530f"},{"path":"/usr/bin/hash","mode":33261,"size":28,"sha256":"2fbf068f4ae7e8240abe961f4e502b58bfbf79d846d5003e5841162662fa3041"},{"path":"/usr/bin/jobs","mode":33261,"size":28,"sha256":"c72308b9c8028894ff3ec7c79002a2edd4e1f57c6f88136bbc5208fb71595f62"},{"path":"/usr/bin/read","mode":33261,"size":28,"sha256":"861f68383739416356289201125631a7826e722a08ff7906bda76fedf3064105"},{"path":"/usr/bin/sh","mode":41471,"size":4,"sha256":""},{"path":"/usr/bin/type","mode":33261,"size":28,"sha256":"bbba5642dd6d04f4272cc24946cae0d3da128b55df84516374b041c9bac42b35"},{"path":"/usr/bin/ulimit","mode":33261,"size":30,"sha256":"cf6fda74a767e0361031e9eb221c344977a8cd8d885b0384797213484aedd683"},{"path":"/usr/bin/umask","mode":33261,"size":29,"sha256":"987439db80ef5206e72c77ef979391a37a9739c8b30b42d7163b5281cc3514f3"},{"path":"/usr/bin/unalias","mode":33261,"size":31,"sha256":"5331b3af54dfd98f900c43b67b079d1da8f0670f25da09429f9f681d77dbffdb"},{"path":"/usr/bin/wait","mode":33261,"size":28,"sha256":"c888588a6995433b050fe8da3164c5ca60239bf4c3e110b52d6130d7b36728ba"},{"path":"/usr/lib/.build-id/c6/651902765f4cb2f5f0b2dd9c136b4486083087","mode":41471,"size":24,"sha256":""},{"path":"/usr/share/licenses/bash/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"}]}},{"name":"bind-export-libs","version":"9.11.13-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:bind-export-libs:bind-export-libs:9.11.13-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:bind-export-libs:9.11.13-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/bind-export-libs@32:9.11.13-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"bind-export-libs","version":"9.11.13","epoch":32,"architecture":"x86_64","release":"3.el8","sourceRpm":"bind-9.11.13-3.el8.src.rpm","size":3067009,"license":"MPLv2.0","vendor":"CentOS","files":[{"path":"/etc/ld.so.conf.d/bind-export-x86_64.conf","mode":33188,"size":26,"sha256":"efeec53def06657c947f064463d5ebdb68f7c6f9e40cc2e72fc11c263484942e"},{"path":"/usr/lib/.build-id/09/d4bbafff54057b5c88b92d07ae6bf215fd7058","mode":41471,"size":60,"sha256":""},{"path":"/usr/lib/.build-id/34/1a05526a8a643a65e2ac91780716f264f57065","mode":41471,"size":60,"sha256":""},{"path":"/usr/lib/.build-id/51/54463186dd0f4398259e5bbf17e18db7f477b9","mode":41471,"size":62,"sha256":""},{"path":"/usr/lib/.build-id/ba/8b42bbe1100154be105100a7428c39f49aef3f","mode":41471,"size":59,"sha256":""},{"path":"/usr/lib64/bind9-export/libdns-export.so.1107","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib64/bind9-export/libdns-export.so.1107.1.0","mode":33261,"size":2341344,"sha256":"99d95769454ef687eb21d276506926fe3c48d626b6d36950bb0c8daa1130f6d3"},{"path":"/usr/lib64/bind9-export/libirs-export.so.161","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib64/bind9-export/libirs-export.so.161.0.0","mode":33261,"size":45272,"sha256":"c7be72806eeca28d39d5f29d6f45a647a53cd1934f04fa5f3cf4f7821081c951"},{"path":"/usr/lib64/bind9-export/libisc-export.so.1104","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib64/bind9-export/libisc-export.so.1104.0.0","mode":33261,"size":463840,"sha256":"c75f9d66746b525b75524d0e1789d276c573464b350dbec5471b137ee5dafe5a"},{"path":"/usr/lib64/bind9-export/libisccfg-export.so.163","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib64/bind9-export/libisccfg-export.so.163.0.4","mode":33261,"size":186816,"sha256":"efadb45453dd4dc64f60f8d08211ae66abc64c1949b4364dbcbc91c249cd95dc"},{"path":"/usr/share/licenses/bind-export-libs/COPYRIGHT","mode":33188,"size":29711,"sha256":"cd02c93b8dcda794f55dfd1231828d69633072a98eee4874f9cf732d22d9dcde"}]}},{"name":"binutils","version":"2.30-73.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:binutils:binutils:2.30-73.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:binutils:2.30-73.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/binutils@0:2.30-73.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"binutils","version":"2.30","epoch":0,"architecture":"x86_64","release":"73.el8","sourceRpm":"binutils-2.30-73.el8.src.rpm","size":24856745,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/addr2line","mode":33261,"size":34256,"sha256":"61414aa9cdd8dea0a971b0c8d72c2841b1ff6e4553f7272a455030c523b6ac4c"},{"path":"/usr/bin/ar","mode":33261,"size":63584,"sha256":"7488d5757725a0199e6dd0e1c9b65cba6a84c9e13a785f78892d9e560502cd7a"},{"path":"/usr/bin/as","mode":33261,"size":944496,"sha256":"572bce3b5ed8df3dbf8b7365314516c5a7be0cca3fda450436ebf05f77ac759b"},{"path":"/usr/bin/c++filt","mode":33261,"size":29768,"sha256":"1fa1957d8185bb01ecf0905225e30e690db965899d1fa7f1b656dec1dcce365e"},{"path":"/usr/bin/dwp","mode":33261,"size":2271304,"sha256":"c24de352fe0adfe442b2b961424a40b8300e31d5d71d97017698a01826567d3f"},{"path":"/usr/bin/elfedit","mode":33261,"size":34280,"sha256":"108449c108575cc682089dca455413ec71ab36d1d915f19b6a4df2dd5d0f832a"},{"path":"/usr/bin/gprof","mode":33261,"size":106024,"sha256":"e656dbe70c0d2fe623c66bbfd03c9e6f2b712bc978ee2909dc47bf81a130e216"},{"path":"/usr/bin/ld","mode":33261,"size":2505504,"sha256":""},{"path":"/usr/bin/ld.bfd","mode":33261,"size":1789288,"sha256":"05401f94322dd5d5ff0503cd530e212ce7b9f531ef7a1a7826c6901fb92ba916"},{"path":"/usr/bin/ld.gold","mode":33261,"size":2505504,"sha256":"028c58d3e8be4c3af069ffbf45944a6eb1944f66c2bca4fd7b71e2de71c1a5f2"},{"path":"/usr/bin/nm","mode":33261,"size":47536,"sha256":"15eb90071d7e39bfb8f11e488f7c9ae5b5d5df17545964b8dbd964da8bf234a7"},{"path":"/usr/bin/objcopy","mode":33261,"size":246032,"sha256":"363d47f784aaaf6f817054eaa3579bf09d5db60712ce925f0055b99eb164f35c"},{"path":"/usr/bin/objdump","mode":33261,"size":425768,"sha256":"158ce391fdfbd1a55243f318ee716a381192951faec14105fd28cda3dee7c30e"},{"path":"/usr/bin/ranlib","mode":33261,"size":63624,"sha256":"34402fc11dd92e56e3af17d64a4af012795aacc7b5bf374062a32f0d60b5a8ce"},{"path":"/usr/bin/readelf","mode":33261,"size":635576,"sha256":"15432fe05b09abcb0f85b0a2177e996a17c0b8b5be147d2d850f205ad53b509a"},{"path":"/usr/bin/size","mode":33261,"size":34216,"sha256":"b066d218f64eca61a1ad7659c769d2cf5a331062710a3ce2a5d382ea5ce81e75"},{"path":"/usr/bin/strings","mode":33261,"size":34280,"sha256":"e6a38b6ebb17fcf9d66fe912c97b734a4875d504307e6c3d5d060882f3eaa7a6"},{"path":"/usr/bin/strip","mode":33261,"size":246032,"sha256":"00b183e11bd79f8d1240dce339062ea06046f240c69475faef400f6d3f4a749e"},{"path":"/usr/lib/.build-id/10/5e64f371205ab475f08a0ad1ca125e53746466","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/19/e7eea575a128c6e0e683715e161099d6be6523","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/22/6330c59d728ba7fc4c0c0c0687fa414ecaa600","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/.build-id/27/3506d29603cdebfa58b68d5d8b2601772ef27d","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/32/2fbb39c60f97611e4226f8aef765fa7080f7a9","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/.build-id/39/852bc540301d622f33ecaebdf4f2685d040f65","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/.build-id/3d/18e91e4c61403d99ec7d14d936f38b1c039f5d","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/4b/8bb1466a706f71ac888cee769fcde89c74dc33","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/5d/1a868155c0ffb8aecbb01084cb12e630fcaa87","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/6d/34d839a732fa0f7ad22919a4120728e431f842","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/7c/596b0999d8d9fcb69020b6f590bc74e33a317d","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/9e/9c5c0474ffc58bb7dcd70ca45b09fca917df1e","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/a4/a52c08ecacf08cc660c24dbb89298575245f7a","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/c4/25cb31116c56a43497d1ff1be52543af14b57e","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/c7/fb79d0921e91366698e1f22ca3305c53025d19","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/e0/c2e1c7b0007bba0f62f09bd955c5db8433a3d6","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/e0/c2e1c7b0007bba0f62f09bd955c5db8433a3d6.1","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/.build-id/e9/f9842e7bd2c0e398bd987f4dba5fb7219ab049","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/f6/3a50f844e5e53d1baf6b25562554119b69ef38","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/f9/2b7304834760fe5ec0fa2ad10e8816c7ec5ddb","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib64/libbfd-2.30-73.el8.so","mode":33261,"size":1470456,"sha256":"3d289670b78aef9d553e1f40251f021fce77089e8cec35ec48fab9fc30c24ebf"},{"path":"/usr/lib64/libopcodes-2.30-73.el8.so","mode":33261,"size":1741072,"sha256":"b32d13629f41e415587106f738600ac175dc1bab50b2d0b577afdac3bd9db598"},{"path":"/usr/share/licenses/binutils/COPYING","mode":33188,"size":18002,"sha256":"231f7edcc7352d7734a96eef0b8030f77982678c516876fcb81e25b32d68564c"},{"path":"/usr/share/licenses/binutils/COPYING.LIB","mode":33188,"size":25291,"sha256":"56bdea73b6145ef6ac5259b3da390b981d840c24cb03b8e1cbc678de7ecfa18d"},{"path":"/usr/share/licenses/binutils/COPYING3","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/binutils/COPYING3.LIB","mode":33188,"size":7639,"sha256":"a853c2ffec17057872340eee242ae4d96cbf2b520ae27d903e1b2fef1a5f9d1c"}]}},{"name":"bzip2-libs","version":"1.0.6-26.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:bzip2-libs:bzip2-libs:1.0.6-26.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:bzip2-libs:1.0.6-26.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/bzip2-libs@0:1.0.6-26.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"bzip2-libs","version":"1.0.6","epoch":0,"architecture":"x86_64","release":"26.el8","sourceRpm":"bzip2-1.0.6-26.el8.src.rpm","size":77229,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/55/a4e7bc5de12f4b08532d85c1315e0edf10afec","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/libbz2.so.1","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libbz2.so.1.0.6","mode":33261,"size":75328,"sha256":"e34b29aee8fac50ddcb1f2099e95de88789e173b63760044b166fff779483d0d"},{"path":"/usr/share/licenses/bzip2-libs/LICENSE","mode":33188,"size":1901,"sha256":"4919cfb14a73cd64fcef67b107613970cf1659a09aa675dba31314f373bc7204"}]}},{"name":"ca-certificates","version":"2019.2.32-80.0.el8_1","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:ca-certificates:ca-certificates:2019.2.32-80.0.el8_1:*:*:*:*:*:*:*","cpe:2.3:a:*:ca-certificates:2019.2.32-80.0.el8_1:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/ca-certificates@0:2019.2.32-80.0.el8_1?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"ca-certificates","version":"2019.2.32","epoch":0,"architecture":"noarch","release":"80.0.el8_1","sourceRpm":"ca-certificates-2019.2.32-80.0.el8_1.src.rpm","size":993761,"license":"Public Domain","vendor":"CentOS","files":[{"path":"/etc/pki/ca-trust/README","mode":33188,"size":166,"sha256":"6c7b9287c41c171c64b358fc7331b8a9ae969fc2d00d997d88bcbf4da0de598a"},{"path":"/etc/pki/ca-trust/ca-legacy.conf","mode":33188,"size":980,"sha256":"400b96da374503fa6b6350a867347082d0c90e05ba4d02cc6b51b11229199c4d"},{"path":"/etc/pki/ca-trust/extracted/README","mode":33188,"size":560,"sha256":"146ff96c60a8ee32bbcf2da59d624d6ecfbab7ef7442529d46d8d63064d8ca58"},{"path":"/etc/pki/ca-trust/extracted/edk2/README","mode":33188,"size":566,"sha256":"757c28eddb0634b74e6482d16324193be27eee41864c1f96c447020dae14b44f"},{"path":"/etc/pki/ca-trust/extracted/edk2/cacerts.bin","mode":33060,"size":0,"sha256":""},{"path":"/etc/pki/ca-trust/extracted/java/README","mode":33188,"size":726,"sha256":"7bb8781320fb3ff84e76c7e7e4a9c3813879c4f1943710a3b0140b31efacfd32"},{"path":"/etc/pki/ca-trust/extracted/java/cacerts","mode":33060,"size":0,"sha256":""},{"path":"/etc/pki/ca-trust/extracted/openssl/README","mode":33188,"size":787,"sha256":"6c812d1ec8ce5bde2216cc42be33021d6345fbea05c14f50c52191a38c175ea9"},{"path":"/etc/pki/ca-trust/extracted/openssl/ca-bundle.trust.crt","mode":33060,"size":0,"sha256":""},{"path":"/etc/pki/ca-trust/extracted/pem/README","mode":33188,"size":898,"sha256":"27362e773c8b6bb065a455a66badb05e2652720bab8ade9ab91f0404cf827dab"},{"path":"/etc/pki/ca-trust/extracted/pem/email-ca-bundle.pem","mode":33060,"size":0,"sha256":""},{"path":"/etc/pki/ca-trust/extracted/pem/objsign-ca-bundle.pem","mode":33060,"size":0,"sha256":""},{"path":"/etc/pki/ca-trust/extracted/pem/tls-ca-bundle.pem","mode":33060,"size":0,"sha256":""},{"path":"/etc/pki/ca-trust/source/README","mode":33188,"size":932,"sha256":"86184318d451bec55d70c84e618cbfe10c8adb7dc893964ce4aaecff99d83433"},{"path":"/etc/pki/ca-trust/source/ca-bundle.legacy.crt","mode":32768,"size":0,"sha256":""},{"path":"/etc/pki/java/cacerts","mode":41471,"size":40,"sha256":""},{"path":"/etc/pki/tls/cert.pem","mode":41471,"size":49,"sha256":""},{"path":"/etc/pki/tls/certs/ca-bundle.crt","mode":41471,"size":49,"sha256":""},{"path":"/etc/pki/tls/certs/ca-bundle.trust.crt","mode":41471,"size":55,"sha256":""},{"path":"/etc/ssl/certs","mode":41471,"size":16,"sha256":""},{"path":"/usr/bin/ca-legacy","mode":33261,"size":1644,"sha256":"de73a03a0cde4aff31ce3d5e27eecd03284a637c102e46b9e47d4369b5152ae0"},{"path":"/usr/bin/update-ca-trust","mode":33261,"size":1268,"sha256":"0c0c0600587db7f59ba5e399666152ea6de6059f37408f3946c43438d607efdd"},{"path":"/usr/share/pki/ca-trust-legacy/ca-bundle.legacy.default.crt","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/share/pki/ca-trust-legacy/ca-bundle.legacy.disable.crt","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/share/pki/ca-trust-source/README","mode":33188,"size":937,"sha256":"0d2e90b6cf575678cd9d4f409d92258ef0d676995d4d733acdb2425309a38ff8"},{"path":"/usr/share/pki/ca-trust-source/ca-bundle.trust.p11-kit","mode":33188,"size":979015,"sha256":"c9bf832ad4e026a464d475cdc7468d8ce286a3c6513d6ef507b06a08c55e293e"}]}},{"name":"centos-gpg-keys","version":"8.2-2.2004.0.1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:centos-gpg-keys:centos-gpg-keys:8.2-2.2004.0.1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:centos-gpg-keys:8.2-2.2004.0.1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/centos-gpg-keys@0:8.2-2.2004.0.1.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"centos-gpg-keys","version":"8.2","epoch":0,"architecture":"noarch","release":"2.2004.0.1.el8","sourceRpm":"centos-release-8.2-2.2004.0.1.el8.src.rpm","size":3370,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial","mode":33188,"size":1683,"sha256":"146059788b214d7ba0dd70c1cf21111e594c6cfde201da8a9a88fe7101be8a78"},{"path":"/etc/pki/rpm-gpg/RPM-GPG-KEY-centostesting","mode":33188,"size":1687,"sha256":"c9c03d66017969a4e7cc2378cac520d726d87e1f24422ec28a96065e43ce8c4a"}]}},{"name":"centos-release","version":"8.2-2.2004.0.1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:centos-release:centos-release:8.2-2.2004.0.1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:centos-release:8.2-2.2004.0.1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/centos-release@0:8.2-2.2004.0.1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"centos-release","version":"8.2","epoch":0,"architecture":"x86_64","release":"2.2004.0.1.el8","sourceRpm":"centos-release-8.2-2.2004.0.1.el8.src.rpm","size":25430,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/etc/centos-release","mode":33188,"size":38,"sha256":"2270da6918b57d65c4fdbe6a7d0ec09eafeb786f3649ffaa98d331640842ea19"},{"path":"/etc/centos-release-upstream","mode":33188,"size":51,"sha256":"68116d88b20b07eb9ad07d0434bd99f7e542b135537419e211d6302129e049f3"},{"path":"/etc/issue","mode":33188,"size":23,"sha256":"188029a4a5fc320b6157195899bf6d424610d385949a857a811d992602fa48c9"},{"path":"/etc/issue.net","mode":33188,"size":22,"sha256":"17657f4ee63966a9c7687e97028b9ca514f6e9bcbefec4b7f4e81ac861eb3483"},{"path":"/etc/os-release","mode":41471,"size":21,"sha256":""},{"path":"/etc/redhat-release","mode":41471,"size":14,"sha256":""},{"path":"/etc/rpm/macros.dist","mode":33188,"size":66,"sha256":"ac1de6c6cd2c05b8411d4ab341e98c64d7699606900f628de5e7834c96c5f818"},{"path":"/etc/system-release","mode":41471,"size":14,"sha256":""},{"path":"/etc/system-release-cpe","mode":33188,"size":23,"sha256":"54c701dd1ed293e03c931055aceb61b0cb5cd4aa61908b7e42c0d5f4ce8a719f"},{"path":"/usr/lib/os-release","mode":33188,"size":420,"sha256":"9fca2dbc22c40311925727621cf8ec233d049882de0eef7e45d5c083e251918d"},{"path":"/usr/lib/systemd/system-preset/85-display-manager.preset","mode":33188,"size":264,"sha256":"ac3e811c49cac013f48b46a20a514b1dbc1a55831498dd4d211bf111a0faa3a9"},{"path":"/usr/lib/systemd/system-preset/90-default.preset","mode":33188,"size":3982,"sha256":"f2547732c5fa871ff31f0a770340b0fb3d4a35fac213a1f691e8ea9356f1d75c"},{"path":"/usr/lib/systemd/system-preset/99-default-disable.preset","mode":33188,"size":10,"sha256":"3127b197b9eae62eb84eeed69b0413419612238332006183e36a3fba89578378"},{"path":"/usr/share/centos-release/EULA","mode":33188,"size":298,"sha256":"070988e97cf5f7a52ad927dcf03f75a93ee3c9257099030ce637431e86847f2a"},{"path":"/usr/share/redhat-release","mode":41471,"size":14,"sha256":""}]}},{"name":"centos-repos","version":"8.2-2.2004.0.1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:centos-repos:centos-repos:8.2-2.2004.0.1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:centos-repos:8.2-2.2004.0.1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/centos-repos@0:8.2-2.2004.0.1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"centos-repos","version":"8.2","epoch":0,"architecture":"x86_64","release":"2.2004.0.1.el8","sourceRpm":"centos-release-8.2-2.2004.0.1.el8.src.rpm","size":9660,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/etc/dnf/vars/contentdir","mode":33188,"size":7,"sha256":"96171c133b33b6db82fe59ca91d45a5dc2803bba19501f00e06d243514da1f76"},{"path":"/etc/dnf/vars/infra","mode":33188,"size":6,"sha256":"394924622dfba63003e3b0eb4bdf696c73c71e55c83c12d5a74e87a31c944779"},{"path":"/etc/yum.repos.d/CentOS-AppStream.repo","mode":33188,"size":731,"sha256":"0e3a78178a75c13d71cfc2fafb3072a009733414a90802b2b67ccc7279e050cd"},{"path":"/etc/yum.repos.d/CentOS-Base.repo","mode":33188,"size":712,"sha256":"ee7da6f7be6623cc6da7613777def9c9801073d725f686eb4e3812584e3e417d"},{"path":"/etc/yum.repos.d/CentOS-CR.repo","mode":33188,"size":1043,"sha256":"4f781d85bd6ee94a6017abcf31751eb178138037769c51c59fdf978976d0c6f6"},{"path":"/etc/yum.repos.d/CentOS-Debuginfo.repo","mode":33188,"size":668,"sha256":"fc4f39ea86eb19b225d839fb87e00ef2f739fc3f1bc69bae4ef59041706d72ec"},{"path":"/etc/yum.repos.d/CentOS-Devel.repo","mode":33188,"size":743,"sha256":"c2568f2cf213079788362f36dfb4988512a91ae608412814e61428161061db88"},{"path":"/etc/yum.repos.d/CentOS-Extras.repo","mode":33188,"size":756,"sha256":"337836cba39c52316fae9f5ba867ad7d7e1ade8134a47ea03b2c408639df0915"},{"path":"/etc/yum.repos.d/CentOS-HA.repo","mode":33188,"size":738,"sha256":"54b661466dc2496653be171a855f2b4461aade859279c6de7a88cb271be71e69"},{"path":"/etc/yum.repos.d/CentOS-Media.repo","mode":33188,"size":928,"sha256":"bc8973f360fbca2f501eca1e6bc2578a95f566fcaa6973fbc18e8c1fc0a1df43"},{"path":"/etc/yum.repos.d/CentOS-PowerTools.repo","mode":33188,"size":736,"sha256":"55b140630a42bd023ff40be2cf0d5fab51f89718f5d4a908ef64bd9b3538b120"},{"path":"/etc/yum.repos.d/CentOS-Sources.repo","mode":33188,"size":1382,"sha256":"786f6399086b63b88366cbea5d8efd2a5316a5c75d787b6d0e88c726b0db59e6"},{"path":"/etc/yum.repos.d/CentOS-Vault.repo","mode":33188,"size":74,"sha256":"863945c3ab656685e362bbb9f0843ddd2af74fcb4acadb5f4734381b990ed793"},{"path":"/etc/yum.repos.d/CentOS-centosplus.repo","mode":33188,"size":798,"sha256":"f4e068d64d48026d29ad38f4d28800daf61e24655c0914d509fb22548e19fbc2"},{"path":"/etc/yum.repos.d/CentOS-fasttrack.repo","mode":33188,"size":338,"sha256":"785b6808af71111422b319e36501afde57ee58c6a3473476df2dded7676133fc"}]}},{"name":"chkconfig","version":"1.11-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:chkconfig:chkconfig:1.11-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:chkconfig:1.11-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/chkconfig@0:1.11-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"chkconfig","version":"1.11","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"chkconfig-1.11-1.el8.src.rpm","size":791234,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/etc/init.d","mode":41471,"size":11,"sha256":""},{"path":"/etc/rc0.d","mode":41471,"size":10,"sha256":""},{"path":"/etc/rc1.d","mode":41471,"size":10,"sha256":""},{"path":"/etc/rc2.d","mode":41471,"size":10,"sha256":""},{"path":"/etc/rc3.d","mode":41471,"size":10,"sha256":""},{"path":"/etc/rc4.d","mode":41471,"size":10,"sha256":""},{"path":"/etc/rc5.d","mode":41471,"size":10,"sha256":""},{"path":"/etc/rc6.d","mode":41471,"size":10,"sha256":""},{"path":"/usr/lib/.build-id/6a/1b633fbb12ce80a02cadf19967f94df24884e6","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/82/46ff08e4360cc9b48bc6b6e4736e7da4e1ee52","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/systemd/systemd-sysv-install","mode":41471,"size":24,"sha256":""},{"path":"/usr/sbin/alternatives","mode":33261,"size":34128,"sha256":"57d4e9d8d4261558fd60e0b5a02b355eb314cdbe518391d722e9522f2f75f87b"},{"path":"/usr/sbin/update-alternatives","mode":41471,"size":12,"sha256":""},{"path":"/usr/share/licenses/chkconfig/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/locale/en_GB/LC_MESSAGES/chkconfig.mo","mode":33188,"size":8371,"sha256":"24b620d64b5a473d8101cda6b56424c5ae74610e42ba7bd719825ddcf5c9c578"}]}},{"name":"coreutils-single","version":"8.30-7.el8_2.1","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:coreutils-single:coreutils-single:8.30-7.el8_2.1:*:*:*:*:*:*:*","cpe:2.3:a:*:coreutils-single:8.30-7.el8_2.1:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/coreutils-single@0:8.30-7.el8_2.1?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"coreutils-single","version":"8.30","epoch":0,"architecture":"x86_64","release":"7.el8_2.1","sourceRpm":"coreutils-8.30-7.el8_2.1.src.rpm","size":1356273,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/[","mode":33133,"size":48,"sha256":"afd97bbd643bfe1473794af167cd5c6f44fe449681033e3584b40b836f624b4b"},{"path":"/usr/bin/arch","mode":33133,"size":51,"sha256":"209bae4071910ef54b4a3bd302059bf7e00870d8bacffcd7c5489425f37ed16f"},{"path":"/usr/bin/b2sum","mode":33133,"size":52,"sha256":"9116333c88eee22e55e30db1ad088483f52a3024b624356416873bc14fad9359"},{"path":"/usr/bin/base32","mode":33133,"size":53,"sha256":"ff10172686b6db691ae57530dff6cd14b980cbba7ed81a8dcf81bd42dd7bb23b"},{"path":"/usr/bin/base64","mode":33133,"size":53,"sha256":"fed1b291454a61812e605fd06b04f915ef7e5436cfc1ee17f96523f56c2fbebf"},{"path":"/usr/bin/basename","mode":33133,"size":55,"sha256":"9a1e6804fef8ca36d39b008210b187dc4a82c456919574e61e17ab40c033589c"},{"path":"/usr/bin/cat","mode":33133,"size":50,"sha256":"c6138c9502337f42763d627e4b665dd4fd66f26a987891d0a7e8313783f689ad"},{"path":"/usr/bin/chcon","mode":33133,"size":52,"sha256":"c191edddab15fd046170527d27f5f2a864684e118020ae3cab9a8c4ce7e6cc8f"},{"path":"/usr/bin/chgrp","mode":33133,"size":52,"sha256":"e1d37a0d06d1d5db7180b10eb367365214de3c458a356efa32960312dabf9bde"},{"path":"/usr/bin/chmod","mode":33133,"size":52,"sha256":"8ee704ee6e399f29d23b37223b4c80a1a5a39fd0752c6d913d9bcb176b4bb930"},{"path":"/usr/bin/chown","mode":33133,"size":52,"sha256":"497a658c90080afd7bba33da8297fdb1be37cf36a3465a344164a8cb14390b53"},{"path":"/usr/bin/cksum","mode":33133,"size":52,"sha256":"09eada4c0374c3c565ebe1f8965bce9943eb7c2790ef031d7b638b3f191b5592"},{"path":"/usr/bin/comm","mode":33133,"size":51,"sha256":"7449de734af6ab89331fc34dabfd40d10fa799369a52fd9df7c3829ded1d0261"},{"path":"/usr/bin/coreutils","mode":33261,"size":1304144,"sha256":"a2ce19f3905edd29b0a55c3317ae783e337d70d1e82b3969a98436189007df07"},{"path":"/usr/bin/cp","mode":33133,"size":49,"sha256":"79c39d67b7969b943045e80485f9dc3202a11ddfc5c9f7fdb4287216d0255a90"},{"path":"/usr/bin/csplit","mode":33133,"size":53,"sha256":"406a678a5b17869b4d148ad1924dd9ff3f2496e6f8b1dde6572edb355ded6316"},{"path":"/usr/bin/cut","mode":33133,"size":50,"sha256":"7448d9549e82dc4aa8917fc2bc2c49ad3f99e85e0c4f9a0957926a1f33c60421"},{"path":"/usr/bin/date","mode":33133,"size":51,"sha256":"71fb38657d2a08ad7fa8a7d6d44b54b4a63b2b0ca654e7865c0993443fe36608"},{"path":"/usr/bin/dd","mode":33133,"size":49,"sha256":"afc84e0b7f78721d72cc70e5207c0a948889401b1ae985f88fe5557010898d16"},{"path":"/usr/bin/df","mode":33133,"size":49,"sha256":"7140d87bcfc96e33d0e40e746734dfa02fb2973428059a83f267f490acf2924c"},{"path":"/usr/bin/dir","mode":33133,"size":50,"sha256":"9dfc129738cbf6c04a0a6bce388f6cabe0212abfb4f7011997477d657c552b2f"},{"path":"/usr/bin/dircolors","mode":33133,"size":56,"sha256":"db0b3071d1896d4cb925e2539b959071d3dd028501e989ae051a7cc2923a131d"},{"path":"/usr/bin/dirname","mode":33133,"size":54,"sha256":"79eb20166b1c6e3c720bbd9d1b7093dba753747f4a9c86c20efd24cfa1b7cd02"},{"path":"/usr/bin/du","mode":33133,"size":49,"sha256":"4f987dcb68ff9790a7da315f18dba495258e0689c9c145cba4ae33bbf1153ef1"},{"path":"/usr/bin/echo","mode":33133,"size":51,"sha256":"5e2e65807f2d7416260cc04c62a37b6aa14c3336632709406a6eb5e20a25676e"},{"path":"/usr/bin/env","mode":33133,"size":50,"sha256":"3164957405d820d74c59ce94cbe8e20eafa4d25366f53e4de9e3f4a149a9576c"},{"path":"/usr/bin/expand","mode":33133,"size":53,"sha256":"b2f2c111df45d87cb069e96a9152847d31a40d2357e770d4c943d04afe6e1acd"},{"path":"/usr/bin/expr","mode":33133,"size":51,"sha256":"27afd110fdd08ce37ae374cdb19348dc82db58b2a299d601b1a202e524ffad7c"},{"path":"/usr/bin/factor","mode":33133,"size":53,"sha256":"ee9ee5a137e0591cd9cb7c833ea6d132715452b6e8ec15a521d5656825600a51"},{"path":"/usr/bin/false","mode":33133,"size":52,"sha256":"deeb84f2992538f7fadfc6946e4e34ce8b491c5d15aac723f2545fc53423609e"},{"path":"/usr/bin/fmt","mode":33133,"size":50,"sha256":"64eb499e5fcea80a3132b009285321317b2660173d3052ca3dc9c3871f07e0e8"},{"path":"/usr/bin/fold","mode":33133,"size":51,"sha256":"1af788b3e940772d2d061a2868af5e034faf977d2d7158cbefa3e56a05304049"},{"path":"/usr/bin/groups","mode":33133,"size":53,"sha256":"80c0a1f602b5a30973ef4aff1549ab8f0c57415f1a1269c60fd463e51bc599f5"},{"path":"/usr/bin/head","mode":33133,"size":51,"sha256":"d9265e0e806df2362b9e6b476b8b16cef39979c6e1ec9f51aae90f202b94a6d4"},{"path":"/usr/bin/hostid","mode":33133,"size":53,"sha256":"a755dbdf0e3c215642c5dad5c02c6b69f1c533fc253aa5206e634cae9a601fff"},{"path":"/usr/bin/id","mode":33133,"size":49,"sha256":"44cd8c4e4d7c0abda1cf8f4d3cb8c3eaa3a099e3583226a71b7b2717862293d3"},{"path":"/usr/bin/install","mode":33133,"size":55,"sha256":"a1e9d54276f52269bf3f3c4787159a8582d093acb918026a389bb03ae886424b"},{"path":"/usr/bin/join","mode":33133,"size":51,"sha256":"9b4380b504cfba01d655f9102279abc3fa6105a4e107aa409912de8407ce7514"},{"path":"/usr/bin/link","mode":33133,"size":51,"sha256":"821714203f91ff6532c52ae3f871e0130435b6ba1f1f08d2d1f7bbc6693c0caf"},{"path":"/usr/bin/ln","mode":33133,"size":49,"sha256":"085d5f728f31abf16f2e2b6f848b10e987c2ddcf160cb9a8f12378de2b6c6657"},{"path":"/usr/bin/logname","mode":33133,"size":54,"sha256":"55fbba98b8cf7ccc3d0920e6630b525360603b1db4c72c955e6d3a09f8602b68"},{"path":"/usr/bin/ls","mode":33133,"size":49,"sha256":"309b3c9a3246361ec0338641aed3c14e7f91e23e7cf10de000c75135ba99fddd"},{"path":"/usr/bin/md5sum","mode":33133,"size":53,"sha256":"ec74d410b372b48ef2b522cb903d48184f299c9290e5fa430fda73009e1ba468"},{"path":"/usr/bin/mkdir","mode":33133,"size":52,"sha256":"3d79925b34d75033957c123dcdb7d9d74bbdf2135ae401aeecd1c7fdbec0541b"},{"path":"/usr/bin/mkfifo","mode":33133,"size":53,"sha256":"3abebd9dd438dfffcd6f958488172a3b403dfa0eac1ac0e1b8c26e94b61472c4"},{"path":"/usr/bin/mknod","mode":33133,"size":52,"sha256":"e0aea7b102cdd165cf69e86c9b72bf9f1610f063a41379ff98e6abd7767a0f0c"},{"path":"/usr/bin/mktemp","mode":33133,"size":53,"sha256":"79dab18e96e909ca19e901731bd14bbd182327ed34050ad15d3c22186c112601"},{"path":"/usr/bin/mv","mode":33133,"size":49,"sha256":"6ee04af6a9560da8304d298561d76ecc42ce167cd37496cbbee5f7975b2b6c83"},{"path":"/usr/bin/nice","mode":33133,"size":51,"sha256":"05dd64c5d88a6308828a66bdf10fe43a1d762bdf9867eddd1613ed95abcd9eb8"},{"path":"/usr/bin/nl","mode":33133,"size":49,"sha256":"9cebdddb5c913efd5a2e2056790c58a4b1f0ea753ab776209f620c8aefaa88d4"},{"path":"/usr/bin/nohup","mode":33133,"size":52,"sha256":"1d120028b00ffd10dc5d2bdb8725cccd994206809a17897b7dfa7d9852b4a109"},{"path":"/usr/bin/nproc","mode":33133,"size":52,"sha256":"802d57a2bb4a148ce86b5987d42de833613df533033939621c98af7c83ed10a9"},{"path":"/usr/bin/numfmt","mode":33133,"size":53,"sha256":"a2d0a24b66f7e706d20cdbf400f0fb170c9737de1f33707639ac83b0c6eb1fe7"},{"path":"/usr/bin/od","mode":33133,"size":49,"sha256":"28cee197c00cc74e4020bc2c63ef4a47269bfc42a0514e8ac39b93d1c9fb5c79"},{"path":"/usr/bin/paste","mode":33133,"size":52,"sha256":"8bc3ecc3066cf717ff77c775897786c7ffbc96d8b4e7bf74ac0d1b1429840cbb"},{"path":"/usr/bin/pathchk","mode":33133,"size":54,"sha256":"c75cdb9159c70035a4fb0c266c75b7046a5e0c65770f1abd3955169ee84495cc"},{"path":"/usr/bin/pinky","mode":33133,"size":52,"sha256":"99376200da341d1d415806ebe99b80bdab70f8e9fecc9faf16b97dd9a0038062"},{"path":"/usr/bin/pr","mode":33133,"size":49,"sha256":"a01cee18df2195a84845ab441c0860ccd2e60fe8420165a46450c4215759c2a4"},{"path":"/usr/bin/printenv","mode":33133,"size":55,"sha256":"d28a352be84024a34f072b7c6a26b94aa87a2e76b90f437107d9b7eeebd0053c"},{"path":"/usr/bin/printf","mode":33133,"size":53,"sha256":"129f7bcc2ae4d017b79e41c979ebfa18fc9052d4186538c25d736bfd2e397280"},{"path":"/usr/bin/ptx","mode":33133,"size":50,"sha256":"4d3ecca846d94b352b5ba97887e413980af43df47f393f860ed07ed3af0ef681"},{"path":"/usr/bin/pwd","mode":33133,"size":50,"sha256":"efabc0b34ff064d6a99456f5f74490573f8b9db6d1bf9450ad2e0aae0402b89c"},{"path":"/usr/bin/readlink","mode":33133,"size":55,"sha256":"b84234996da12c81e5762285b91ae7681342e012612df920b94ae0bd1557884f"},{"path":"/usr/bin/realpath","mode":33133,"size":55,"sha256":"504d523de86fa1463b8d96abf3cdd7ec8e85571593bc95650130c83ee8ff20cf"},{"path":"/usr/bin/rm","mode":33133,"size":49,"sha256":"c909af3f4c8ae30d059b96a9cf7b097db39159d161622b95190d60d25a5db776"},{"path":"/usr/bin/rmdir","mode":33133,"size":52,"sha256":"6e999e3d0c2ccfeb001f513f6a6f51c5121327894ea279e2682b4b8272c4bca8"},{"path":"/usr/bin/runcon","mode":33133,"size":53,"sha256":"7ee2793317816a3898f317c53f3ae9324f9e245e52e9df7014553daeaf99b9f8"},{"path":"/usr/bin/seq","mode":33133,"size":50,"sha256":"bb11a10b8a0f5c8e974b844f2fb6c94f81d50ed2508f4583235d4cbe8bc0fbc6"},{"path":"/usr/bin/sha1sum","mode":33133,"size":54,"sha256":"c5e5033951d2d051b6a8412aab455294f2ec529aec279e2bc1600d21dd242a7d"},{"path":"/usr/bin/sha224sum","mode":33133,"size":56,"sha256":"7737b55fb338ea353ae400752f720edbcf38ef09b84ef9be9985195853a62d0d"},{"path":"/usr/bin/sha256sum","mode":33133,"size":56,"sha256":"377e96d9304a3e91119a58155becca958b4dc286c203ea2917ebeadba183db1c"},{"path":"/usr/bin/sha384sum","mode":33133,"size":56,"sha256":"94e88e0dcf5ee93b44fed867bf4e42e737dfac9ca957247489264bbf1b2f6ec7"},{"path":"/usr/bin/sha512sum","mode":33133,"size":56,"sha256":"23809accfe32a32da5b0fdb65f6d638f96f3c48be4fa59c41a04067677daec6e"},{"path":"/usr/bin/shred","mode":33133,"size":52,"sha256":"b06cd470398f9e5505b962475935ce2922ad8b8f24d469e55ca398c6a4c840fe"},{"path":"/usr/bin/shuf","mode":33133,"size":51,"sha256":"76918b2e6df2cd31f4e6812766b003fb4a037507d12e089e4a513f8f13c312e1"},{"path":"/usr/bin/sleep","mode":33133,"size":52,"sha256":"96f0366d3535f1556981c0ccc68c160328eb6f2757971e15642d585b2cd1f344"},{"path":"/usr/bin/sort","mode":33133,"size":51,"sha256":"7db440f4b4270d53050569407160d7f7c23fd7832394ce9bfbbc0b1d6e7e7dac"},{"path":"/usr/bin/split","mode":33133,"size":52,"sha256":"9b963841b57f729c71909fe9d4c5f1644aea4260b736b37050b35f18ab82b4ab"},{"path":"/usr/bin/stat","mode":33133,"size":51,"sha256":"9f6ffbf89d8463633790130b1d79999e1f5ef72fa63ac128eefc19101116b4d3"},{"path":"/usr/bin/stdbuf","mode":33133,"size":53,"sha256":"64ca8854673bbe7597c0be2ebc1ea1248e16a022e07216fe5ff2af5af1408cd7"},{"path":"/usr/bin/stty","mode":33133,"size":51,"sha256":"347183bf373a494eb701af0b8f2c2c7d296a6ac1a90fad3cfe4745d236bd0dc9"},{"path":"/usr/bin/sum","mode":33133,"size":50,"sha256":"4f443e4c6d5063c4affc2b9d12852eab4c4eb675e323603441b0cc96fb9c2389"},{"path":"/usr/bin/sync","mode":33133,"size":51,"sha256":"5f3ecf316cc8d0461cdc69e55f97c575a2c37f250e77461ac6241d049d65b177"},{"path":"/usr/bin/tac","mode":33133,"size":50,"sha256":"054324a3bf86ff8d7de940b38abfea90434de3f7e6dbfb68c28fef13ab194a4b"},{"path":"/usr/bin/tail","mode":33133,"size":51,"sha256":"c84b690e840c9297566787aa939370f9b2e181e01c91b727e77ae07865f06c1a"},{"path":"/usr/bin/tee","mode":33133,"size":50,"sha256":"97a3eca66552d324751b1e8e5af6ca4295328b98fa57bc43f1f81cc0a53e197e"},{"path":"/usr/bin/test","mode":33133,"size":51,"sha256":"12f025e9fc03f2dde8653295c2c685c1a010120b768a5becc53f61a652469005"},{"path":"/usr/bin/timeout","mode":33133,"size":54,"sha256":"a58c5c3de98fedf0d7199e4e51e6d241169678259b99c21c75e5bbc17b885662"},{"path":"/usr/bin/touch","mode":33133,"size":52,"sha256":"cc4165b10af3012c31ff266d74ec268c5f0ebf0521faf2596141d1b33b9c1309"},{"path":"/usr/bin/tr","mode":33133,"size":49,"sha256":"e3bb9a0ff998a6452a2652ad9fe93913ed17426812718c0618b769c0a45859be"},{"path":"/usr/bin/true","mode":33133,"size":51,"sha256":"c73afb60197c9c64805d2b4ab95efdee8646f8248ff800de2575a11eed8f9f08"},{"path":"/usr/bin/truncate","mode":33133,"size":55,"sha256":"e58155261499fd6ba41e6f6cf6b696529f929b2ea82d710b8d0467e28f9eb6b8"},{"path":"/usr/bin/tsort","mode":33133,"size":52,"sha256":"f93ec3a790a5f9283da66b22aa307a9289ba40a6a9f413c74dbb18d243c71da2"},{"path":"/usr/bin/tty","mode":33133,"size":50,"sha256":"47fb87400000912b988e1a8708d99287751c976b942ffb5dacc21316d07fd6d0"},{"path":"/usr/bin/uname","mode":33133,"size":52,"sha256":"050964cc46affadcf00d817106c47a6bde087fc483fa0643e168a816b76de608"},{"path":"/usr/bin/unexpand","mode":33133,"size":55,"sha256":"9dd5e2f796993334c5d66b9d2258c48d447fcdc2762a6aa0987590f5384552cb"},{"path":"/usr/bin/uniq","mode":33133,"size":51,"sha256":"2e91d5ac599019cb960094ed9a9b9973d7c1980b209dcba3de2f1549e85a0cd2"},{"path":"/usr/bin/unlink","mode":33133,"size":53,"sha256":"d9a4afe24003912290d8a8fed7781afeeee64bb88a53cfd5b2f820ab6df355c2"},{"path":"/usr/bin/users","mode":33133,"size":52,"sha256":"d8f7ba3fd846a96259a17e8785a172d653fdfb03c1507f95aeeb8d5461407b5c"},{"path":"/usr/bin/vdir","mode":33133,"size":51,"sha256":"fff208202d47a5ff1daec8820f11555149ec8d9d9b39235e14555c3a14bd8572"},{"path":"/usr/bin/wc","mode":33133,"size":49,"sha256":"709f6b9228d11ea5bf6298c953c98a3d11ec89a50916646494661aca8c32a775"},{"path":"/usr/bin/who","mode":33133,"size":50,"sha256":"5f2f1a73f39388b45a8ee56e44abe0a084d6849ba4c432130f9ef04bc6a58e4e"},{"path":"/usr/bin/whoami","mode":33133,"size":53,"sha256":"112e9bdfc8975c4413bb940c0ab36034902d0037b2b25d24f2d1b4f93a32bd6a"},{"path":"/usr/bin/yes","mode":33133,"size":50,"sha256":"614d5aab2a46b047fb5160018dd4f1c7655f792a467dcb8abea75cbec5579b08"},{"path":"/usr/lib/.build-id/74/56d7c71eed6803962c38007ecf07d4c25c8c06","mode":41471,"size":53,"sha256":""},{"path":"/usr/lib/.build-id/f2/ae7bc7969e6de6f4eb0fc802b5f82225d64a66","mode":41471,"size":36,"sha256":""},{"path":"/usr/libexec/coreutils/libstdbuf.so","mode":33261,"size":11600,"sha256":"362065efa6c314da7c0228a8215dcf55e38e01571061b577b5cff79e3f946382"},{"path":"/usr/sbin/chroot","mode":33133,"size":53,"sha256":"739f7aeb037de1264e7801b4a2b01b6e98bf66b1fe81c751989241de6f878b19"},{"path":"/usr/share/licenses/coreutils-single/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"}]}},{"name":"cpio","version":"2.12-8.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:cpio:cpio:2.12-8.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:cpio:2.12-8.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/cpio@0:2.12-8.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"cpio","version":"2.12","epoch":0,"architecture":"x86_64","release":"8.el8","sourceRpm":"cpio-2.12-8.el8.src.rpm","size":989536,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/cpio","mode":33261,"size":185320,"sha256":"581886abeb293212c9c27705f5363969939f232b0d0bb71ae3854a2a306a3a51"},{"path":"/usr/lib/.build-id/90/89581371e22960dbec4479efad9042e5fc150e","mode":41471,"size":24,"sha256":""},{"path":"/usr/share/licenses/cpio/COPYING","mode":33188,"size":35068,"sha256":"fc82ca8b6fdb18d4e3e85cfd8ab58d1bcd3f1b29abe782895abd91d64763f8e7"}]}},{"name":"cracklib","version":"2.9.6-15.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:cracklib:cracklib:2.9.6-15.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:cracklib:2.9.6-15.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/cracklib@0:2.9.6-15.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"cracklib","version":"2.9.6","epoch":0,"architecture":"x86_64","release":"15.el8","sourceRpm":"cracklib-2.9.6-15.el8.src.rpm","size":239047,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/2a/b3ca352642eddf459647af45d10196b68e803e","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/2c/f06ecb760830a44054a2dae5e46d37c0096bdc","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/45/eadd32bae2bb25d417c9c1c246cf6fba760ba6","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/61/d2f881301c3bb88a1baa2a50115429de33b825","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib64/libcrack.so.2","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libcrack.so.2.9.0","mode":33261,"size":46232,"sha256":"0130a8325893b5b540902e881bc13f223ed41c87d77453ae7dec5dfb61462a4d"},{"path":"/usr/sbin/cracklib-check","mode":33261,"size":13360,"sha256":"59fdd9ba1b742a1344634248065b0cddddd6ce94e0705675eed56f1bb599e3d3"},{"path":"/usr/sbin/cracklib-format","mode":33261,"size":251,"sha256":"fa9c53f74aa35d417a2520f2545addcd5fc0f6b59324e51834740b39f13c1aaf"},{"path":"/usr/sbin/cracklib-packer","mode":33261,"size":13368,"sha256":"b158f64c08ad5d3251f09b1886deb80bf3f41bf800771b01cf0b17c4eb69a836"},{"path":"/usr/sbin/cracklib-unpacker","mode":33261,"size":9248,"sha256":"b246dd1e219141f712daa68dfde2c31080709e3e0ddc8dc5ae830306fe49051a"},{"path":"/usr/sbin/create-cracklib-dict","mode":33261,"size":990,"sha256":"7f0691c00d8cea3ac2f69c7a5e7b2f97eaddab2d792ef4e969f6bab544314dcc"},{"path":"/usr/share/cracklib/cracklib.magic","mode":33188,"size":360,"sha256":"ce9de85e27f60a8905bcdfd3554df17ec49c9cd2d23342c6f45af9fb0e266965"},{"path":"/usr/share/licenses/cracklib/COPYING.LIB","mode":33188,"size":26542,"sha256":"f18a0811fa0e220ccbc42f661545e77f0388631e209585ed582a1c693029c6aa"}]}},{"name":"crypto-policies","version":"20191128-2.git23e1bf1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:crypto-policies:crypto-policies:20191128-2.git23e1bf1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:crypto-policies:20191128-2.git23e1bf1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/crypto-policies@0:20191128-2.git23e1bf1.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"crypto-policies","version":"20191128","epoch":0,"architecture":"noarch","release":"2.git23e1bf1.el8","sourceRpm":"crypto-policies-20191128-2.git23e1bf1.el8.src.rpm","size":190228,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/etc/crypto-policies/back-ends/bind.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/gnutls.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/java.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/krb5.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/libreswan.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/libssh.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/nss.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/openssh.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/opensshserver.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/openssl.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/back-ends/opensslcnf.config","mode":32768,"size":0,"sha256":""},{"path":"/etc/crypto-policies/config","mode":33188,"size":688,"sha256":"f3efd2462de1d6408d2de1d48b4fc0fecc9609254222fccc6cc82cae32303281"},{"path":"/usr/bin/fips-finish-install","mode":33261,"size":891,"sha256":"209e39064035fe35de0df1db8f8bde9725e907b076d6abaaeda1843b9c869659"},{"path":"/usr/bin/fips-mode-setup","mode":33261,"size":4206,"sha256":"6d9881132c4d1017b6ab428d7df1bd1fcd2d803dd5aafa4d17bc37c7fe08d17d"},{"path":"/usr/bin/update-crypto-policies","mode":33261,"size":87,"sha256":"6addb83218c406dc7f789cd90b7f230feac4938419570cff45d9f0ae00710dd3"},{"path":"/usr/share/crypto-policies/DEFAULT/bind.txt","mode":33188,"size":75,"sha256":"07b5c0a6dfe62dd10878e05a15137d10f74580c352fb213bb0e0eedb930c5d99"},{"path":"/usr/share/crypto-policies/DEFAULT/gnutls.txt","mode":33188,"size":437,"sha256":"ec2027bc5c04968e7205a8035047be021fa22ea92fb9dbb2f02a0eed24faee65"},{"path":"/usr/share/crypto-policies/DEFAULT/java.txt","mode":33188,"size":389,"sha256":"d7879dfd9e853f8239cf883ab3a53e425bb72ef2270539a7fea1d77a49e671cc"},{"path":"/usr/share/crypto-policies/DEFAULT/krb5.txt","mode":33188,"size":179,"sha256":"49800062b22a59de7b2dd2e8ab272de57670dc65fba73b6db66a90a629e3bfdc"},{"path":"/usr/share/crypto-policies/DEFAULT/libreswan.txt","mode":33188,"size":448,"sha256":"6e6764cdbe50f15dd04226fa815d7e31dffeb555e5393fb48778f75ef411acb3"},{"path":"/usr/share/crypto-policies/DEFAULT/libssh.txt","mode":33188,"size":1294,"sha256":"332cb6f1f2d0dd7cd7b6c087084bcef69f3469f9c3e35285a15b6ad754ac96f7"},{"path":"/usr/share/crypto-policies/DEFAULT/nss.txt","mode":33188,"size":383,"sha256":"730e688abe235f4f4c513fccdb899080918023631103ea57cd2a1362686118c5"},{"path":"/usr/share/crypto-policies/DEFAULT/openssh.txt","mode":33188,"size":1173,"sha256":"1f6ad778c1b4f3c2ee4c3300a2a829ada209c0f4daa211bde3159a46ad45a14b"},{"path":"/usr/share/crypto-policies/DEFAULT/opensshserver.txt","mode":33188,"size":1579,"sha256":"b6d5ad2e4c5083c3b33a44359352d6c09cc1e0279949b5e467402814d4dd16e8"},{"path":"/usr/share/crypto-policies/DEFAULT/openssl.txt","mode":33188,"size":142,"sha256":"04794651f763a547d662f93bf5080d8e8577fe5f0c417643611f4404ef49891d"},{"path":"/usr/share/crypto-policies/DEFAULT/opensslcnf.txt","mode":33188,"size":315,"sha256":"2a414c5a4d8e1e19e81cfa3c7b0fa2a83464a650c6e66e81bf3e5a6b6d306b25"},{"path":"/usr/share/crypto-policies/EMPTY/bind.txt","mode":33188,"size":123,"sha256":"d2625e9228258edc2e53da32845d06dbc584a7bcbdef590e821fb88a66feb071"},{"path":"/usr/share/crypto-policies/EMPTY/gnutls.txt","mode":33188,"size":42,"sha256":"ebdecc00b137b3d663a15c1a3b51c4bcf564146bbcf56c31dbc6d62eaa023ad0"},{"path":"/usr/share/crypto-policies/EMPTY/java.txt","mode":33188,"size":789,"sha256":"e469e892431a4044d296fc9059b909a1921a9a4658fdea25bf1fa8b29978f3f3"},{"path":"/usr/share/crypto-policies/EMPTY/krb5.txt","mode":33188,"size":36,"sha256":"f13c7ed127764aab9e626e84b99061a0c6a6a71ecee3dfe821eefd2f4d970679"},{"path":"/usr/share/crypto-policies/EMPTY/libreswan.txt","mode":33188,"size":23,"sha256":"17c9621cbd4a12bd0c548a16ae61f858284de1472326996e12140985c6d28636"},{"path":"/usr/share/crypto-policies/EMPTY/libssh.txt","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/share/crypto-policies/EMPTY/nss.txt","mode":33188,"size":147,"sha256":"ffa3482faff8b9c39e8f4496aab37e93c694c758c67876eb4d6e3dbefb9f3ed5"},{"path":"/usr/share/crypto-policies/EMPTY/openssh.txt","mode":33188,"size":21,"sha256":"3297ada25f072eafff0a6b217030d100875107296af6fe20ec4f33025e672ead"},{"path":"/usr/share/crypto-policies/EMPTY/opensshserver.txt","mode":33188,"size":38,"sha256":"e0495c3620a57e37e9e2a11ef1e8a3872dc90f1ac8c08723782b4907f51bc2b5"},{"path":"/usr/share/crypto-policies/EMPTY/openssl.txt","mode":33188,"size":197,"sha256":"8f5163345552ed09d8834e105cc058c04b49e10a66171adce432dc9383eb7044"},{"path":"/usr/share/crypto-policies/EMPTY/opensslcnf.txt","mode":33188,"size":244,"sha256":"695877851253083a75019e1fc00e1290acc32103994c44942bc691ab12d4c660"},{"path":"/usr/share/crypto-policies/FIPS/bind.txt","mode":33188,"size":105,"sha256":"49f1bb6234b52eefda267dc53f937458633362c2e285679101eb400db2cf14ea"},{"path":"/usr/share/crypto-policies/FIPS/gnutls.txt","mode":33188,"size":473,"sha256":"abae6db4f2cbd6ffe8560a00eebd4ca2f49d1c332ba09e6f169272eb11662750"},{"path":"/usr/share/crypto-policies/FIPS/java.txt","mode":33188,"size":587,"sha256":"eb8befa366552ac59e3e036e22dc1d9d609aeb589d06cca5f4c34bb51e29b1ed"},{"path":"/usr/share/crypto-policies/FIPS/krb5.txt","mode":33188,"size":137,"sha256":"18ca0b8c4856e18c4af73db1852021d862ea64aaa9595bc17f8bfa918c53f839"},{"path":"/usr/share/crypto-policies/FIPS/libreswan.txt","mode":33188,"size":359,"sha256":"8aa799cdf385605ea5fdaf0403aa38c961c5e2447d15e40ac0e45f4fede0bfef"},{"path":"/usr/share/crypto-policies/FIPS/libssh.txt","mode":33188,"size":990,"sha256":"52f66a1867b570c4eb883658b4463277c0a90497a08f2551db6fc911874e4d27"},{"path":"/usr/share/crypto-policies/FIPS/nss.txt","mode":33188,"size":345,"sha256":"77ce70c3137b8282c9aee4509ffce1e7c3419e04aa36ac95aa6b625b95c70f0c"},{"path":"/usr/share/crypto-policies/FIPS/openssh.txt","mode":33188,"size":854,"sha256":"d140ff8ee38d517fae026cda89037192693a049286889c05fdee060467599ca2"},{"path":"/usr/share/crypto-policies/FIPS/opensshserver.txt","mode":33188,"size":1178,"sha256":"3fea975c146d78df87cf69a34f301a8de153004e8371c19b98c0154638763c7d"},{"path":"/usr/share/crypto-policies/FIPS/openssl.txt","mode":33188,"size":162,"sha256":"b32ee82d524b28abb8bd5b7263560cd3e0a5ae01dc1ccb93825722eaeff454fd"},{"path":"/usr/share/crypto-policies/FIPS/opensslcnf.txt","mode":33188,"size":306,"sha256":"87de1697ebcd23fa2b77e195d3657b5ef8dc4da6c061371f8ee7796d044c4bbb"},{"path":"/usr/share/crypto-policies/FUTURE/bind.txt","mode":33188,"size":105,"sha256":"49f1bb6234b52eefda267dc53f937458633362c2e285679101eb400db2cf14ea"},{"path":"/usr/share/crypto-policies/FUTURE/gnutls.txt","mode":33188,"size":529,"sha256":"424f33891d98f2445efcee2e2d4919d8c8c5b6293d442752e9d3ff8305605b15"},{"path":"/usr/share/crypto-policies/FUTURE/java.txt","mode":33188,"size":657,"sha256":"864d29685f292b7f4f3b7a29c9ba917aa469dcb1d8a9700c441aa7be59333614"},{"path":"/usr/share/crypto-policies/FUTURE/krb5.txt","mode":33188,"size":131,"sha256":"ae21711a4138a99de04797f2057e7c0e730229ebb807f19d7696006159282582"},{"path":"/usr/share/crypto-policies/FUTURE/libreswan.txt","mode":33188,"size":281,"sha256":"aa21f8da5381b4812b62c6f16a3d8aecb11260cc9414a72b4d8a7e25381834d4"},{"path":"/usr/share/crypto-policies/FUTURE/libssh.txt","mode":33188,"size":1076,"sha256":"3d2ee1b77c63487f1a81bc6d87100d12dd3faf2faf55155dae1b4f07a244da0b"},{"path":"/usr/share/crypto-policies/FUTURE/nss.txt","mode":33188,"size":324,"sha256":"3d34c34d5ba273acd91c648b0276572a698c0d2002b2eac07c51192c0855fb74"},{"path":"/usr/share/crypto-policies/FUTURE/openssh.txt","mode":33188,"size":923,"sha256":"c0c2c69bea40231791f5c93f61b9f13644dd8cf0c799e550606083e0875e2727"},{"path":"/usr/share/crypto-policies/FUTURE/opensshserver.txt","mode":33188,"size":1292,"sha256":"f38acfe306a4548626dd6b388f42a4b2ebda98810d708c13611600dc3233fb6c"},{"path":"/usr/share/crypto-policies/FUTURE/openssl.txt","mode":33188,"size":165,"sha256":"588fecc57cd07a6e1260e7a6f44236d35a14b1275f746d7d4d609b2389a10270"},{"path":"/usr/share/crypto-policies/FUTURE/opensslcnf.txt","mode":33188,"size":292,"sha256":"8e8ce04dd2005f3c2726e67120ac0d7fb0fd64ebf640632322655191b233dd24"},{"path":"/usr/share/crypto-policies/LEGACY/bind.txt","mode":33188,"size":70,"sha256":"07cbda37a6b3b6757625622e6ea6c00047d10459370bdf222ce9d9e5ab466f13"},{"path":"/usr/share/crypto-policies/LEGACY/gnutls.txt","mode":33188,"size":335,"sha256":"fe33108d69c3e21b0b44f017f5c24698fb81b21a1d0faa61b465368c3fc19aa6"},{"path":"/usr/share/crypto-policies/LEGACY/java.txt","mode":33188,"size":357,"sha256":"3591e27fb622b0519684f10e9ac435968dc22101282fa35ec92dca058e78f19b"},{"path":"/usr/share/crypto-policies/LEGACY/krb5.txt","mode":33188,"size":210,"sha256":"3ddd217f3eb3613d993330f7e0cc2a577eab4caf5e72b0d6c8e56602af4924ee"},{"path":"/usr/share/crypto-policies/LEGACY/libreswan.txt","mode":33188,"size":468,"sha256":"a6e872b5bfa2bf84c5ba4424cc6b23602900b0664a511888a0cb6e7367b8368d"},{"path":"/usr/share/crypto-policies/LEGACY/libssh.txt","mode":33188,"size":1404,"sha256":"3fbddffdea99234ca02bfff8804cc30c84b0aa4ae79c6a8fdd80ff2e37474ee0"},{"path":"/usr/share/crypto-policies/LEGACY/nss.txt","mode":33188,"size":412,"sha256":"500da59630b879c628df58e4b84a9dfa5e586bfff0381b6c8db03c3c187ed651"},{"path":"/usr/share/crypto-policies/LEGACY/openssh.txt","mode":33188,"size":1271,"sha256":"76fe9070b172ee9baf59c3cba81814c203580a979bb275f699cd3f5d5efed30b"},{"path":"/usr/share/crypto-policies/LEGACY/opensshserver.txt","mode":33188,"size":1670,"sha256":"2ac8b41914b52b6a62155a297927cf3f0a05666f3d6f58a06e91137fd3d8c80c"},{"path":"/usr/share/crypto-policies/LEGACY/openssl.txt","mode":33188,"size":125,"sha256":"50e7761e50638529444b61710ec27a564278bc79bf238c7e719e198ca99a99d3"},{"path":"/usr/share/crypto-policies/LEGACY/opensslcnf.txt","mode":33188,"size":296,"sha256":"e764f45a32432a6b0c1c651b1ee3bcd295c5dc2a8982b86bacf9559034758822"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/bind.config","mode":33188,"size":75,"sha256":"07b5c0a6dfe62dd10878e05a15137d10f74580c352fb213bb0e0eedb930c5d99"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/gnutls.config","mode":33188,"size":437,"sha256":"ec2027bc5c04968e7205a8035047be021fa22ea92fb9dbb2f02a0eed24faee65"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/java.config","mode":33188,"size":389,"sha256":"d7879dfd9e853f8239cf883ab3a53e425bb72ef2270539a7fea1d77a49e671cc"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/krb5.config","mode":33188,"size":179,"sha256":"49800062b22a59de7b2dd2e8ab272de57670dc65fba73b6db66a90a629e3bfdc"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/libreswan.config","mode":33188,"size":448,"sha256":"6e6764cdbe50f15dd04226fa815d7e31dffeb555e5393fb48778f75ef411acb3"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/libssh.config","mode":33188,"size":1294,"sha256":"332cb6f1f2d0dd7cd7b6c087084bcef69f3469f9c3e35285a15b6ad754ac96f7"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/nss.config","mode":33188,"size":383,"sha256":"730e688abe235f4f4c513fccdb899080918023631103ea57cd2a1362686118c5"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/openssh.config","mode":33188,"size":1173,"sha256":"1f6ad778c1b4f3c2ee4c3300a2a829ada209c0f4daa211bde3159a46ad45a14b"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/opensshserver.config","mode":33188,"size":1579,"sha256":"b6d5ad2e4c5083c3b33a44359352d6c09cc1e0279949b5e467402814d4dd16e8"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/openssl.config","mode":33188,"size":142,"sha256":"04794651f763a547d662f93bf5080d8e8577fe5f0c417643611f4404ef49891d"},{"path":"/usr/share/crypto-policies/back-ends/DEFAULT/opensslcnf.config","mode":33188,"size":315,"sha256":"2a414c5a4d8e1e19e81cfa3c7b0fa2a83464a650c6e66e81bf3e5a6b6d306b25"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/bind.config","mode":33188,"size":105,"sha256":"49f1bb6234b52eefda267dc53f937458633362c2e285679101eb400db2cf14ea"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/gnutls.config","mode":33188,"size":473,"sha256":"abae6db4f2cbd6ffe8560a00eebd4ca2f49d1c332ba09e6f169272eb11662750"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/java.config","mode":33188,"size":587,"sha256":"eb8befa366552ac59e3e036e22dc1d9d609aeb589d06cca5f4c34bb51e29b1ed"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/krb5.config","mode":33188,"size":137,"sha256":"18ca0b8c4856e18c4af73db1852021d862ea64aaa9595bc17f8bfa918c53f839"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/libreswan.config","mode":33188,"size":359,"sha256":"8aa799cdf385605ea5fdaf0403aa38c961c5e2447d15e40ac0e45f4fede0bfef"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/libssh.config","mode":33188,"size":990,"sha256":"52f66a1867b570c4eb883658b4463277c0a90497a08f2551db6fc911874e4d27"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/nss.config","mode":33188,"size":345,"sha256":"77ce70c3137b8282c9aee4509ffce1e7c3419e04aa36ac95aa6b625b95c70f0c"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/openssh.config","mode":33188,"size":854,"sha256":"d140ff8ee38d517fae026cda89037192693a049286889c05fdee060467599ca2"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/opensshserver.config","mode":33188,"size":1178,"sha256":"3fea975c146d78df87cf69a34f301a8de153004e8371c19b98c0154638763c7d"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/openssl.config","mode":33188,"size":162,"sha256":"b32ee82d524b28abb8bd5b7263560cd3e0a5ae01dc1ccb93825722eaeff454fd"},{"path":"/usr/share/crypto-policies/back-ends/FIPS/opensslcnf.config","mode":33188,"size":306,"sha256":"87de1697ebcd23fa2b77e195d3657b5ef8dc4da6c061371f8ee7796d044c4bbb"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/bind.config","mode":33188,"size":105,"sha256":"49f1bb6234b52eefda267dc53f937458633362c2e285679101eb400db2cf14ea"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/gnutls.config","mode":33188,"size":529,"sha256":"424f33891d98f2445efcee2e2d4919d8c8c5b6293d442752e9d3ff8305605b15"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/java.config","mode":33188,"size":657,"sha256":"864d29685f292b7f4f3b7a29c9ba917aa469dcb1d8a9700c441aa7be59333614"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/krb5.config","mode":33188,"size":131,"sha256":"ae21711a4138a99de04797f2057e7c0e730229ebb807f19d7696006159282582"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/libreswan.config","mode":33188,"size":281,"sha256":"aa21f8da5381b4812b62c6f16a3d8aecb11260cc9414a72b4d8a7e25381834d4"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/libssh.config","mode":33188,"size":1076,"sha256":"3d2ee1b77c63487f1a81bc6d87100d12dd3faf2faf55155dae1b4f07a244da0b"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/nss.config","mode":33188,"size":324,"sha256":"3d34c34d5ba273acd91c648b0276572a698c0d2002b2eac07c51192c0855fb74"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/openssh.config","mode":33188,"size":923,"sha256":"c0c2c69bea40231791f5c93f61b9f13644dd8cf0c799e550606083e0875e2727"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/opensshserver.config","mode":33188,"size":1292,"sha256":"f38acfe306a4548626dd6b388f42a4b2ebda98810d708c13611600dc3233fb6c"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/openssl.config","mode":33188,"size":165,"sha256":"588fecc57cd07a6e1260e7a6f44236d35a14b1275f746d7d4d609b2389a10270"},{"path":"/usr/share/crypto-policies/back-ends/FUTURE/opensslcnf.config","mode":33188,"size":292,"sha256":"8e8ce04dd2005f3c2726e67120ac0d7fb0fd64ebf640632322655191b233dd24"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/bind.config","mode":33188,"size":70,"sha256":"07cbda37a6b3b6757625622e6ea6c00047d10459370bdf222ce9d9e5ab466f13"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/gnutls.config","mode":33188,"size":335,"sha256":"fe33108d69c3e21b0b44f017f5c24698fb81b21a1d0faa61b465368c3fc19aa6"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/java.config","mode":33188,"size":357,"sha256":"3591e27fb622b0519684f10e9ac435968dc22101282fa35ec92dca058e78f19b"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/krb5.config","mode":33188,"size":210,"sha256":"3ddd217f3eb3613d993330f7e0cc2a577eab4caf5e72b0d6c8e56602af4924ee"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/libreswan.config","mode":33188,"size":468,"sha256":"a6e872b5bfa2bf84c5ba4424cc6b23602900b0664a511888a0cb6e7367b8368d"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/libssh.config","mode":33188,"size":1404,"sha256":"3fbddffdea99234ca02bfff8804cc30c84b0aa4ae79c6a8fdd80ff2e37474ee0"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/nss.config","mode":33188,"size":412,"sha256":"500da59630b879c628df58e4b84a9dfa5e586bfff0381b6c8db03c3c187ed651"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/openssh.config","mode":33188,"size":1271,"sha256":"76fe9070b172ee9baf59c3cba81814c203580a979bb275f699cd3f5d5efed30b"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/opensshserver.config","mode":33188,"size":1670,"sha256":"2ac8b41914b52b6a62155a297927cf3f0a05666f3d6f58a06e91137fd3d8c80c"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/openssl.config","mode":33188,"size":125,"sha256":"50e7761e50638529444b61710ec27a564278bc79bf238c7e719e198ca99a99d3"},{"path":"/usr/share/crypto-policies/back-ends/LEGACY/opensslcnf.config","mode":33188,"size":296,"sha256":"e764f45a32432a6b0c1c651b1ee3bcd295c5dc2a8982b86bacf9559034758822"},{"path":"/usr/share/crypto-policies/default-config","mode":33188,"size":688,"sha256":"f3efd2462de1d6408d2de1d48b4fc0fecc9609254222fccc6cc82cae32303281"},{"path":"/usr/share/crypto-policies/policies/DEFAULT.pol","mode":33188,"size":2035,"sha256":"87904977d9dfb3f22bfe0fb90cb357b04da0ceb67204e2319731d52fac9c6d21"},{"path":"/usr/share/crypto-policies/policies/EMPTY.pol","mode":33188,"size":364,"sha256":"65e19a3cfa3e4eb86c6546a6c076053bdad4b6e7a65cb5b1e17415ff58691101"},{"path":"/usr/share/crypto-policies/policies/FIPS.pol","mode":33188,"size":1641,"sha256":"6d0b72e01081dd96462a8ab1ee64037f0ee3be0e1c1b8e15384e5f5951199abd"},{"path":"/usr/share/crypto-policies/policies/FUTURE.pol","mode":33188,"size":1972,"sha256":"41b6ac6178b32144fee22fb31e11677324afba0a03a489605b4dedd941f4d096"},{"path":"/usr/share/crypto-policies/policies/LEGACY.pol","mode":33188,"size":2463,"sha256":"4cde848a96ac852b345c62efc84a3f33526b48ee482100483d47af3bf37367b3"},{"path":"/usr/share/crypto-policies/policies/modules/NO-CAMELLIA.pmod","mode":33188,"size":246,"sha256":"99f0729c2ec3b141b237006a0e4121e31a95b707239b8499d0580934f522cf11"},{"path":"/usr/share/crypto-policies/policies/modules/NO-SHA1.pmod","mode":33188,"size":132,"sha256":"4b7f06f3194e84951eb5423e1a8bbceb02087f35f1ee0ebee5d8e389b308f651"},{"path":"/usr/share/crypto-policies/policies/modules/OSPP.pmod","mode":33188,"size":773,"sha256":"a0854e0df9d090a830cf5a8174849fcacf22744c14a4010d22a1cc50acc6386d"},{"path":"/usr/share/crypto-policies/python/__pycache__/build-crypto-policies.cpython-36.opt-1.pyc","mode":33188,"size":4089,"sha256":"c468f052306c56c2e7dffd69528974fc69e43fe4817ec44a1b80ad00b721a96a"},{"path":"/usr/share/crypto-policies/python/__pycache__/build-crypto-policies.cpython-36.pyc","mode":33188,"size":4089,"sha256":"c468f052306c56c2e7dffd69528974fc69e43fe4817ec44a1b80ad00b721a96a"},{"path":"/usr/share/crypto-policies/python/__pycache__/update-crypto-policies.cpython-36.opt-1.pyc","mode":33188,"size":7796,"sha256":"0c8461595ad96f9557f64df9fbfcffe90c1142bacd4a398bc2c91d2b5a138aae"},{"path":"/usr/share/crypto-policies/python/__pycache__/update-crypto-policies.cpython-36.pyc","mode":33188,"size":7796,"sha256":"0c8461595ad96f9557f64df9fbfcffe90c1142bacd4a398bc2c91d2b5a138aae"},{"path":"/usr/share/crypto-policies/python/build-crypto-policies.py","mode":33261,"size":4114,"sha256":"c63b0c7d8bab3e2b2fd4fbaf30cfa84079a64631b68744232ad8108a346e7bf6"},{"path":"/usr/share/crypto-policies/python/cryptopolicies/__init__.py","mode":33188,"size":184,"sha256":"495d51480de0c3a3af6cacac04c3a5a170338e0a549f9691d5a7809e150f1a42"},{"path":"/usr/share/crypto-policies/python/cryptopolicies/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":195,"sha256":"73ca2d4422c3e8404352c87f1cefccbfe86c6758c141381715f34552dd2fa9a6"},{"path":"/usr/share/crypto-policies/python/cryptopolicies/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":195,"sha256":"73ca2d4422c3e8404352c87f1cefccbfe86c6758c141381715f34552dd2fa9a6"},{"path":"/usr/share/crypto-policies/python/cryptopolicies/__pycache__/cryptopolicies.cpython-36.opt-1.pyc","mode":33188,"size":6433,"sha256":"f10b37ae3c4961d37f0b900a66f5496c4ee7438d9267fffa08d79ed03b464c36"},{"path":"/usr/share/crypto-policies/python/cryptopolicies/__pycache__/cryptopolicies.cpython-36.pyc","mode":33188,"size":6433,"sha256":"f10b37ae3c4961d37f0b900a66f5496c4ee7438d9267fffa08d79ed03b464c36"},{"path":"/usr/share/crypto-policies/python/cryptopolicies/cryptopolicies.py","mode":33188,"size":6562,"sha256":"dc245a4f721497a6607c56c17e587fc4fadf58c54307e97bbebf095945ebcb9e"},{"path":"/usr/share/crypto-policies/python/policygenerators/__init__.py","mode":33188,"size":553,"sha256":"93bbf25e37b9b27c66498eb83cc679c15faab52ea50afe7013e5e36b82e41629"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":648,"sha256":"03398023b93b77c0d7e31ccfe669bf03e0bbd69a94046a55a3efeb87f8368bea"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":648,"sha256":"03398023b93b77c0d7e31ccfe669bf03e0bbd69a94046a55a3efeb87f8368bea"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/bind.cpython-36.opt-1.pyc","mode":33188,"size":1870,"sha256":"94aff8db632f05e47234389de641f9806b02730fd730aaf98f9b678945b92cca"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/bind.cpython-36.pyc","mode":33188,"size":1870,"sha256":"94aff8db632f05e47234389de641f9806b02730fd730aaf98f9b678945b92cca"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/configgenerator.cpython-36.opt-1.pyc","mode":33188,"size":724,"sha256":"13b7356c8a539640127445b2d7305d2bb0c0e786b489e50b57876975fd4dd63f"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/configgenerator.cpython-36.pyc","mode":33188,"size":724,"sha256":"13b7356c8a539640127445b2d7305d2bb0c0e786b489e50b57876975fd4dd63f"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/gnutls.cpython-36.opt-1.pyc","mode":33188,"size":5092,"sha256":"7c6b63eb82e03b55bccab1bc5dc146cd48f5366d6e3c2a8ee40a3ec145c482bf"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/gnutls.cpython-36.pyc","mode":33188,"size":5092,"sha256":"7c6b63eb82e03b55bccab1bc5dc146cd48f5366d6e3c2a8ee40a3ec145c482bf"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/java.cpython-36.opt-1.pyc","mode":33188,"size":3472,"sha256":"ee5dd726fb6be3a3ab277b4fe52e5036d66e9ad0ea1b64abf79b7d7384ddbf20"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/java.cpython-36.pyc","mode":33188,"size":3472,"sha256":"ee5dd726fb6be3a3ab277b4fe52e5036d66e9ad0ea1b64abf79b7d7384ddbf20"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/krb5.cpython-36.opt-1.pyc","mode":33188,"size":1480,"sha256":"bd6326b4717c4f94775cb4e050ede4024d2d0ae93a691034b1eab23942565be4"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/krb5.cpython-36.pyc","mode":33188,"size":1480,"sha256":"bd6326b4717c4f94775cb4e050ede4024d2d0ae93a691034b1eab23942565be4"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/libreswan.cpython-36.opt-1.pyc","mode":33188,"size":4042,"sha256":"196f4d5d6160548e7f7f9c5645ecc2654d004db6e00a3204c876ce318669a70c"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/libreswan.cpython-36.pyc","mode":33188,"size":4042,"sha256":"196f4d5d6160548e7f7f9c5645ecc2654d004db6e00a3204c876ce318669a70c"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/libssh.cpython-36.opt-1.pyc","mode":33188,"size":3695,"sha256":"12c9397135ac7f310c60f609012fbd3761086fe0102d28c1a7e68e647df29df0"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/libssh.cpython-36.pyc","mode":33188,"size":3695,"sha256":"12c9397135ac7f310c60f609012fbd3761086fe0102d28c1a7e68e647df29df0"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/nss.cpython-36.opt-1.pyc","mode":33188,"size":3734,"sha256":"7ad15d82d684d222727471b1b1df0a578490057625f347ae41466cabad69c0cb"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/nss.cpython-36.pyc","mode":33188,"size":3734,"sha256":"7ad15d82d684d222727471b1b1df0a578490057625f347ae41466cabad69c0cb"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/openssh.cpython-36.opt-1.pyc","mode":33188,"size":7365,"sha256":"a20a149457602b90758954165c780f49f6758bea404b40d23a1b33e24d6b3b37"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/openssh.cpython-36.pyc","mode":33188,"size":7365,"sha256":"a20a149457602b90758954165c780f49f6758bea404b40d23a1b33e24d6b3b37"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/openssl.cpython-36.opt-1.pyc","mode":33188,"size":5013,"sha256":"443e66096301251aabe34c095fe33617633b41c2cf05b6a88df0fa94fcfde080"},{"path":"/usr/share/crypto-policies/python/policygenerators/__pycache__/openssl.cpython-36.pyc","mode":33188,"size":5013,"sha256":"443e66096301251aabe34c095fe33617633b41c2cf05b6a88df0fa94fcfde080"},{"path":"/usr/share/crypto-policies/python/policygenerators/bind.py","mode":33188,"size":1662,"sha256":"945a63e71739c0f3fbe188cf019de26def944525812af3e431e460ddcd443fec"},{"path":"/usr/share/crypto-policies/python/policygenerators/configgenerator.py","mode":33188,"size":425,"sha256":"35eeec5bcb56a184e944871f5c5a5787f3e6d11d44cc8be159a9666ca571f94f"},{"path":"/usr/share/crypto-policies/python/policygenerators/gnutls.py","mode":33188,"size":5397,"sha256":"75aa7024b879a95eb7cb920d2267c4e163b7c4696061a671b4a7d9bfa0b97ef6"},{"path":"/usr/share/crypto-policies/python/policygenerators/java.py","mode":33188,"size":3565,"sha256":"b4ac3ff33e4c06a2ea9af9704e65393fd2c24d0f2da78f8d399240b5f3fc0259"},{"path":"/usr/share/crypto-policies/python/policygenerators/krb5.py","mode":33188,"size":1396,"sha256":"6acaf8a6f58727262ffa12b0d104c50b5c3c3b1a2cc9f259454a71ee929794ab"},{"path":"/usr/share/crypto-policies/python/policygenerators/libreswan.py","mode":33188,"size":4411,"sha256":"b28b09658060e6eaa2f78d03179be7fa46ba71ce609f873bec963508b3d31b42"},{"path":"/usr/share/crypto-policies/python/policygenerators/libssh.py","mode":33188,"size":3755,"sha256":"841f466eb73c463a06e60e1936801e93c3fc36ac32fa4de93ffa0dc7b301294d"},{"path":"/usr/share/crypto-policies/python/policygenerators/nss.py","mode":33188,"size":3526,"sha256":"1d752c46e187e6c2fa905ef43cf75107a533f1d1cfa719f5c765f9c82ea551da"},{"path":"/usr/share/crypto-policies/python/policygenerators/openssh.py","mode":33188,"size":8016,"sha256":"e5064d751b3205a0631da142d3f2c0fa103d70a266f6b879abb9d8e42480ed7f"},{"path":"/usr/share/crypto-policies/python/policygenerators/openssl.py","mode":33188,"size":4611,"sha256":"137c5f1f6d3533b5cb9b302335c6e647f8b13992452df9a094ea4b649ec5449f"},{"path":"/usr/share/crypto-policies/python/update-crypto-policies.py","mode":33261,"size":7030,"sha256":"c8405b07358088854da2d39b26830265c4a09af2defb352374926b3f43b87100"},{"path":"/usr/share/crypto-policies/reload-cmds.sh","mode":33188,"size":167,"sha256":"69121b6719a4a96cb77bf2372cb58a389b08726e4448b1037b70ec9950af1048"},{"path":"/usr/share/licenses/crypto-policies/COPYING.LESSER","mode":33188,"size":26432,"sha256":"6095e9ffa777dd22839f7801aa845b31c9ed07f3d6bf8a26dc5d2dec8ccc0ef3"}]}},{"name":"cryptsetup-libs","version":"2.2.2-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:cryptsetup-libs:cryptsetup-libs:2.2.2-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:cryptsetup-libs:2.2.2-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/cryptsetup-libs@0:2.2.2-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"cryptsetup-libs","version":"2.2.2","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"cryptsetup-2.2.2-1.el8.src.rpm","size":1871402,"license":"GPLv2+ and LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/7d/6e65b5d72db9a6b5dcfbfec6dd32f721b9b1d0","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/tmpfiles.d/cryptsetup.conf","mode":33188,"size":35,"sha256":"d6bb4b689200c2348945700a6b0dad5df92bc2015860d15f36a25590814d77b0"},{"path":"/usr/lib64/libcryptsetup.so.12","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib64/libcryptsetup.so.12.5.0","mode":33261,"size":484904,"sha256":"d9447f9bc852b72e9516a1f852d0517720dd5e46d515cc55aaf6b3638207dda4"},{"path":"/usr/share/licenses/cryptsetup-libs/COPYING","mode":33188,"size":18802,"sha256":"45670cce8b6a0ddd66c8016cd8ccef6cd71f35717cbacc7f1e895b3855207b33"},{"path":"/usr/share/licenses/cryptsetup-libs/COPYING.LGPL","mode":33188,"size":27247,"sha256":"8c33cc37871654ec7ed87e6fbb896c8cf33ef5ef05b1611a5aed857596ffafa5"}]}},{"name":"curl","version":"7.61.1-12.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:curl:curl:7.61.1-12.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:curl:7.61.1-12.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/curl@0:7.61.1-12.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"curl","version":"7.61.1","epoch":0,"architecture":"x86_64","release":"12.el8","sourceRpm":"curl-7.61.1-12.el8.src.rpm","size":709006,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/bin/curl","mode":33261,"size":243704,"sha256":"9d180f11502a917136ac910f63907beb82469a21e314ce8d27f6825468cdc16f"},{"path":"/usr/lib/.build-id/00/c85131480a6063f70a065e7a324f9ea2c6b477","mode":41471,"size":24,"sha256":""},{"path":"/usr/share/zsh/site-functions/_curl","mode":33188,"size":13328,"sha256":"9b1119ff5631d3b3d9e475c775f7ab8baabcbcc0273b038c6d6e5f54bea3265c"}]}},{"name":"cyrus-sasl-lib","version":"2.1.27-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:cyrus-sasl-lib:cyrus-sasl-lib:2.1.27-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:cyrus-sasl-lib:2.1.27-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/cyrus-sasl-lib@0:2.1.27-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"cyrus-sasl-lib","version":"2.1.27","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"cyrus-sasl-2.1.27-1.el8.src.rpm","size":734978,"license":"BSD with advertising","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/12/05690f08767d57005fab8269658f296f01d0c0","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/7d/00148d1ebcce3eb9a044c6ae40be42e1951d0d","mode":41471,"size":49,"sha256":""},{"path":"/usr/lib/.build-id/86/2196e17588ac75e6360c2ca7dfe8718acbf1fc","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/8e/996e1f62a7cfde54d38ef0281101f309f8338a","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/f0/0d64a2736f57331869c89fdc248071ca7ff2ef","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib64/libsasl2.so.3","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libsasl2.so.3.0.0","mode":33261,"size":130176,"sha256":"ff2dac84e02fa21519c42754502e80e57b909588db1db4a7248776285b77c567"},{"path":"/usr/lib64/sasl2/libanonymous.so","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/sasl2/libanonymous.so.3","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/sasl2/libanonymous.so.3.0.0","mode":33261,"size":21456,"sha256":"364193aae006c614e6e46004ca7d7ecac1e0e224af5ecfc3d84ee0d80ce4a7a0"},{"path":"/usr/lib64/sasl2/libsasldb.so","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/sasl2/libsasldb.so.3","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/sasl2/libsasldb.so.3.0.0","mode":33261,"size":30440,"sha256":"add54ec1025f0feb2aaf77320f67845f6714caa9213bbf5bd129ce19918a3591"},{"path":"/usr/sbin/sasldblistusers2","mode":33261,"size":22688,"sha256":"558a5947d8cd618b58671acf026365631d98a0700f050231299234989c6281e2"},{"path":"/usr/sbin/saslpasswd2","mode":33261,"size":17576,"sha256":"ee32725d2852e424645d289f649365758bf3e55be3a33ac235ad36098609f3d3"},{"path":"/usr/share/licenses/cyrus-sasl-lib/COPYING","mode":33188,"size":1861,"sha256":"9d6e5d1632140a6c135b251260953650d17d87cd1124f87aaf72192aa4580d4b"}]}},{"name":"dbus","version":"1.12.8-9.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dbus:dbus:1.12.8-9.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dbus:1.12.8-9.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dbus@1:1.12.8-9.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dbus","version":"1.12.8","epoch":1,"architecture":"x86_64","release":"9.el8","sourceRpm":"dbus-1.12.8-9.el8.src.rpm","size":0,"license":"(GPLv2+ or AFL) and GPLv2+","vendor":"CentOS","files":[]}},{"name":"dbus-common","version":"1.12.8-9.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dbus-common:dbus-common:1.12.8-9.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dbus-common:1.12.8-9.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dbus-common@1:1.12.8-9.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"dbus-common","version":"1.12.8","epoch":1,"architecture":"noarch","release":"9.el8","sourceRpm":"dbus-1.12.8-9.el8.src.rpm","size":11131,"license":"(GPLv2+ or AFL) and GPLv2+","vendor":"CentOS","files":[{"path":"/etc/dbus-1/session.conf","mode":33188,"size":838,"sha256":"2218b9313dc6d2e07d85751f318124cc5138787358ae1039703321cf6b35602a"},{"path":"/etc/dbus-1/system.conf","mode":33188,"size":833,"sha256":"a6f50dc70ef082a110dcdb164579cd2af221b90226c5e0aca237edcad98a1c26"},{"path":"/usr/lib/sysusers.d/dbus.conf","mode":33188,"size":205,"sha256":"3d645ac41a3fc8b63ac4b295a8c46d02c9261a0c610f2715e1c5e2c7b8286b44"},{"path":"/usr/share/dbus-1/session.conf","mode":33188,"size":3561,"sha256":"206f009ddcf909422f3651c687b4623a5780fb7486c6d650e5332f57c00d6be1"},{"path":"/usr/share/dbus-1/system.conf","mode":33188,"size":5694,"sha256":"f04a4d38054f5d67135283f8034be9517046255bdf29a467e37bf3f644be142e"}]}},{"name":"dbus-daemon","version":"1.12.8-9.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dbus-daemon:dbus-daemon:1.12.8-9.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dbus-daemon:1.12.8-9.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dbus-daemon@1:1.12.8-9.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dbus-daemon","version":"1.12.8","epoch":1,"architecture":"x86_64","release":"9.el8","sourceRpm":"dbus-1.12.8-9.el8.src.rpm","size":583585,"license":"(GPLv2+ or AFL) and GPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/dbus-cleanup-sockets","mode":33261,"size":17480,"sha256":"ac8eceb697ca5d3201c342a92688d3834bb96ea86605b5210c23c0c79b4a5016"},{"path":"/usr/bin/dbus-daemon","mode":33261,"size":259472,"sha256":"07311cabfcc59a83900aaeb392ded9aaf5daec034ee37f9cbe09c8a49fdba210"},{"path":"/usr/bin/dbus-run-session","mode":33261,"size":17448,"sha256":"353f9cac2b251d5b0acff8afca21211929de6d54e72561f5e19ab99cec1134a5"},{"path":"/usr/bin/dbus-test-tool","mode":33261,"size":27064,"sha256":"a89a57b0d7c2f785f3fac0cc07dc06431a2beb04e33925bd16a2dcb8d8846d91"},{"path":"/usr/lib/.build-id/39/a72029110592344fadb1f34de22587feea5931","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/85/484c4ab4591f5c7afc29d02f1784a71f4a0473","mode":41471,"size":56,"sha256":""},{"path":"/usr/lib/.build-id/a0/2833ebed7cfa2bbb40c84a9730c3f620c93c1c","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/d2/123bf4a39097887d6062b48528e2c2c5b6fd9c","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/d2/8261688085a1a20d8fc345fb85a40e61520d00","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/systemd/system/dbus.service","mode":33188,"size":380,"sha256":"7d9d706cc9966c2b6dfebcd64ef460010522194f5b3cb92bc119566b5c8c7864"},{"path":"/usr/lib/systemd/system/dbus.socket","mode":33188,"size":102,"sha256":"e05359bbdc083b8db2b49542b26429166b5e13367a63668a4e8ff8a1b496f7ae"},{"path":"/usr/lib/systemd/system/messagebus.service","mode":41471,"size":12,"sha256":""},{"path":"/usr/lib/systemd/system/multi-user.target.wants/dbus.service","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib/systemd/system/sockets.target.wants/dbus.socket","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib/systemd/user/dbus.service","mode":33188,"size":360,"sha256":"19d7b51e1e6da255346ac6acbf95627baf14c324e84ee841d90fab98bcc0e994"},{"path":"/usr/lib/systemd/user/dbus.socket","mode":33188,"size":178,"sha256":"2b7ac7357065180d1c2f3f00c11d17dadd31cdc3d7e59c623eb733beb3e50cef"},{"path":"/usr/lib/systemd/user/sockets.target.wants/dbus.socket","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib/tmpfiles.d/dbus.conf","mode":33188,"size":365,"sha256":"d1b15f34a0590f6535dbff91727dd6bbf10752e8abb2cab73fa66a6184f9df1a"},{"path":"/usr/libexec/dbus-1/dbus-daemon-launch-helper","mode":35304,"size":70064,"sha256":"9379ffbc5bdcccc20c4ef346532af100e2433e78fcce04822905500994b1f5eb"},{"path":"/usr/share/licenses/dbus-daemon/COPYING","mode":33188,"size":29176,"sha256":"0e46f54efb12d04ab5c33713bacd0e140c9a35b57ae29e03c853203266e8f3a1"}]}},{"name":"dbus-libs","version":"1.12.8-9.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dbus-libs:dbus-libs:1.12.8-9.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dbus-libs:1.12.8-9.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dbus-libs@1:1.12.8-9.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dbus-libs","version":"1.12.8","epoch":1,"architecture":"x86_64","release":"9.el8","sourceRpm":"dbus-1.12.8-9.el8.src.rpm","size":399664,"license":"(GPLv2+ or AFL) and GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/3d/5116ee9a979180640d020d1875012ca8bf6953","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libdbus-1.so.3","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libdbus-1.so.3.19.7","mode":33261,"size":370488,"sha256":"82c4161c8ea1bcb64a58ce8d8490a2c5205a5658fd4a13579fdfed78ff726c45"},{"path":"/usr/share/licenses/dbus-libs/COPYING","mode":33188,"size":29176,"sha256":"0e46f54efb12d04ab5c33713bacd0e140c9a35b57ae29e03c853203266e8f3a1"}]}},{"name":"dbus-tools","version":"1.12.8-9.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dbus-tools:dbus-tools:1.12.8-9.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dbus-tools:1.12.8-9.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dbus-tools@1:1.12.8-9.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dbus-tools","version":"1.12.8","epoch":1,"architecture":"x86_64","release":"9.el8","sourceRpm":"dbus-1.12.8-9.el8.src.rpm","size":129722,"license":"(GPLv2+ or AFL) and GPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/dbus-monitor","mode":33261,"size":30728,"sha256":"4e3d0595bf2cc53287185f2eecf111d363ddd038e2ceaaf0c07ff18e678ff8e2"},{"path":"/usr/bin/dbus-send","mode":33261,"size":30688,"sha256":"ae03034c940c021fbf3d0975d32f121fa7f872da42a549d782ee5d124bc55d23"},{"path":"/usr/bin/dbus-update-activation-environment","mode":33261,"size":17928,"sha256":"d3419c40c16bbd818d810541f7e7fe34109b96c1601f8619737bae8e0333e862"},{"path":"/usr/bin/dbus-uuidgen","mode":33261,"size":13376,"sha256":"0bb1204b5d95b7fc34ba7b23b45e0608b79326da256af70abb96febf1237fa79"},{"path":"/usr/lib/.build-id/12/8c7e370c32d7e80c425ba525ead78b5bc608f6","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/2e/4fa1b16c5fa6b057da520a2b3b0fe7f8c0f943","mode":41471,"size":54,"sha256":""},{"path":"/usr/lib/.build-id/58/a9adefc85c801a1d8f28b098b38cc95690f1c2","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/76/dffe7d1029a044ffe13c0e748aab1ddfbda79a","mode":41471,"size":32,"sha256":""},{"path":"/usr/share/licenses/dbus-tools/COPYING","mode":33188,"size":29176,"sha256":"0e46f54efb12d04ab5c33713bacd0e140c9a35b57ae29e03c853203266e8f3a1"}]}},{"name":"device-mapper","version":"1.02.169-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:device-mapper:device-mapper:1.02.169-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:device-mapper:1.02.169-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/device-mapper@8:1.02.169-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"device-mapper","version":"1.02.169","epoch":8,"architecture":"x86_64","release":"3.el8","sourceRpm":"lvm2-2.03.08-3.el8.src.rpm","size":355102,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/0d/13bbfa7122ca3f0055be9ccaeacf039621c810","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/0f/15958b1a46cdcc225fa182d750bdad9188341a","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/udev/rules.d/10-dm.rules","mode":33060,"size":7266,"sha256":"eb329854ebc0478ffe54d53954c360ba90859a786eeb011df35302dcddb06d2d"},{"path":"/usr/lib/udev/rules.d/13-dm-disk.rules","mode":33060,"size":1794,"sha256":"4f29624db81570ade0ab633c68eadf84eccd7136421b1effa70ed0484f16825e"},{"path":"/usr/lib/udev/rules.d/95-dm-notify.rules","mode":33060,"size":483,"sha256":"d24e725fc78306ff2355eb91e4eebcc7dc9388d54dc27d20d6fe6f695054d536"},{"path":"/usr/sbin/blkdeactivate","mode":33133,"size":14837,"sha256":"b2e62590a43851b57491f02de4c4b2adc796d94b1374ce52cc3deb24781280c9"},{"path":"/usr/sbin/dmfilemapd","mode":33133,"size":25232,"sha256":"7394293dfcdbbb7c3bb250682996262e306a1cb3d72b29fb460f5b65f4f13666"},{"path":"/usr/sbin/dmsetup","mode":33133,"size":162472,"sha256":"8f66ee62854d658606917013266cb6caffc26df7d80a1d036e1def87b068b550"},{"path":"/usr/sbin/dmstats","mode":41471,"size":7,"sha256":""},{"path":"/usr/share/licenses/device-mapper/COPYING","mode":33188,"size":17995,"sha256":"e76fbcd2fb97cf202da330301327754d2db5c58b5b4bebd3a8a749393e7603d1"},{"path":"/usr/share/licenses/device-mapper/COPYING.LIB","mode":33188,"size":26436,"sha256":"5df07007198989c622f5d41de8d703e7bef3d0e79d62e24332ee739a452af62a"}]}},{"name":"device-mapper-libs","version":"1.02.169-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:device-mapper-libs:device-mapper-libs:1.02.169-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:device-mapper-libs:1.02.169-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/device-mapper-libs@8:1.02.169-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"device-mapper-libs","version":"1.02.169","epoch":8,"architecture":"x86_64","release":"3.el8","sourceRpm":"lvm2-2.03.08-3.el8.src.rpm","size":416167,"license":"LGPLv2","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/77/00a7da8230763257f1ebb69e40cd1dcd0b0a15","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib64/libdevmapper.so.1.02","mode":33133,"size":371736,"sha256":"bcd0b9cb0a314162d63cb273c6e30b623b6b8d05c8f28a4875fbcc0cd362c033"},{"path":"/usr/share/licenses/device-mapper-libs/COPYING","mode":33188,"size":17995,"sha256":"e76fbcd2fb97cf202da330301327754d2db5c58b5b4bebd3a8a749393e7603d1"},{"path":"/usr/share/licenses/device-mapper-libs/COPYING.LIB","mode":33188,"size":26436,"sha256":"5df07007198989c622f5d41de8d703e7bef3d0e79d62e24332ee739a452af62a"}]}},{"name":"dhcp-client","version":"4.3.6-40.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dhcp-client:dhcp-client:4.3.6-40.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dhcp-client:4.3.6-40.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dhcp-client@12:4.3.6-40.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dhcp-client","version":"4.3.6","epoch":12,"architecture":"x86_64","release":"40.el8","sourceRpm":"dhcp-4.3.6-40.el8.src.rpm","size":530732,"license":"ISC","vendor":"CentOS","files":[{"path":"/etc/NetworkManager/dispatcher.d/11-dhclient","mode":33261,"size":1062,"sha256":"752fff425446e7e9007d663775cfc87a2d63e5ecb9a723350c7481c8c02e0f99"},{"path":"/etc/dhcp/dhclient.conf","mode":33188,"size":513,"sha256":"2fdf1f93579dc1e3cbf9518ece2e3eda50a385dc63b070eb63f5f7b794149410"},{"path":"/usr/lib/.build-id/a7/524cd73bb316cc93d85bebe058dd31cafa8ef2","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib64/pm-utils/sleep.d/56dhclient","mode":33261,"size":1810,"sha256":"687344e144ab436a393163defc54aa2cf85bbc16aab321f982dee63624c1ec31"},{"path":"/usr/sbin/dhclient","mode":33261,"size":464776,"sha256":"c863d4ce82ecaa0f68909dd592d57a618e226d12eb9a127a42722770e57f7b4a"},{"path":"/usr/sbin/dhclient-script","mode":33261,"size":33646,"sha256":"38c2791c43539e7c79e1772a412d7c211bf75ad78303d64a0d68c5bff7cad765"}]}},{"name":"dhcp-common","version":"4.3.6-40.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dhcp-common:dhcp-common:4.3.6-40.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dhcp-common:4.3.6-40.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dhcp-common@12:4.3.6-40.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"dhcp-common","version":"4.3.6","epoch":12,"architecture":"noarch","release":"40.el8","sourceRpm":"dhcp-4.3.6-40.el8.src.rpm","size":301814,"license":"ISC","vendor":"CentOS","files":[{"path":"/usr/share/licenses/dhcp-common/LICENSE","mode":33188,"size":1050,"sha256":"dd7ae2201c0c11c3c1e2510d731c67b2f4bc8ba735707d7348ddd65f7b598562"}]}},{"name":"dhcp-libs","version":"4.3.6-40.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dhcp-libs:dhcp-libs:4.3.6-40.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dhcp-libs:4.3.6-40.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dhcp-libs@12:4.3.6-40.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dhcp-libs","version":"4.3.6","epoch":12,"architecture":"x86_64","release":"40.el8","sourceRpm":"dhcp-4.3.6-40.el8.src.rpm","size":161256,"license":"ISC","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/58/c3853c4468f67df8432255069575c73692701a","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/bf/fc46beebf1d7764177eacc19ded981b99ad29b","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libdhcpctl.so.0","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libdhcpctl.so.0.0.0","mode":33261,"size":24528,"sha256":"e280318b2b8f8b1ac2db87c9e81913260094812b2185d73f88c6339954ae3482"},{"path":"/usr/lib64/libomapi.so.0","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libomapi.so.0.0.0","mode":33261,"size":136728,"sha256":"127ae1d67d11dcd0b9b06291f5a03dd99308e41b5c44db250d21565d994b5497"}]}},{"name":"dnf","version":"4.2.17-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dnf:dnf:4.2.17-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dnf:4.2.17-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dnf@0:4.2.17-6.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"dnf","version":"4.2.17","epoch":0,"architecture":"noarch","release":"6.el8","sourceRpm":"dnf-4.2.17-6.el8.src.rpm","size":1670640,"license":"GPLv2+ and GPLv2 and GPL","vendor":"CentOS","files":[{"path":"/usr/bin/dnf","mode":41471,"size":5,"sha256":""},{"path":"/usr/lib/systemd/system/dnf-makecache.service","mode":33188,"size":457,"sha256":"64fd20c5163f9a310c2e0211e53d4f731285535a4798c6c074f16c1e6680304d"},{"path":"/usr/lib/systemd/system/dnf-makecache.timer","mode":33188,"size":301,"sha256":"dd43cbac42a225465b2fd64c5a58590e4d582691fe663637e4aac5df6858810b"},{"path":"/usr/share/bash-completion/completions/dnf","mode":33188,"size":9556,"sha256":"bafd2578ee83f3cf8cfd8f1ec803fccaff531347d26f32d2ffde16320a4a34c1"},{"path":"/usr/share/locale/en_GB/LC_MESSAGES/dnf.mo","mode":33188,"size":24363,"sha256":"ac7ab63dc495e79c62dddc5a4e19222280d040606b742a02f08490395001ba89"}]}},{"name":"dnf-data","version":"4.2.17-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dnf-data:dnf-data:4.2.17-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dnf-data:4.2.17-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dnf-data@0:4.2.17-6.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"dnf-data","version":"4.2.17","epoch":0,"architecture":"noarch","release":"6.el8","sourceRpm":"dnf-4.2.17-6.el8.src.rpm","size":36253,"license":"GPLv2+ and GPLv2 and GPL","vendor":"CentOS","files":[{"path":"/etc/dnf/dnf.conf","mode":33188,"size":108,"sha256":"1557f960a39d444375a3a28994eb082fdab2887a16da2b677ba181658f2512b7"},{"path":"/etc/dnf/protected.d/dnf.conf","mode":33188,"size":4,"sha256":"b6f0d7b9f4d69e86833ec77802d3af8e5ecc5b9820e1fe0d774b7922e1da57fe"},{"path":"/etc/libreport/events.d/collect_dnf.conf","mode":33188,"size":813,"sha256":"cc0feca59af66ea18656fc5774b78f586b97864965cf1add75b3f9944678e999"},{"path":"/etc/logrotate.d/dnf","mode":33188,"size":212,"sha256":"32fc5ad9665f8bf30720d1774d16d79762f551c8cc2924ff47f4996e3ca0f458"},{"path":"/usr/lib/tmpfiles.d/dnf.conf","mode":33188,"size":164,"sha256":"cbaff13faea6f5eae694d5d45ca022b90597c8325be2919920b519bb67980a87"},{"path":"/usr/share/licenses/dnf/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/dnf/PACKAGE-LICENSING","mode":33188,"size":415,"sha256":"c06f0c7eb611c6d77892bd02832dcae01c9fac292ccd55d205924388e178a35c"}]}},{"name":"dracut","version":"049-70.git20200228.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dracut:dracut:049-70.git20200228.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dracut:049-70.git20200228.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dracut@0:049-70.git20200228.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dracut","version":"049","epoch":0,"architecture":"x86_64","release":"70.git20200228.el8","sourceRpm":"dracut-049-70.git20200228.el8.src.rpm","size":1046582,"license":"GPLv2+ and LGPLv2+","vendor":"CentOS","files":[{"path":"/etc/dracut.conf","mode":33188,"size":117,"sha256":"e157d2c2ca987ece9fb284b2def670904f959dce0ca1f82076dfbf6858516fcb"},{"path":"/usr/bin/dracut","mode":33261,"size":70203,"sha256":"1500f8cff39ddfc65b4cbdd5a58f06412515b33fdf4f8d380616455685b4316b"},{"path":"/usr/bin/lsinitrd","mode":33261,"size":8232,"sha256":"6d1b027df2ae1199199492c18eab227e6ff7523f6b9770d2d1436d42780117dd"},{"path":"/usr/bin/mkinitrd","mode":33261,"size":6585,"sha256":"9d9b43cade9a6644647ce6fa3bf73ef675ac51e4cfed7d0d96fde5359c157668"},{"path":"/usr/lib/.build-id/1e/55d75084ba135e504f0e7ed3897f1fd10f1f67","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/d6/26c1bca20342274999c83686891f2eab0f8174","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/dracut/dracut-functions","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib/dracut/dracut-functions.sh","mode":33261,"size":20145,"sha256":"971ad97874b3ff532cef154d2242b028b008615291cb4df5138f357bdfc3b444"},{"path":"/usr/lib/dracut/dracut-init.sh","mode":33261,"size":34539,"sha256":"f8855a82fe8f7084af9c42a4d86fb643e51e80c1f09e6079542f08a81ba8ca6f"},{"path":"/usr/lib/dracut/dracut-initramfs-restore","mode":33261,"size":1277,"sha256":"aa58a6625b2f08677060bad5f3c34198e75e4688abf7c65af54b250f268ca6db"},{"path":"/usr/lib/dracut/dracut-install","mode":33261,"size":76080,"sha256":"99912eabb1a47f22cba93b736e8103893f33d5bc5d99feb9ab90180ed0cc58f5"},{"path":"/usr/lib/dracut/dracut-logger.sh","mode":33261,"size":13304,"sha256":"f4af8626e7746cb72e4d1293dd8cd39f67809dfb840ee422dc56308c86495da0"},{"path":"/usr/lib/dracut/dracut-version.sh","mode":33188,"size":38,"sha256":"5e236bb428b849920c64ac140039b44a964773744d492c16dafba4c71509993f"},{"path":"/usr/lib/dracut/dracut.conf.d/01-dist.conf","mode":33188,"size":536,"sha256":"10456148cc42a37de5ab9c3d630a5dbaebdc426cf5b1138b0277a8ca68ae3413"},{"path":"/usr/lib/dracut/modules.d/00bash/module-setup.sh","mode":33261,"size":361,"sha256":"a6adccf4b41d02689a2f9367d412cffba0ad56d1cb0b0c9ada1062ea2f390c3f"},{"path":"/usr/lib/dracut/modules.d/00systemd/module-setup.sh","mode":33261,"size":9456,"sha256":"696e909c8ef29dcbbf8c33c9fffd3c4781127304806ed69bbc91bbe5734ef907"},{"path":"/usr/lib/dracut/modules.d/00warpclock/module-setup.sh","mode":33188,"size":662,"sha256":"9d6177941826f62c419314294f344c5237bf61af068bcdeb9529aa06c77ce409"},{"path":"/usr/lib/dracut/modules.d/00warpclock/warpclock.sh","mode":33188,"size":151,"sha256":"dfe9adfa7de5d19e9c862ea2609c3faf56052e8607080f6608c35dc187b21551"},{"path":"/usr/lib/dracut/modules.d/01fips/fips-boot.sh","mode":33261,"size":265,"sha256":"ab106047f36befd5e1074ff40b9fd0f28a772df2eabf03f3b2006809ad847848"},{"path":"/usr/lib/dracut/modules.d/01fips/fips-load-crypto.sh","mode":33188,"size":209,"sha256":"79e97373b6136bc2f55e0f532eb62e2c6c45e883e520ca62e98641361bce33f4"},{"path":"/usr/lib/dracut/modules.d/01fips/fips-noboot.sh","mode":33261,"size":244,"sha256":"bbf0f3b783e2dd8531a2060759d2ddf09f602625c4b08a621f965b2774bf9a61"},{"path":"/usr/lib/dracut/modules.d/01fips/fips.sh","mode":33261,"size":4707,"sha256":"e23f12adf28b7c52f16712f764b6c6ea957355678b219d8c9e27ee1b2399fa60"},{"path":"/usr/lib/dracut/modules.d/01fips/module-setup.sh","mode":33261,"size":2433,"sha256":"9ad6d166f019c9b975fd3a96ecd3eaedec627666a1c9f734315c4a983cbdf927"},{"path":"/usr/lib/dracut/modules.d/01systemd-initrd/module-setup.sh","mode":33261,"size":1862,"sha256":"05e6fefbfdd29cc4c6fea2778d9f08e37a60eee2f0f223c7d0585ecbae54e179"},{"path":"/usr/lib/dracut/modules.d/03modsign/load-modsign-keys.sh","mode":33261,"size":234,"sha256":"6011f2fe5b1fe5b4b8a74d4de4dfb9bb056ce30649a8150bb9c572db17163162"},{"path":"/usr/lib/dracut/modules.d/03modsign/module-setup.sh","mode":33261,"size":728,"sha256":"4f2d632dc5e53fecc193d7110ca4ee1222fe91a7021dd576ad3d67ff63f1c030"},{"path":"/usr/lib/dracut/modules.d/03rescue/module-setup.sh","mode":33261,"size":377,"sha256":"7069667ddc37b73afc94db34f15d81628dfc6e7ed24a39dde463edd025ae45a2"},{"path":"/usr/lib/dracut/modules.d/04watchdog/module-setup.sh","mode":33261,"size":2876,"sha256":"241b6c197bfa7dbe45d26f5aa20fca3bb789ce763b462c7f4b92600bf4266c30"},{"path":"/usr/lib/dracut/modules.d/04watchdog/watchdog-stop.sh","mode":33261,"size":61,"sha256":"76aea04877c2856545349293a98d0c2687a8add94965e2fc3b1f63460756bf07"},{"path":"/usr/lib/dracut/modules.d/04watchdog/watchdog.sh","mode":33261,"size":245,"sha256":"b595ece211ee978dbb81394df222126e885fda3c2c0f1ffb0b775b87495f8b19"},{"path":"/usr/lib/dracut/modules.d/05busybox/module-setup.sh","mode":33261,"size":699,"sha256":"dd2bc517a7b83e519da5d8dfb15a71f210a30329883c16950a580897faf172af"},{"path":"/usr/lib/dracut/modules.d/06rngd/module-setup.sh","mode":33188,"size":1288,"sha256":"8528c88669859fc019fd0e67072f6d001f595861cc95d7373342c4a64fe9e849"},{"path":"/usr/lib/dracut/modules.d/06rngd/rngd.service","mode":33188,"size":147,"sha256":"a8cfb816ee800367605eff9cbd56e7e71cf2ff93cf629c1b037316e2b089c7f3"},{"path":"/usr/lib/dracut/modules.d/10i18n/10-console.rules","mode":33188,"size":168,"sha256":"98ccbc8f85a1dea5c3d371b86d7a7b781019d840fa06786e3765d31f9dd4bdca"},{"path":"/usr/lib/dracut/modules.d/10i18n/README","mode":33188,"size":4420,"sha256":"c0d384430249c51269fd17cd96602ad8b878fda1642883555264606712754e1f"},{"path":"/usr/lib/dracut/modules.d/10i18n/console_init.sh","mode":33261,"size":1612,"sha256":"338fd522c9375ecee7516e6a121b80f75be5fce2f460bc83755d85a53c057bb1"},{"path":"/usr/lib/dracut/modules.d/10i18n/module-setup.sh","mode":33261,"size":8308,"sha256":"7d6822992ce382715146b92af2acc2f0bbae9b6d48e7091840d90ce6e1c34166"},{"path":"/usr/lib/dracut/modules.d/10i18n/parse-i18n.sh","mode":33261,"size":1159,"sha256":"b5ffa9074fd0983d5caee39f7f9a0f016d2bd96436ab365487e511895c8c42a7"},{"path":"/usr/lib/dracut/modules.d/30convertfs/convertfs.sh","mode":33261,"size":6035,"sha256":"410141eddb24c1cd7ec58d8286ff474642e5fc0f05dc573c49a02bb6ba12eecf"},{"path":"/usr/lib/dracut/modules.d/30convertfs/do-convertfs.sh","mode":33261,"size":194,"sha256":"ccbbc718b1beb9400fc74a413b9be6340d19087f2279c72d5c60902b4404c96c"},{"path":"/usr/lib/dracut/modules.d/30convertfs/module-setup.sh","mode":33261,"size":336,"sha256":"65b77ee7310ed758ccd4c2a406292ec425dcccbe0f37a8904da225cffc68c1ad"},{"path":"/usr/lib/dracut/modules.d/45url-lib/module-setup.sh","mode":33261,"size":3051,"sha256":"7c455ba241bf2fb39b7da22534617700f95373665750b249b9af461f5739ca9e"},{"path":"/usr/lib/dracut/modules.d/45url-lib/url-lib.sh","mode":33261,"size":5028,"sha256":"6bab8657e82cde89deb06539a4624c93d3e529d15da3575bb135781b7a78868b"},{"path":"/usr/lib/dracut/modules.d/50drm/module-setup.sh","mode":33261,"size":1322,"sha256":"d7488ecd26c70866929439b3c4937e42f104b708792f937195013ad5c5d916c9"},{"path":"/usr/lib/dracut/modules.d/50plymouth/module-setup.sh","mode":33261,"size":1240,"sha256":"c1f29ef918a3adc00abaa12f04a15206e520334bdc7b06eb15831e5dc93f1af5"},{"path":"/usr/lib/dracut/modules.d/50plymouth/plymouth-emergency.sh","mode":33261,"size":51,"sha256":"068a6d7ffd97514b950c19882451252efe95ed09b4480d990233dc1b7d23497d"},{"path":"/usr/lib/dracut/modules.d/50plymouth/plymouth-newroot.sh","mode":33261,"size":113,"sha256":"e64a7fd39db017ff11eebe61abc75a50995fa641f3e64898cfc90c0b37ee198a"},{"path":"/usr/lib/dracut/modules.d/50plymouth/plymouth-populate-initrd.sh","mode":33261,"size":1454,"sha256":"7d98d410f12374263e0bdc1cb8f011a935682f9c125d27cae02ed61ad8d62daf"},{"path":"/usr/lib/dracut/modules.d/50plymouth/plymouth-pretrigger.sh","mode":33261,"size":1177,"sha256":"33173643d0086dfc5d5f160972fbcaf25b94be02507fa28e1d27db2d1b4b4c5e"},{"path":"/usr/lib/dracut/modules.d/80lvmmerge/README.md","mode":33188,"size":2093,"sha256":"a291d0fefe068fdef9892965fdbdbdae63da9781ed425e542753458074906252"},{"path":"/usr/lib/dracut/modules.d/80lvmmerge/lvmmerge.sh","mode":33261,"size":3087,"sha256":"0d7cf367dced801a4c1ed7acd6f4c948f058314f4c84bd6907b5786c4b5c4f5f"},{"path":"/usr/lib/dracut/modules.d/80lvmmerge/module-setup.sh","mode":33261,"size":424,"sha256":"e004ad99fac4cdf0dce19162a9a3849397853df39c913d796195cf755ecccf0a"},{"path":"/usr/lib/dracut/modules.d/90btrfs/80-btrfs.rules","mode":33188,"size":270,"sha256":"7fb1c1a23de302d82623d960eb4201993f12061c63608ab8912f20c39882ac43"},{"path":"/usr/lib/dracut/modules.d/90btrfs/btrfs_device_ready.sh","mode":33261,"size":467,"sha256":"5ecf194cc31161970b7af9c684c585b08141b060e889489aa39be2173dae0543"},{"path":"/usr/lib/dracut/modules.d/90btrfs/btrfs_finished.sh","mode":33261,"size":597,"sha256":"9aeddb8df7021d5133a67a1ca77547119aed96a6b04b126e7c72baef0d4fabdf"},{"path":"/usr/lib/dracut/modules.d/90btrfs/btrfs_timeout.sh","mode":33261,"size":142,"sha256":"c2dfb621735e6bd7a5141c3a7e5baa080ba2946346a7a76d993616c5670fcd25"},{"path":"/usr/lib/dracut/modules.d/90btrfs/module-setup.sh","mode":33261,"size":1238,"sha256":"61ee044731cd09fa98e684507c679050ac56c1eb83686a0d8db66926217b850f"},{"path":"/usr/lib/dracut/modules.d/90crypt/crypt-cleanup.sh","mode":33261,"size":442,"sha256":"f268ba9c0ee4aa392d76676e67d3cd054f4dfb6c3bbefa700de5beb368a8fdba"},{"path":"/usr/lib/dracut/modules.d/90crypt/crypt-lib.sh","mode":33261,"size":7651,"sha256":"9c8b73cf73071e262d5325917d716ee30d9a100b12db183db393aea14b14ffbc"},{"path":"/usr/lib/dracut/modules.d/90crypt/crypt-run-generator.sh","mode":33261,"size":770,"sha256":"7ff626b45e370aece5181a34ca21ad90a94f4648427a19dad75460b07c787ae4"},{"path":"/usr/lib/dracut/modules.d/90crypt/cryptroot-ask.sh","mode":33261,"size":4870,"sha256":"06fc60af8bc9e38c06d9bc7d2d8dfeabd368013912fd0aef26bd0d5360e2702c"},{"path":"/usr/lib/dracut/modules.d/90crypt/module-setup.sh","mode":33261,"size":4431,"sha256":"dffbe0ffd6843d9ec4582e3446c6860ed96b9bb25164921d5773146facbbb295"},{"path":"/usr/lib/dracut/modules.d/90crypt/parse-crypt.sh","mode":33261,"size":7137,"sha256":"e31f359164fdabb5edc1c9cbe2fd68c1401a35ddfb2876e9220d87309b49c75d"},{"path":"/usr/lib/dracut/modules.d/90crypt/parse-keydev.sh","mode":33261,"size":1377,"sha256":"163a14e9a155e43a30a55125bbd1043bf4137fb6d3980eda0ba26499d8f63e61"},{"path":"/usr/lib/dracut/modules.d/90crypt/probe-keydev.sh","mode":33261,"size":382,"sha256":"23cecbaa79f39ec1a13ad1570f06782114a3b803e963ce3c54b4037f638fd9cf"},{"path":"/usr/lib/dracut/modules.d/90dm/11-dm.rules","mode":33188,"size":142,"sha256":"7a42ae0582bec603f18aa490e21550088680481f15206213718a6b8b84f610bf"},{"path":"/usr/lib/dracut/modules.d/90dm/59-persistent-storage-dm.rules","mode":33188,"size":669,"sha256":"91d4f5c41e6191dd30cc851b154a41f871053bc0ab85992d0bae464ee2ed855f"},{"path":"/usr/lib/dracut/modules.d/90dm/dm-pre-udev.sh","mode":33261,"size":102,"sha256":"23a5e0f5054afb84286cf319d58ee06cb9537619e705aadee47e56f79ac702fb"},{"path":"/usr/lib/dracut/modules.d/90dm/dm-shutdown.sh","mode":33261,"size":1237,"sha256":"4bbb54eb6d834f89ab4603631b2ca8328ae26ca0b9eda92124c42845a56bcffb"},{"path":"/usr/lib/dracut/modules.d/90dm/module-setup.sh","mode":33261,"size":1005,"sha256":"2b115b9ddf19aba446f0b34a999786907662108772e6a79edfe1ddd81f8fffb3"},{"path":"/usr/lib/dracut/modules.d/90dmraid/61-dmraid-imsm.rules","mode":33188,"size":921,"sha256":"8c6381796208387904bb2f998328f0847e08ea7832d9ceff9314cd08ae3c1842"},{"path":"/usr/lib/dracut/modules.d/90dmraid/dmraid.sh","mode":33261,"size":1206,"sha256":"429642df7abdb1585b4e58fed265434f2fb722df070132bdb99bc41bdc23f807"},{"path":"/usr/lib/dracut/modules.d/90dmraid/module-setup.sh","mode":33261,"size":2123,"sha256":"b2165139e88fb8d5aca18643fdb3652d41901d8d1a006204e092ab861d46ddcf"},{"path":"/usr/lib/dracut/modules.d/90dmraid/parse-dm.sh","mode":33261,"size":826,"sha256":"240639e707371bb1e13bdac14e8f9724097b2596242af0b86d611f5ebd922d9d"},{"path":"/usr/lib/dracut/modules.d/90kernel-modules-extra/module-setup.sh","mode":33261,"size":5101,"sha256":"878ac313c5d2058e486d69ddab7c20ec50e62c258d176d9638654d0b634762f3"},{"path":"/usr/lib/dracut/modules.d/90kernel-modules/insmodpost.sh","mode":33261,"size":193,"sha256":"25d5ca59bb50b7ec69432fc190999e33d68918960ec9d81c266b0d52f7829078"},{"path":"/usr/lib/dracut/modules.d/90kernel-modules/module-setup.sh","mode":33261,"size":3463,"sha256":"8235deb08fed8c5d5c4e52af71ca3948ea18169895416eecd821467b023414db"},{"path":"/usr/lib/dracut/modules.d/90kernel-modules/parse-kernel.sh","mode":33261,"size":921,"sha256":"1f801f74072ea53d9b24c0ad7a99fdfc25177ad57a26d63ac998eb93ddd30c5a"},{"path":"/usr/lib/dracut/modules.d/90lvm/64-lvm.rules","mode":33188,"size":775,"sha256":"ff387389b1bb61e28f5e7e97db78d2ccf045bc4de4bc501f6915ae008de7a5cf"},{"path":"/usr/lib/dracut/modules.d/90lvm/lvm_scan.sh","mode":33261,"size":3527,"sha256":"9dec15d8fde9402dd1fb78f905528c83dbf129c7d71bd5e466b7a64d41b02dd5"},{"path":"/usr/lib/dracut/modules.d/90lvm/module-setup.sh","mode":33261,"size":5307,"sha256":"99cc8231691680a77f7567177fa45056ec19ba66ea6e3a0bd7f970cb1157c7e2"},{"path":"/usr/lib/dracut/modules.d/90lvm/parse-lvm.sh","mode":33261,"size":487,"sha256":"288924e47a438cafd49b31271bf72a4136dbf035336b7e6d6f360e4715df013d"},{"path":"/usr/lib/dracut/modules.d/90mdraid/59-persistent-storage-md.rules","mode":33188,"size":842,"sha256":"c754d8962754ed9d337605d5df02d17d07cd3312fcaeb5306b8508a59e29886e"},{"path":"/usr/lib/dracut/modules.d/90mdraid/65-md-incremental-imsm.rules","mode":33188,"size":1475,"sha256":"5847cf3d0ac33d4db60abe8f1cffb27f39acfcf87ca0b5b6cb989f9a8df78873"},{"path":"/usr/lib/dracut/modules.d/90mdraid/md-noddf.sh","mode":33261,"size":88,"sha256":"6c8b3323154fcae13c7de77bb62ec87646d30ff90c0c47eb0d0dc21737abd67e"},{"path":"/usr/lib/dracut/modules.d/90mdraid/md-noimsm.sh","mode":33261,"size":90,"sha256":"d190ae7149ec0f834561141e3036fda78738beda1a8a9458c4e22b0ad253fb02"},{"path":"/usr/lib/dracut/modules.d/90mdraid/md-shutdown.sh","mode":33261,"size":563,"sha256":"7e52969aaf37a0cf129c3810a22a3a5c67f71d9da8cd8316abd4a998e756ae62"},{"path":"/usr/lib/dracut/modules.d/90mdraid/mdmon-pre-shutdown.sh","mode":33261,"size":229,"sha256":"ea5a56d41ca70906607fd2b89e1cf0471200b31628a9d420eabe36ed7f0fe3c7"},{"path":"/usr/lib/dracut/modules.d/90mdraid/mdmon-pre-udev.sh","mode":33261,"size":130,"sha256":"efc21f5ed3d19f3489e659605e757fb40e94a70694dfc36c5c196f6a6fe8f5f3"},{"path":"/usr/lib/dracut/modules.d/90mdraid/mdraid-cleanup.sh","mode":33261,"size":598,"sha256":"32701f39332ef0a0d77100fac88e6bd3e94160897cf4a52f20eff8d40320b2fd"},{"path":"/usr/lib/dracut/modules.d/90mdraid/mdraid-needshutdown.sh","mode":33261,"size":155,"sha256":"fdf1d0e3ba434cc1c323aef6a455bbb627042ede0ea6f5589229e754ba32d27a"},{"path":"/usr/lib/dracut/modules.d/90mdraid/mdraid-waitclean.sh","mode":33261,"size":800,"sha256":"8f83128acd1964e79d6fd0b08b5df2ac6cac4b14e83be34ed882e372250dd331"},{"path":"/usr/lib/dracut/modules.d/90mdraid/mdraid_start.sh","mode":33261,"size":1993,"sha256":"967fadb9a863f29e80f3751ecb27cc9b3ef28769fef517e3e3f4beb5006d3c9c"},{"path":"/usr/lib/dracut/modules.d/90mdraid/module-setup.sh","mode":33261,"size":4493,"sha256":"716388816abff8974b328bb7d44b338c96b1551f2fd1881aa8be005e2d81ba51"},{"path":"/usr/lib/dracut/modules.d/90mdraid/parse-md.sh","mode":33261,"size":2683,"sha256":"17fdc2f8f13c0a6bbb4c3059eb5cb5d7c2f61afd65eb8133c34d7afaf46e203c"},{"path":"/usr/lib/dracut/modules.d/90multipath/module-setup.sh","mode":33261,"size":3352,"sha256":"55403c828b2107bb8e8549bc8d2648f38406d0510d797c730435cfbaa915e57d"},{"path":"/usr/lib/dracut/modules.d/90multipath/multipath-shutdown.sh","mode":33261,"size":172,"sha256":"9f87ddc35ab2f29a6c556af8ec1ccbe6f10684898e2cd1a3f224336eae9473eb"},{"path":"/usr/lib/dracut/modules.d/90multipath/multipathd-needshutdown.sh","mode":33261,"size":162,"sha256":"bf0debd877642edee3c836e3306c67b13108b7c62084a0378146972ea9bd4887"},{"path":"/usr/lib/dracut/modules.d/90multipath/multipathd-stop.sh","mode":33261,"size":237,"sha256":"c2c3e00ac95c6983452c9c2e429f5150ac2d96122a785716f1cf25b688fe8826"},{"path":"/usr/lib/dracut/modules.d/90multipath/multipathd.service","mode":33188,"size":722,"sha256":"9770d3e53522ad066cb4692d14cce39c215a7b4ca081d00aeb7362ee4b2c919f"},{"path":"/usr/lib/dracut/modules.d/90multipath/multipathd.sh","mode":33261,"size":242,"sha256":"aa3c410b1267a9a45ae2a7d9f9fe245739fc0a5801e717904da844b64ab297ff"},{"path":"/usr/lib/dracut/modules.d/90qemu/module-setup.sh","mode":33261,"size":1026,"sha256":"dca9cdb7aa2b960d57bc6b26bc5e5ad0026260ce41035369d59b96a06de79e0a"},{"path":"/usr/lib/dracut/modules.d/90stratis/module-setup.sh","mode":33261,"size":901,"sha256":"fe8122978948f2fda3d3c82109ab5183d9575f4081139e94db8dbd1c56f3b340"},{"path":"/usr/lib/dracut/modules.d/90stratis/stratisd-init.service","mode":33188,"size":334,"sha256":"4523df4f0fa4f38d9acc1303b7a7dfcac1601f9f92f11783f61a460793e384c5"},{"path":"/usr/lib/dracut/modules.d/90stratis/stratisd-start.sh","mode":33261,"size":51,"sha256":"14301e58f2aee1af313a08d5967946140e4c9391db39d8784888b9a20c91ebff"},{"path":"/usr/lib/dracut/modules.d/90stratis/stratisd-stop.sh","mode":33261,"size":118,"sha256":"3fe47afe0d86eb96003176083d44e441aab06af93a5e936787cfc27e374e66b6"},{"path":"/usr/lib/dracut/modules.d/91crypt-gpg/README","mode":33188,"size":2595,"sha256":"a0ad975623f32470e53a06d077ad4af10378b2827c0676154711fb55e1936df4"},{"path":"/usr/lib/dracut/modules.d/91crypt-gpg/crypt-gpg-lib.sh","mode":33261,"size":2618,"sha256":"fb42068328d50f4ed57e7a94d3024106b6102b0fb445b921d5fe502c114649bd"},{"path":"/usr/lib/dracut/modules.d/91crypt-gpg/module-setup.sh","mode":33261,"size":1509,"sha256":"fc340df813a342cfe198bae3e78d71663100e992b9a8db1907e13667917d5e39"},{"path":"/usr/lib/dracut/modules.d/91crypt-loop/crypt-loop-lib.sh","mode":33261,"size":1278,"sha256":"b2465599538e05b0a58bbed5cfd19bcb21064c3f96c374d600606baaf18357d0"},{"path":"/usr/lib/dracut/modules.d/91crypt-loop/module-setup.sh","mode":33261,"size":375,"sha256":"adf4b89467fb3edb1a9b577b9de60545d728b81c0aad4bf3c30bdf7b18785b30"},{"path":"/usr/lib/dracut/modules.d/95debug/module-setup.sh","mode":33261,"size":550,"sha256":"fd35fcd68f3166357f68206be28f78c91fda95e36a9ff3c38eb6e789e8a0c80d"},{"path":"/usr/lib/dracut/modules.d/95fstab-sys/module-setup.sh","mode":33261,"size":305,"sha256":"ced43c05074c82fa66161c2a8eebbca29990e456fcdbf1ab88284de1535ab162"},{"path":"/usr/lib/dracut/modules.d/95fstab-sys/mount-sys.sh","mode":33261,"size":1285,"sha256":"94c390fad5bce771ac3eb7aec35f3fc5c82214e568e8bf8db500888fcdcb8ce6"},{"path":"/usr/lib/dracut/modules.d/95lunmask/fc_transport_scan_lun.sh","mode":33261,"size":562,"sha256":"63ae959ddf83bcf0f51224421c331748f05d325d3c664f1d8ca2a054dab47e69"},{"path":"/usr/lib/dracut/modules.d/95lunmask/module-setup.sh","mode":33261,"size":2254,"sha256":"698730cfd3da0223f93ba994e036a42b55691547ee398c1628035dea132ff310"},{"path":"/usr/lib/dracut/modules.d/95lunmask/parse-lunmask.sh","mode":33261,"size":1227,"sha256":"85389966c2af9330d5904c64fe44f34b35504a07aac8cc55d3972cfd56ee7add"},{"path":"/usr/lib/dracut/modules.d/95lunmask/sas_transport_scan_lun.sh","mode":33261,"size":568,"sha256":"f972c64778ced3f6002a990f8ec39cfdf8f06d5e53b7ab0f983f442e3e71f1a8"},{"path":"/usr/lib/dracut/modules.d/95resume/module-setup.sh","mode":33261,"size":1920,"sha256":"99476ca9b74425b80fcc3140b6414070b58bcd96b616764b4a8f6a5463580e06"},{"path":"/usr/lib/dracut/modules.d/95resume/parse-resume.sh","mode":33261,"size":3623,"sha256":"03058ec68c5c64820552d73b5dd1ae9d1c472a97c03a7fb3a78f56dd7731d820"},{"path":"/usr/lib/dracut/modules.d/95resume/resume.sh","mode":33261,"size":560,"sha256":"23857edf2e0488b9b8fde15c80ca664602b1827ba453166f395b5d2ba248a0d0"},{"path":"/usr/lib/dracut/modules.d/95rootfs-block/block-genrules.sh","mode":33261,"size":469,"sha256":"fbd41278c7fe9e833b86686cd057921732bc45590dea6112fa244b6e3528f019"},{"path":"/usr/lib/dracut/modules.d/95rootfs-block/module-setup.sh","mode":33261,"size":2300,"sha256":"e0d8e6b739be83302f316675a9b2adcf9f7832452f96b5d4498222cce5f0f537"},{"path":"/usr/lib/dracut/modules.d/95rootfs-block/mount-root.sh","mode":33261,"size":4422,"sha256":"cb6d60ff4ef71bd8600ec70273290fbdf8df9b41fbdc2f32371f07665691193f"},{"path":"/usr/lib/dracut/modules.d/95rootfs-block/parse-block.sh","mode":33261,"size":924,"sha256":"7320f0af902ab760b530d44c4c4d6f028c370077a06f0a7058b33e1fd7f7ae89"},{"path":"/usr/lib/dracut/modules.d/95rootfs-block/rootfallback.sh","mode":33261,"size":1242,"sha256":"cbdf7ad4cb06eb04bb4d7e45b48b42556cba0b93185c4088336833f66626af1a"},{"path":"/usr/lib/dracut/modules.d/95terminfo/module-setup.sh","mode":33261,"size":528,"sha256":"d5927c26d3321289a5044d7f1ffa371550fa1e164296c7d0365150d8d7def519"},{"path":"/usr/lib/dracut/modules.d/95udev-rules/59-persistent-storage.rules","mode":33188,"size":275,"sha256":"e5c736b763400c587499c0d64a908f8660a2e04987d82be72eee15433deea890"},{"path":"/usr/lib/dracut/modules.d/95udev-rules/61-persistent-storage.rules","mode":33188,"size":1019,"sha256":"384a0a3291a6b71fb7f4957dead3061d1ac88d2fe14d386abab77825d595d4c7"},{"path":"/usr/lib/dracut/modules.d/95udev-rules/load-modules.sh","mode":33261,"size":78,"sha256":"06d33a413f92cb14ab30030934e40be6cd828c02dc4b6b6f1e41b9aa024cb435"},{"path":"/usr/lib/dracut/modules.d/95udev-rules/module-setup.sh","mode":33261,"size":3333,"sha256":"47f8aeb26f84c2c96de2e1d4a87c1d719c099b5a8ce52e46400b539ab52714c2"},{"path":"/usr/lib/dracut/modules.d/95virtfs/module-setup.sh","mode":33261,"size":970,"sha256":"3d0418c1fb1b0a0e005c82ee2bb2454d682f70b0e3ac8893d775895785cfd92a"},{"path":"/usr/lib/dracut/modules.d/95virtfs/mount-virtfs.sh","mode":33261,"size":1863,"sha256":"39fc1bc8b3a9dcf8605c654788ef72989d89d13d4fc09d8532b5de5b0c3749f7"},{"path":"/usr/lib/dracut/modules.d/95virtfs/parse-virtfs.sh","mode":33261,"size":93,"sha256":"09304b2c81c40ea102aaa8770391afb47c777c085177929744abdfd1243052c3"},{"path":"/usr/lib/dracut/modules.d/97biosdevname/module-setup.sh","mode":33261,"size":287,"sha256":"64fff65984ee187f2959465731b8a41a20e9a3ade1d0f4c409106814d0ee2183"},{"path":"/usr/lib/dracut/modules.d/97biosdevname/parse-biosdevname.sh","mode":33261,"size":309,"sha256":"72136ca0c791dface5d01e3dc0e3d42bc1111e09a1b5429d9421ef503294c5f0"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-cmdline-ask.service","mode":33188,"size":847,"sha256":"b01a035992525fd3680310e4556503ca8f53249978018151bcdc857a7194adc4"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-cmdline-ask.sh","mode":33261,"size":418,"sha256":"bc7bb84cb4de8fdebf055be3a772af5e5eee01a7409d6c1b33f15d305f0201f1"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-cmdline.service","mode":33188,"size":904,"sha256":"c9c806f6e7efc1b7933892cc4d86fb1318e5141a8cbd8e1b77590ea42e1b9855"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-cmdline.service.8","mode":33188,"size":1555,"sha256":"b503aa2ec458dfcb34cf23da89cff41996bc688de182ba241a7cc136ce1bd1ee"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-cmdline.service.8.asc","mode":33188,"size":442,"sha256":"ec1b78fdbb20f52a8e37a14eded89ddea853e5205d9378596a3c9da423bcfb6e"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-cmdline.sh","mode":33261,"size":2662,"sha256":"63d05df86482757f42f7e0eef39d197bd28726803744feb3f84bf48e408f0c8e"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-emergency.service","mode":33188,"size":681,"sha256":"7d505421eee056a93a489764cd5f68083c83ec78f0ca5ec5035e42b39f0e6928"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-emergency.sh","mode":33261,"size":1382,"sha256":"2328393b82fa4b95a43bc3dd1052bb2ba03e06af676467ef6a92c7bbf5739e86"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-initqueue.service","mode":33188,"size":821,"sha256":"a1b9a5bf1b08c7e6fcb6621fe6b76fdb20ad127b1867849d127cd60bb49d1abc"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-initqueue.service.8","mode":33188,"size":1550,"sha256":"2cec3bc099befdf15508185dea553a528815a6e8abb9fc1fc9217d425f71d916"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-initqueue.service.8.asc","mode":33188,"size":439,"sha256":"38dee5101c13beeb40f39acd69b7fae683c3c417e5e52465ab8f625ddd4adb8c"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-initqueue.sh","mode":33261,"size":2147,"sha256":"026d7583227eebc9872eb86483a6b99bea5c317741d5105b320d714d453ec5f6"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-mount.service","mode":33188,"size":793,"sha256":"05217fb2e241f23db679ca8d15422c60052e93e9412e45ac262ac61b523fe0ed"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-mount.service.8","mode":33188,"size":1531,"sha256":"cc9d2eaa0fe6a732a52607f509ff384188a9c8e45eb1c8b08425399b683f28ff"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-mount.service.8.asc","mode":33188,"size":416,"sha256":"0a7d49fb3a6afff1824819cbb2b2058005a8c82453e92dadc17178a86e966b5d"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-mount.sh","mode":33261,"size":1052,"sha256":"4d767d543ed9333a2a44d5c9b021d465820b69dc9d27d2180b1691cc9e7c3912"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-mount.service","mode":33188,"size":822,"sha256":"4e8752b103851e60adf1f1c60620975c53c2a74a1e362c8450c353d3806d18d0"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-mount.service.8","mode":33188,"size":1546,"sha256":"cc43ddb477d3b9fb139bde89f6b9f5f1203f76494362177f59766254d79f5223"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-mount.service.8.asc","mode":33188,"size":434,"sha256":"e77ce2e56c82a6a1c76210843576ab3ff111854339123303274076f7d0330ad3"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-mount.sh","mode":33261,"size":513,"sha256":"e76f2734522ab5e82248a28eb10a8238f211088199279b6dabfd5e3e6571fdf8"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-pivot.service","mode":33188,"size":1125,"sha256":"8b320d93a00beb019225664f3b9e6fa9df69d7bf642507602c33f9d8e0bb96a6"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-pivot.service.8","mode":33188,"size":1541,"sha256":"2b456d576624a748aeb11ff6bcae0b9b8817901a080c774a2a179e9889e61e4f"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-pivot.service.8.asc","mode":33188,"size":429,"sha256":"68110572014f7ec86475081e4af371e2354fc2ff2920d42144d111455cef26bd"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-pivot.sh","mode":33261,"size":924,"sha256":"e0360422b90b24ff5ab4788da49b2e324676878cf6268c9c533df957b91b201e"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-trigger.service","mode":33188,"size":914,"sha256":"2516aa88cb92e69739af5f81a01466fc7874f09b806bbd2ae6c5e26621e2aa5f"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-trigger.service.8","mode":33188,"size":1550,"sha256":"c366cc726eef5b80c795290692e36087a7f594eabe9e07483e9384559ea41f8e"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-trigger.service.8.asc","mode":33188,"size":440,"sha256":"b0bb8a4b3745aa7afb00f5f4257d82aa8abc32ce076896526fbc3e8a768d85b1"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-trigger.sh","mode":33261,"size":478,"sha256":"ac40a755302a0d52c23b9460599a043b077719bfba16f580e57a4ad75d0dc31f"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-udev.service","mode":33188,"size":993,"sha256":"46635578b0872a259e69a7d93ac56896bc08f938db83fd582f38506edd76902f"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-udev.service.8","mode":33188,"size":1537,"sha256":"e9fd46198e0365ef0f93d45a1ae9ee6a1e47835f5e290695007929da12a76b2e"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-udev.service.8.asc","mode":33188,"size":424,"sha256":"2ee85c29c1c70c50650d5d135edf23563e5210f6df6895a4dd69e1bec94bc161"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-pre-udev.sh","mode":33261,"size":1413,"sha256":"ccfe0d96219866993ce775da37f2367fab0e37a8c66434394d4d95a147a3b8ff"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-shutdown.service","mode":33188,"size":459,"sha256":"160766a970a0e6715aff9ff70f815c7131140f140bb383f002b71f6d4d5eaaee"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-shutdown.service.8","mode":33188,"size":3609,"sha256":"cae8c09e56330a36699174cfe1f9b647348a5ef87308a0e002f2d3491f41455e"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-shutdown.service.8.asc","mode":33188,"size":1689,"sha256":"97d85a9118750e95be31d008b08789c76d4dc2888bf1ceb96318424012c61e3b"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/dracut-tmpfiles.conf","mode":33188,"size":135,"sha256":"7a5a36daadea6cac469e69ba8005e7e153d49e46a6d53b0b33539d8eaaaaa717"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/emergency.service","mode":33188,"size":692,"sha256":"0ca89e1dd845a980fb568fa6b3b58c3866aab7475cd029cd405d9459f3f5fed7"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/module-setup.sh","mode":33261,"size":2095,"sha256":"4aaeec04c99fdcdb7cb915d8c131f32d1f9d441654deb1564e0746555eb446ab"},{"path":"/usr/lib/dracut/modules.d/98dracut-systemd/rootfs-generator.sh","mode":33261,"size":3746,"sha256":"2c9cbabacd3adaf728e931752a7199fe10777141f78fca7e64ebedf8249f900d"},{"path":"/usr/lib/dracut/modules.d/98ecryptfs/README","mode":33188,"size":2343,"sha256":"ce490eaaab6431e41c4c83d937161f7c4dcf0856fcb202850c91779afc12c4d2"},{"path":"/usr/lib/dracut/modules.d/98ecryptfs/ecryptfs-mount.sh","mode":33261,"size":2742,"sha256":"da2b75d317c6a048e8fe84928a65e40f9108067f202d591f57cc96304fb16768"},{"path":"/usr/lib/dracut/modules.d/98ecryptfs/module-setup.sh","mode":33261,"size":276,"sha256":"c78dacc9f923cf4d742a8ace79b76af52eed6b1e8c8d58b1cefe11f610624cf3"},{"path":"/usr/lib/dracut/modules.d/98pollcdrom/module-setup.sh","mode":33261,"size":199,"sha256":"7d081b60acf43f5c2b4fd52744bbab52f604a8801dccbcec46ac864ef7a02a9a"},{"path":"/usr/lib/dracut/modules.d/98pollcdrom/pollcdrom.sh","mode":33261,"size":635,"sha256":"d00c14c63eda3147e673e69e86381bb5809318a1d7f979c02b05e9ee8f53f09a"},{"path":"/usr/lib/dracut/modules.d/98selinux/module-setup.sh","mode":33261,"size":229,"sha256":"852ca7d56ee022e99a9827127e8437c04dce0f1209044beec8e6c010bc4c23cc"},{"path":"/usr/lib/dracut/modules.d/98selinux/selinux-loadpolicy.sh","mode":33261,"size":2242,"sha256":"b52b573f8e4853243829bacf9f185e6c6550049f100ee363911a1f548a49fead"},{"path":"/usr/lib/dracut/modules.d/98syslog/README","mode":33188,"size":832,"sha256":"6eebfb036cb23b759d37f64dda2b3ab445a841d4a7fa0ab1580930504d14a514"},{"path":"/usr/lib/dracut/modules.d/98syslog/module-setup.sh","mode":33261,"size":1157,"sha256":"e4a99e4bb53ef145510d7f178b4b67c5739421ae8c9baddba0a4000a7cc0c642"},{"path":"/usr/lib/dracut/modules.d/98syslog/parse-syslog-opts.sh","mode":33261,"size":1154,"sha256":"d9ddab96dd02efe14c33c1778236cc2363da9dee7fd1d2bbf9febdd322745f33"},{"path":"/usr/lib/dracut/modules.d/98syslog/rsyslog.conf","mode":33188,"size":820,"sha256":"2d15df129a18010f3b648850ef445c421ba21c64894dce6265305eac6aa23316"},{"path":"/usr/lib/dracut/modules.d/98syslog/rsyslogd-start.sh","mode":33261,"size":1233,"sha256":"6e9dba6f15ad475b68553f0d6d3fc6bfa92f1a13234a6e89e3493027767eeef4"},{"path":"/usr/lib/dracut/modules.d/98syslog/rsyslogd-stop.sh","mode":33261,"size":286,"sha256":"28bbb4db434217b759d4e50cdb02a6df3a7978ad50862f667236c66f594c5421"},{"path":"/usr/lib/dracut/modules.d/98syslog/syslog-cleanup.sh","mode":33261,"size":407,"sha256":"30545eb8371f689690c87a9eb80af1774310d8218289a3b316a75a84283490f1"},{"path":"/usr/lib/dracut/modules.d/98usrmount/module-setup.sh","mode":33261,"size":294,"sha256":"8f3fba52e54e4533c516377784da847b78d38ed826cf8d0a26913a8fb5061013"},{"path":"/usr/lib/dracut/modules.d/98usrmount/mount-usr.sh","mode":33261,"size":3606,"sha256":"12ccbbffa416f47882c2c32785bf7c61c02d5fcf4d9c03c256b85f3644d353dd"},{"path":"/usr/lib/dracut/modules.d/99base/dracut-lib.sh","mode":33261,"size":34162,"sha256":"4fb4d22936741b4482709de33546b844aa51e773d3805b76b24302a2a964a453"},{"path":"/usr/lib/dracut/modules.d/99base/init.sh","mode":33261,"size":11832,"sha256":"c56a59554edc41948e31afe3a7bb8f49715dde36df505bd7f2b8c7ea4e9aac16"},{"path":"/usr/lib/dracut/modules.d/99base/initqueue.sh","mode":33261,"size":1163,"sha256":"9c320e1b7a1d028ccf92e53aa3397f001802fa6b82fd119cf62bdf657c78ccd2"},{"path":"/usr/lib/dracut/modules.d/99base/loginit.sh","mode":33261,"size":492,"sha256":"34551d9cf84930dfff9663eea1ea07bbe3aebc30ee6606ab98a76a3dd041c6b3"},{"path":"/usr/lib/dracut/modules.d/99base/memtrace-ko.sh","mode":33261,"size":6052,"sha256":"3675b601e59b33775d22f4981a61748a136a1283ae3439a76fd31c7e1929937f"},{"path":"/usr/lib/dracut/modules.d/99base/module-setup.sh","mode":33261,"size":4167,"sha256":"dafd8a4ed1fd6cd02c9c3d024759662980f2499d8aa6057b85251d8abcdbf9ff"},{"path":"/usr/lib/dracut/modules.d/99base/parse-root-opts.sh","mode":33261,"size":246,"sha256":"4e07ef0a39226066a62a2ac32be79c242f90cb64641261b5f3d618f58f633c67"},{"path":"/usr/lib/dracut/modules.d/99base/rdsosreport.sh","mode":33261,"size":1346,"sha256":"a2a2ad64b2a99f08472a6702f9a5d2712d98b6fa0394e526406117042d41e60a"},{"path":"/usr/lib/dracut/modules.d/99fs-lib/fs-lib.sh","mode":33261,"size":6381,"sha256":"fb3c201f345507039b660fbd560f99005fc7115425ece6f8a212c8cd030a7fb3"},{"path":"/usr/lib/dracut/modules.d/99fs-lib/module-setup.sh","mode":33261,"size":1722,"sha256":"af70bb601d4d163d71425fa813aad5054ed670e43d76ea63cbbaf4cba398b080"},{"path":"/usr/lib/dracut/modules.d/99shutdown/module-setup.sh","mode":33261,"size":585,"sha256":"ac5eacafcba7616290c3d0949abf1c7f76703978132d34c1afe8b3e1505bd511"},{"path":"/usr/lib/dracut/modules.d/99shutdown/shutdown.sh","mode":33261,"size":3126,"sha256":"3cc5a1b5a144e4fb839f6085e1cc406da81139710ff63f4e347a1c7c36139b8a"},{"path":"/usr/lib/dracut/skipcpio","mode":33261,"size":12264,"sha256":"da0080fe40a502cce99db93868b63af7622877e6620a1372995657cb17b1723d"},{"path":"/usr/lib/kernel/install.d/50-dracut.install","mode":33261,"size":1700,"sha256":"9bc93d24aff2ffc3b860dbe22ebbce73b400b0df7eab4878e8f51a4237c0bb27"},{"path":"/usr/lib/systemd/system/dracut-cmdline.service","mode":41471,"size":62,"sha256":""},{"path":"/usr/lib/systemd/system/dracut-initqueue.service","mode":41471,"size":64,"sha256":""},{"path":"/usr/lib/systemd/system/dracut-mount.service","mode":41471,"size":60,"sha256":""},{"path":"/usr/lib/systemd/system/dracut-pre-mount.service","mode":41471,"size":64,"sha256":""},{"path":"/usr/lib/systemd/system/dracut-pre-pivot.service","mode":41471,"size":64,"sha256":""},{"path":"/usr/lib/systemd/system/dracut-pre-trigger.service","mode":41471,"size":66,"sha256":""},{"path":"/usr/lib/systemd/system/dracut-pre-udev.service","mode":41471,"size":63,"sha256":""},{"path":"/usr/lib/systemd/system/dracut-shutdown.service","mode":41471,"size":63,"sha256":""},{"path":"/usr/lib/systemd/system/initrd.target.wants/dracut-cmdline.service","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/initrd.target.wants/dracut-initqueue.service","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/systemd/system/initrd.target.wants/dracut-mount.service","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/systemd/system/initrd.target.wants/dracut-pre-mount.service","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/systemd/system/initrd.target.wants/dracut-pre-pivot.service","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/systemd/system/initrd.target.wants/dracut-pre-trigger.service","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/systemd/system/initrd.target.wants/dracut-pre-udev.service","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/dracut-shutdown.service","mode":41471,"size":26,"sha256":""},{"path":"/usr/share/bash-completion/completions/dracut","mode":33188,"size":3580,"sha256":"5a5385685fed86fe13043d70a7f53a0b78a944203c660f3a90f0b33c766316f8"},{"path":"/usr/share/bash-completion/completions/lsinitrd","mode":33188,"size":1983,"sha256":"9f7904494ad7795d99caa2960ea2ace7f1422349c8a8d0ad55b962dd105fa05a"},{"path":"/usr/share/licenses/dracut/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/dracut/lgpl-2.1.txt","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"},{"path":"/usr/share/pkgconfig/dracut.pc","mode":33188,"size":196,"sha256":"e64ba16acb94555045c875c798c8dbfafdeba4468634982bf154e6054bb7e3f6"}]}},{"name":"dracut-network","version":"049-70.git20200228.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dracut-network:dracut-network:049-70.git20200228.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dracut-network:049-70.git20200228.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dracut-network@0:049-70.git20200228.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dracut-network","version":"049","epoch":0,"architecture":"x86_64","release":"70.git20200228.el8","sourceRpm":"dracut-049-70.git20200228.el8.src.rpm","size":160704,"license":"GPLv2+ and LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/dracut/modules.d/02systemd-networkd/module-setup.sh","mode":33261,"size":2249,"sha256":"e4df3b8f89d03a720cf3db2152736fdcc27168e3ddc7bfc25792aae141cc136f"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/dhclient-script.sh","mode":33261,"size":9273,"sha256":"00a5ce5ff46fe6f17ee803fc9ee9d37752557fe2dddded9a2260470958d5cba1"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/dhclient.conf","mode":33188,"size":303,"sha256":"30b82e8b108c78d9baac064b66d11540912ecc3cdebfad01f5b1654fa110b513"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/ifup.sh","mode":33261,"size":15390,"sha256":"17cfad9a369eb2e6871edb7239a674c5c4c284ce167342833eb923dc584bdf69"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/kill-dhclient.sh","mode":33261,"size":252,"sha256":"9916351386bdca388dd87c3368b1a227d65751a67f20056d82e7dbf95abf60b6"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/module-setup.sh","mode":33261,"size":2880,"sha256":"c78682cc56c240ff65f1314548772f8a91a160d7c1d64b011b5bc42bea836e90"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/net-genrules.sh","mode":33261,"size":3925,"sha256":"0548588aed8abc6fa5c72c40c007c90870633919c031af2571d64103c93e6be7"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/parse-bond.sh","mode":33261,"size":2007,"sha256":"5b1676fffb5701e81145cc10b7866bc5840a0cfeb9a8836693e75d7d24988b7a"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/parse-bridge.sh","mode":33261,"size":1124,"sha256":"65096f25c8c91933e2fbc0407695945a238e1bafc66429a2f039d5e8c628cd46"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/parse-ibft.sh","mode":33261,"size":283,"sha256":"89f56de99708eacef4b54e506059211c36e0b5c7bb3eba95db587cd9e2a8dcc7"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/parse-ifname.sh","mode":33261,"size":552,"sha256":"392d047b07cfde1a2b5b0e7e2d18f92e4fbc42761888c0f174c418ffc64e4b2d"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/parse-ip-opts.sh","mode":33261,"size":4798,"sha256":"c2e72a442199bab981bd67ef9a438cfbede28c968a9f1565b7ef45215b46f73a"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/parse-team.sh","mode":33261,"size":1047,"sha256":"40dd1ccdb7ea1bed49a6211f827b79d8cc52303ad4f6bfc64231e31b5b9dce42"},{"path":"/usr/lib/dracut/modules.d/35network-legacy/parse-vlan.sh","mode":33261,"size":662,"sha256":"6b579099b708172ab1a20bf5ef328708c39884ea630df8ee74859f9561671821"},{"path":"/usr/lib/dracut/modules.d/35network-manager/module-setup.sh","mode":33261,"size":1428,"sha256":"03a72195c418972e0b33357a39217620a7101dc04315e1ea7e3246e80a78db7b"},{"path":"/usr/lib/dracut/modules.d/35network-manager/nm-config.sh","mode":33261,"size":172,"sha256":"ff421518a0c393e29833e2ad0274dae2561e30c2979f0da6db6268b4f7103799"},{"path":"/usr/lib/dracut/modules.d/35network-manager/nm-run.sh","mode":33261,"size":592,"sha256":"b5652e900930a5dbea0794d1301e18e8428f7a8b70792e3b453defb17af6a696"},{"path":"/usr/lib/dracut/modules.d/40network/dhcp-root.sh","mode":33261,"size":816,"sha256":"40d76a471b3f351a6f49df7baba41e399252d0c50e86c8ed0143eebc29c82977"},{"path":"/usr/lib/dracut/modules.d/40network/ifname-genrules.sh","mode":33261,"size":1119,"sha256":"2fcb00299e8d838d81ebeddd285542c7b6e4472249fa0954d681e43ae4727722"},{"path":"/usr/lib/dracut/modules.d/40network/module-setup.sh","mode":33261,"size":683,"sha256":"989e061278665e8bb8407627bceaa039422efc5cefa9bb2c43f57f4f74cf55a0"},{"path":"/usr/lib/dracut/modules.d/40network/net-lib.sh","mode":33261,"size":25333,"sha256":"de0c5166b1d4086c63b4dd97d044a51e75d3ecd0f638a03d016ba659fa71b5f1"},{"path":"/usr/lib/dracut/modules.d/40network/netroot.sh","mode":33261,"size":2677,"sha256":"c3a113770fb6a4a825e59031a03ea3b4d7f09e9b9ee0f9117bb4ddd6c5178112"},{"path":"/usr/lib/dracut/modules.d/45ifcfg/module-setup.sh","mode":33261,"size":289,"sha256":"fbe01fa522c27c04126e76db5f99d506ca803eed6ca7f982cdc1e29ae1747edd"},{"path":"/usr/lib/dracut/modules.d/45ifcfg/write-ifcfg.sh","mode":33261,"size":8724,"sha256":"b930d37f6bedb794c02c84232d25ac18f562dd5f92c956df1ea1a43c0c289fd7"},{"path":"/usr/lib/dracut/modules.d/90kernel-network-modules/module-setup.sh","mode":33261,"size":958,"sha256":"afd15439fc700a95975ea80901d8da5b9ad0f6b62b03267dd697756cfdd778b2"},{"path":"/usr/lib/dracut/modules.d/90qemu-net/module-setup.sh","mode":33261,"size":802,"sha256":"f9ee6f0f258e06873033e67fbf6533cc63b68e4526c5d8761bede77f84bc5ca9"},{"path":"/usr/lib/dracut/modules.d/95cifs/cifs-lib.sh","mode":33261,"size":969,"sha256":"64ae19c6c09e68683e5ced3d99f0b66d13a8043657ec89adf74a799f57ac7f60"},{"path":"/usr/lib/dracut/modules.d/95cifs/cifsroot.sh","mode":33261,"size":609,"sha256":"6838e1ae6088de237d0aa16191f6b1c2dafceec80be17874e025eef71dcde942"},{"path":"/usr/lib/dracut/modules.d/95cifs/module-setup.sh","mode":33261,"size":1267,"sha256":"68444a1970f8b582703a51721fc8f8a725a0cf84f537847ee03c5caed9c166ac"},{"path":"/usr/lib/dracut/modules.d/95cifs/parse-cifsroot.sh","mode":33261,"size":1182,"sha256":"3c242aa781c7bdf599e0441a7e014398ed8fdb29ecbb219baad83f05dbc7b944"},{"path":"/usr/lib/dracut/modules.d/95fcoe-uefi/module-setup.sh","mode":33261,"size":788,"sha256":"3429a8800272279a63aa9609291196d7fd9e6651421b731e1759292812bf4e27"},{"path":"/usr/lib/dracut/modules.d/95fcoe-uefi/parse-uefifcoe.sh","mode":33261,"size":922,"sha256":"e765227076c9f00231066170d0968de6943c5334a4c2c366fc5ce367e0877a8a"},{"path":"/usr/lib/dracut/modules.d/95fcoe/cleanup-fcoe.sh","mode":33261,"size":544,"sha256":"4ae60ee404cc38b43e7bb6db2ebc0c67ea9c0f352adab45a652b6917e7849044"},{"path":"/usr/lib/dracut/modules.d/95fcoe/fcoe-edd.sh","mode":33261,"size":1162,"sha256":"f76a925f1d101d40891019f967a40b7b28b098725769b9eab8b65eeafc506766"},{"path":"/usr/lib/dracut/modules.d/95fcoe/fcoe-genrules.sh","mode":33261,"size":1204,"sha256":"bc8e43633a4520af031f40918d5d3afc1418fa2da5cc26f9c451c01c0e10c876"},{"path":"/usr/lib/dracut/modules.d/95fcoe/fcoe-up.sh","mode":33261,"size":2531,"sha256":"e9d666a92fc061859e64f9dcc84ce6f46341166c1b2b395552f69b4aa9c82c9b"},{"path":"/usr/lib/dracut/modules.d/95fcoe/lldpad.sh","mode":33261,"size":363,"sha256":"5f854af1f499134508f81aaab0147cad7b3432e4ee45c9307a3fed59d6062fa6"},{"path":"/usr/lib/dracut/modules.d/95fcoe/module-setup.sh","mode":33261,"size":3474,"sha256":"4d1e4ad7a46af8045d936383052a0f77ae33e1229ffaeec1fc9c9c6b3dcf2663"},{"path":"/usr/lib/dracut/modules.d/95fcoe/parse-fcoe.sh","mode":33261,"size":1942,"sha256":"a6e346c9a4e87e54fb4ad3a15622a015a16ec1d515e48e3c5a587903c4403ff6"},{"path":"/usr/lib/dracut/modules.d/95fcoe/stop-fcoe.sh","mode":33261,"size":111,"sha256":"6b0dd3e5b0f7f9f13a17ffc352d7f40d7b049b075a561280b022299de8bd7f41"},{"path":"/usr/lib/dracut/modules.d/95iscsi/cleanup-iscsi.sh","mode":33261,"size":88,"sha256":"f69180379e23604187aefca3bcb6a2393e98e5104aac82bf6283ca920481c01b"},{"path":"/usr/lib/dracut/modules.d/95iscsi/iscsiroot.sh","mode":33261,"size":10426,"sha256":"932e8e8b28fa5e57df98403cecfb03271c664bd26d4bae164f3a3978ca85e3c7"},{"path":"/usr/lib/dracut/modules.d/95iscsi/module-setup.sh","mode":33261,"size":9319,"sha256":"aebb4de9acf0651d51a655c751c7641d40e90811b6bdcc9200f385b581b1f56a"},{"path":"/usr/lib/dracut/modules.d/95iscsi/mount-lun.sh","mode":33261,"size":332,"sha256":"92ed3ef81e4464fa8553eae5e5644cac7d7718c3d6e7c98d6cd9421c5213b5ad"},{"path":"/usr/lib/dracut/modules.d/95iscsi/parse-iscsiroot.sh","mode":33261,"size":5965,"sha256":"657bf1dcb27b4a79cc0836e3986fdb83709d237fdcece0edaec11b4e2c503f80"},{"path":"/usr/lib/dracut/modules.d/95nbd/module-setup.sh","mode":33261,"size":1024,"sha256":"27ffb55170232b67708cbe8a05a22aa55104a67f7dbb3348583fd1d10b4b1b36"},{"path":"/usr/lib/dracut/modules.d/95nbd/nbd-generator.sh","mode":33261,"size":1152,"sha256":"62e33222eec03260bea4e1a87c94bbfe0b9af779f625251e31ab87e20aa9cae3"},{"path":"/usr/lib/dracut/modules.d/95nbd/nbdroot.sh","mode":33261,"size":3764,"sha256":"4080a82272314f9c9815aa6274fbf714a6f7d89d37ae687d052ef952464b230c"},{"path":"/usr/lib/dracut/modules.d/95nbd/parse-nbdroot.sh","mode":33261,"size":1756,"sha256":"df500d0cd62cccd8528fd1bf1b45329dea20424a0c9b420616b11b96b9fc06f1"},{"path":"/usr/lib/dracut/modules.d/95nfs/module-setup.sh","mode":33261,"size":4045,"sha256":"a222dcb98e04614aacb38f73253f8c7aa172ad4e8e793b6e2a71c438187f4652"},{"path":"/usr/lib/dracut/modules.d/95nfs/nfs-lib.sh","mode":33261,"size":4644,"sha256":"7a2f1af9ff1baa5c9fb176c7272b328dcdd7a2353e377dc9b2ae591b48160397"},{"path":"/usr/lib/dracut/modules.d/95nfs/nfs-start-rpc.sh","mode":33261,"size":870,"sha256":"1693a364e8e9593c6f35cb26df21b78f2a9641e53b0f45f06b444ac6eb75162c"},{"path":"/usr/lib/dracut/modules.d/95nfs/nfsroot-cleanup.sh","mode":33261,"size":845,"sha256":"38be42abc9fd91d4f98ee4c0c07c199cf40d5796e8518d65da9d04bd7fa061e2"},{"path":"/usr/lib/dracut/modules.d/95nfs/nfsroot.sh","mode":33261,"size":715,"sha256":"cf7abc11a210f8e694d05991239fcd35165d7e95b405f8f09dc3397157e5acda"},{"path":"/usr/lib/dracut/modules.d/95nfs/parse-nfsroot.sh","mode":33261,"size":3333,"sha256":"c3a99d2a3f53f9a0f78fcfa31a227c999ded330a3c44f8f2063e9ee4ea72ba90"},{"path":"/usr/lib/dracut/modules.d/95ssh-client/module-setup.sh","mode":33261,"size":2067,"sha256":"2ca66ab229375fb479b9550b8cb53c29e1969d2ee90ba8d7f9271341aac9bd9f"},{"path":"/usr/lib/dracut/modules.d/99uefi-lib/module-setup.sh","mode":33261,"size":212,"sha256":"3a6322a6b95a51b34a3fc72a8d0a6cde34cdbad6656ab73125018cfdea381cd7"},{"path":"/usr/lib/dracut/modules.d/99uefi-lib/uefi-lib.sh","mode":33261,"size":4741,"sha256":"f487e4f8abf071a11b987716fc0b3c5616564aa9cbe40457e1eeca5eee418e68"}]}},{"name":"dracut-squash","version":"049-70.git20200228.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:dracut-squash:dracut-squash:049-70.git20200228.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:dracut-squash:049-70.git20200228.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/dracut-squash@0:049-70.git20200228.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"dracut-squash","version":"049","epoch":0,"architecture":"x86_64","release":"70.git20200228.el8","sourceRpm":"dracut-049-70.git20200228.el8.src.rpm","size":3054,"license":"GPLv2+ and LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/dracut/modules.d/99squash/clear-squash.sh","mode":33261,"size":174,"sha256":"d59317f3dfa52b5849e2a0b0ca988b68bf6679f577d3372ebd112c5155f74271"},{"path":"/usr/lib/dracut/modules.d/99squash/init.sh","mode":33261,"size":135,"sha256":"1a4168dff97f24599f3df69b4ca11fe593d438aaeaa65dada0ca9007a9808f49"},{"path":"/usr/lib/dracut/modules.d/99squash/module-setup.sh","mode":33188,"size":885,"sha256":"68e2a65a39beb7e77201e690678e2671054464c28dab94aea957baf919d59017"},{"path":"/usr/lib/dracut/modules.d/99squash/setup-squash.sh","mode":33261,"size":1345,"sha256":"a862593a77029c32c77f87edc8163775795298f4988a34b08edaae485b1c8727"},{"path":"/usr/lib/dracut/modules.d/99squash/shutdown.sh","mode":33261,"size":143,"sha256":"a78b0a2429c0ad3976fcc296533fce076f071cf27464c22f37508343f29e3fc9"},{"path":"/usr/lib/dracut/modules.d/99squash/squash-mnt-clear.service","mode":33188,"size":372,"sha256":"9a2b9ca246aa27dd600c83e76e768d3afa968786ae3eb61f58a8300e00e26b28"}]}},{"name":"elfutils-default-yama-scope","version":"0.178-7.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:elfutils-default-yama-scope:elfutils-default-yama-scope:0.178-7.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:elfutils-default-yama-scope:0.178-7.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/elfutils-default-yama-scope@0:0.178-7.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"elfutils-default-yama-scope","version":"0.178","epoch":0,"architecture":"noarch","release":"7.el8","sourceRpm":"elfutils-0.178-7.el8.src.rpm","size":1810,"license":"GPLv2+ or LGPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/sysctl.d/10-default-yama-scope.conf","mode":33188,"size":1810,"sha256":"5d1322bb224f78beb5c06089a52ff53c9e5c77c6039d60f978429071bdba9870"}]}},{"name":"elfutils-libelf","version":"0.178-7.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:elfutils-libelf:elfutils-libelf:0.178-7.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:elfutils-libelf:0.178-7.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/elfutils-libelf@0:0.178-7.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"elfutils-libelf","version":"0.178","epoch":0,"architecture":"x86_64","release":"7.el8","sourceRpm":"elfutils-0.178-7.el8.src.rpm","size":920699,"license":"GPLv2+ or LGPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/2c/aa9cdb6c0295e842541ec595dbf46d2fece376","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/libelf-0.178.so","mode":33261,"size":104552,"sha256":"e9b7239997122649b5cd81076816295ef149bca3a4e315e2ccbd76521701b4f3"},{"path":"/usr/lib64/libelf.so.1","mode":41471,"size":15,"sha256":""},{"path":"/usr/share/licenses/elfutils-libelf/COPYING-GPLV2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/elfutils-libelf/COPYING-LGPLV3","mode":33188,"size":7651,"sha256":"da7eabb7bafdf7d3ae5e9f223aa5bdc1eece45ac569dc21b3b037520b4464768"}]}},{"name":"elfutils-libs","version":"0.178-7.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:elfutils-libs:elfutils-libs:0.178-7.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:elfutils-libs:0.178-7.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/elfutils-libs@0:0.178-7.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"elfutils-libs","version":"0.178","epoch":0,"architecture":"x86_64","release":"7.el8","sourceRpm":"elfutils-0.178-7.el8.src.rpm","size":717567,"license":"GPLv2+ or LGPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/82/175964da8a6a07837ec0a80f0fb43e89382b82","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/e7/8a2156bd25522246925006abdc616f9ccabd28","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/libasm-0.178.so","mode":33261,"size":33480,"sha256":"6abab67ac074c2d4d43d0df842b1b6d3f807b57159b586667c1e7037bc760b14"},{"path":"/usr/lib64/libasm.so.1","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libdw-0.178.so","mode":33261,"size":658344,"sha256":"406569741372c38a574710e24c1bc526dffeb6835edc63e666a09b703aec53d7"},{"path":"/usr/lib64/libdw.so.1","mode":41471,"size":14,"sha256":""},{"path":"/usr/share/licenses/elfutils-libs/COPYING-GPLV2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/elfutils-libs/COPYING-LGPLV3","mode":33188,"size":7651,"sha256":"da7eabb7bafdf7d3ae5e9f223aa5bdc1eece45ac569dc21b3b037520b4464768"}]}},{"name":"ethtool","version":"5.0-2.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:ethtool:ethtool:5.0-2.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:ethtool:5.0-2.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/ethtool@2:5.0-2.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"ethtool","version":"5.0","epoch":2,"architecture":"x86_64","release":"2.el8","sourceRpm":"ethtool-5.0-2.el8.src.rpm","size":502623,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/43/56cfc74aadb9fc1e73b02654d80078e27c878e","mode":41471,"size":28,"sha256":""},{"path":"/usr/sbin/ethtool","mode":33261,"size":445368,"sha256":"f9b4b550a581b9d5de07361f91c183fbd4142b15497bf4266c5c72b867eb78c5"},{"path":"/usr/share/licenses/ethtool/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/ethtool/LICENSE","mode":33188,"size":100,"sha256":"5d632934396f90c82dfebe3c9512648bbb6333b406113d0cd331b0e0aa2d34a1"}]}},{"name":"expat","version":"2.2.5-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:expat:expat:2.2.5-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:expat:2.2.5-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/expat@0:2.2.5-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"expat","version":"2.2.5","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"expat-2.2.5-3.el8.src.rpm","size":314068,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/bin/xmlwf","mode":33261,"size":35680,"sha256":"f35a3cbabe0d9a6c5d2683567da1cc069f96ec98fc75d61825a65a9055d3e455"},{"path":"/usr/lib/.build-id/25/8df9bb0bd70bda1248bd075b2ea977b5842d77","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/b9/98df7b8fa4581b8dc11f7206fe166c5aed1fe5","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib64/libexpat.so.1","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libexpat.so.1.6.7","mode":33261,"size":245080,"sha256":"1503792fe46d252566e647a859ce40545958f58eac0a0d6bdef3a2350bbe5399"},{"path":"/usr/share/licenses/expat/COPYING","mode":33188,"size":1144,"sha256":"46336ab2fec900803e2f1a4253e325ac01d998efb09bc6906651f7259e636f76"}]}},{"name":"file-libs","version":"5.33-13.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:file-libs:file-libs:5.33-13.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:file-libs:5.33-13.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/file-libs@0:5.33-13.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"file-libs","version":"5.33","epoch":0,"architecture":"x86_64","release":"13.el8","sourceRpm":"file-5.33-13.el8.src.rpm","size":6382974,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/08/7c3762d8af405d3c054ab0bdada02fdda43a37","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libmagic.so.1","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libmagic.so.1.0.0","mode":33261,"size":161568,"sha256":"3f10dab1d3e9c5d60810a21de44fa73ab365bf232d5575ce6c5afd938fd35174"},{"path":"/usr/share/file/magic","mode":41471,"size":8,"sha256":""},{"path":"/usr/share/licenses/file-libs/COPYING","mode":33188,"size":1650,"sha256":"3c0ad13c36f891a9b4f951e59eb2fc108065a46f849697cc6fd3cdb41cc23a3d"},{"path":"/usr/share/magic","mode":41471,"size":10,"sha256":""},{"path":"/usr/share/misc/magic","mode":33188,"size":962492,"sha256":"35dd4ca80d1c0d329ef04e68b6306672485ee1a34bb5e573055749e26e5b6099"},{"path":"/usr/share/misc/magic.mgc","mode":33188,"size":5192336,"sha256":"e18ca36dec791f274e9c0dd07225869824f609ce408fd08068d707e5450eb4f8"}]}},{"name":"filesystem","version":"3.8-2.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:filesystem:filesystem:3.8-2.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:filesystem:3.8-2.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/filesystem@0:3.8-2.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"filesystem","version":"3.8","epoch":0,"architecture":"x86_64","release":"2.el8","sourceRpm":"filesystem-3.8-2.el8.src.rpm","size":0,"license":"Public Domain","vendor":"CentOS","files":[{"path":"/bin","mode":41471,"size":7,"sha256":""},{"path":"/lib","mode":41471,"size":7,"sha256":""},{"path":"/lib64","mode":41471,"size":9,"sha256":""},{"path":"/sbin","mode":41471,"size":8,"sha256":""},{"path":"/usr/lib/debug/bin","mode":41471,"size":7,"sha256":""},{"path":"/usr/lib/debug/lib","mode":41471,"size":7,"sha256":""},{"path":"/usr/lib/debug/lib64","mode":41471,"size":9,"sha256":""},{"path":"/usr/lib/debug/sbin","mode":41471,"size":8,"sha256":""},{"path":"/usr/lib/debug/usr/.dwz","mode":41471,"size":7,"sha256":""},{"path":"/usr/tmp","mode":41471,"size":10,"sha256":""},{"path":"/var/lock","mode":41471,"size":11,"sha256":""},{"path":"/var/mail","mode":41471,"size":10,"sha256":""},{"path":"/var/run","mode":41471,"size":6,"sha256":""}]}},{"name":"findutils","version":"4.6.0-20.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:findutils:findutils:4.6.0-20.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:findutils:4.6.0-20.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/findutils@1:4.6.0-20.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"findutils","version":"4.6.0","epoch":1,"architecture":"x86_64","release":"20.el8","sourceRpm":"findutils-4.6.0-20.el8.src.rpm","size":1816673,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/find","mode":33261,"size":261992,"sha256":"75726e4ef1e7dd185e7dfd675fe6490fd4e5973babbff89a8927c46137638cb9"},{"path":"/usr/bin/xargs","mode":33261,"size":90312,"sha256":"d1be79ae6da65e0094ce30ca4a43ddeb0a6f9784aa323241349dc0a70b76c69d"},{"path":"/usr/lib/.build-id/5a/f2fc2eb5f08b1a8f9e87053d29edf7e3a4eaa3","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/95/cd66d3860a56011de9f9c4120d9b7ae34a7155","mode":41471,"size":25,"sha256":""},{"path":"/usr/share/licenses/findutils/COPYING","mode":33188,"size":35068,"sha256":"fc82ca8b6fdb18d4e3e85cfd8ab58d1bcd3f1b29abe782895abd91d64763f8e7"}]}},{"name":"gawk","version":"4.2.1-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:gawk:gawk:4.2.1-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:gawk:4.2.1-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/gawk@0:4.2.1-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"gawk","version":"4.2.1","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"gawk-4.2.1-1.el8.src.rpm","size":2717614,"license":"GPLv3+ and GPLv2+ and LGPLv2+ and BSD","vendor":"CentOS","files":[{"path":"/etc/profile.d/gawk.csh","mode":33188,"size":1107,"sha256":"9ba2af9853121df6dd5edff9254a2946e39eab8dc6513348fea28f739ee96648"},{"path":"/etc/profile.d/gawk.sh","mode":33188,"size":757,"sha256":"70621a3b586d3d523b020e76977633b444a70013ba50e1ea901a3a07a676f15f"},{"path":"/usr/bin/awk","mode":41471,"size":4,"sha256":""},{"path":"/usr/bin/gawk","mode":33261,"size":698520,"sha256":"183d91837e301bcf25334f2cf2391cd50f0e321292824e87629a0fa554c7993a"},{"path":"/usr/lib/.build-id/0b/a0aadde8b03d936b13026fd0029e2fa466ba80","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/1e/15252a044652c8305b77f690ab115e731c0ded","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/2f/2340a2716026197ac9c9a6a6e0b3c74f34cbe0","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/47/fbaf9efbdba767db824eb231a2ac20e86a49c7","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/54/d69c320dd947da89103ba9111b791af9dc36b5","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/68/912c6fc6c41ec7ebbc7c992542c4667e3c32df","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/6c/5fcdecb7208a7a68ef8e02e3556fcc08e6343c","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/6d/fbd280b53a39d5f82939218fd8a2b7db9960e1","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/7b/e45ea783bf16162d246c27f23d8c0534963901","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/88/091476f27478e9069caf0fe1996c2c32dfa212","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/a0/5b3881857608dd071939f2bc016fbd7e31911c","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/aa/4be5f83c4742f365157065f4439dbbd9ec5763","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/d6/2cb11d3f784ba870fa05b38011f9b965b92946","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/e1/5863441619e5e347477679aa10352825b1d8e5","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/eb/f71cd1e2aa8306fac4d0072943edbd3de8bf81","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/gawk/filefuncs.so","mode":33261,"size":34632,"sha256":"23777c04e5a16d5a23e8055a33cda76d71aa621a8540a65c68299450a31001ba"},{"path":"/usr/lib64/gawk/fnmatch.so","mode":33261,"size":12016,"sha256":"01363bf7ec81b7a73f193425ef4ad4939f7e8d48725a6b2adfd6d0cc031464ea"},{"path":"/usr/lib64/gawk/fork.so","mode":33261,"size":12128,"sha256":"17c6a86f775b64e143d4fff368dee1054bf5ff6272ae45292c2ac68fd2ac56ea"},{"path":"/usr/lib64/gawk/inplace.so","mode":33261,"size":16224,"sha256":"b41b556f31587afe1e25ce480726ab1c8f251c579a6fd34866267e9f1230ffe0"},{"path":"/usr/lib64/gawk/intdiv.so","mode":33261,"size":12048,"sha256":"8e414832facdb6fec68924957b52680bc52a6cb48c0c051686a22c0649c29d6c"},{"path":"/usr/lib64/gawk/ordchr.so","mode":33261,"size":12048,"sha256":"432ae6cc0c6720485b046825cd2fcf3ce98f35f2a98dd67690fd48173ccb1658"},{"path":"/usr/lib64/gawk/readdir.so","mode":33261,"size":12032,"sha256":"74bbcb55017f33564b393786d5ff76271e90594eed7f211a0fb5bc43cb71677d"},{"path":"/usr/lib64/gawk/readfile.so","mode":33261,"size":12128,"sha256":"ee9b1761e4b544fd07ebe28c11a68aad63bcf0c8eb7f84902a03f3125331d19e"},{"path":"/usr/lib64/gawk/revoutput.so","mode":33261,"size":12032,"sha256":"df3fd3ef680f398b64961b74832a05eca4c6dc7d5418630424046356daf14ae0"},{"path":"/usr/lib64/gawk/revtwoway.so","mode":33261,"size":12112,"sha256":"a86260ac2d637ba7f43d63c4e2a9c715cd7ca5a5052e0ff9cffe53800c6bfc82"},{"path":"/usr/lib64/gawk/rwarray.so","mode":33261,"size":16168,"sha256":"81be38b3ab864a3154ef572c7ef5fe222dfc81d5fbbf43b39369f6bc173e709e"},{"path":"/usr/lib64/gawk/time.so","mode":33261,"size":12056,"sha256":"c0df353f79ed5b2281ee6c2dd75359101d57aeff890bf9b383e6057a8f1695e1"},{"path":"/usr/libexec/awk/grcat","mode":33261,"size":9240,"sha256":"5fe45c08c28eb8490067d039c2c1cb137b8666c2e559e27a3e6fbdd9fabf6b51"},{"path":"/usr/libexec/awk/pwcat","mode":33261,"size":9224,"sha256":"a6568386a4a5d560995e22119b32542f07545ae8c76f69ab6b4f4e9665ada450"},{"path":"/usr/libexec/gawk","mode":41471,"size":16,"sha256":""},{"path":"/usr/share/awk/assert.awk","mode":33188,"size":383,"sha256":"07f9e0362956d40ea6a92bedd4f292666185d038885387cb00adb5ade1582d93"},{"path":"/usr/share/awk/bits2str.awk","mode":33188,"size":334,"sha256":"d7529387edb12e4054b384e96bc4911cb3b0e544602fb1e9de8a983f5fd46c5a"},{"path":"/usr/share/awk/cliff_rand.awk","mode":33188,"size":307,"sha256":"41b20eba1d788cdc7d64c3860315b3bb8613f80b5f7d8f04774c31caef64dd42"},{"path":"/usr/share/awk/ctime.awk","mode":33188,"size":234,"sha256":"cf1b816f600516ec0a4f84901e12c48f44c5309bd6bd7b32f9a17abd026f2b86"},{"path":"/usr/share/awk/ftrans.awk","mode":33188,"size":315,"sha256":"9957afaddfec5f2c6bc4f9cb12c576e6c367c1b681a472e91ced9caff5292722"},{"path":"/usr/share/awk/getopt.awk","mode":33188,"size":2202,"sha256":"990d764228a3ae5f919dd0e585661fd14bf217617e7fcf33e4c40124d6969287"},{"path":"/usr/share/awk/gettime.awk","mode":33188,"size":2491,"sha256":"7baacb670919547d1fc2ec186d6ad937c6f7cc2d03e0b2e8f6802742dc7c6023"},{"path":"/usr/share/awk/group.awk","mode":33188,"size":1765,"sha256":"dcabe4d2e2f93972471e7eade26a7779e0c160c23570d3b32509433756083073"},{"path":"/usr/share/awk/have_mpfr.awk","mode":33188,"size":221,"sha256":"40d45f7e243e4f7faa1335852c5839fa80c60d70eccd94918cee7edbc58fd9a4"},{"path":"/usr/share/awk/inplace.awk","mode":33188,"size":1996,"sha256":"05bbddbdd78282e495d971a9473b761875f8b11f07963312bb515e0121d7f5e3"},{"path":"/usr/share/awk/intdiv0.awk","mode":33188,"size":462,"sha256":"c184f8a175c7226e9c567a8bb91e5e67ed8e239769012ad16f93c48f8e328bfd"},{"path":"/usr/share/awk/join.awk","mode":33188,"size":378,"sha256":"9af26157a40c1e1c09dfa73152e07cbff4c4f4b31b7bf8132572270da6dfc052"},{"path":"/usr/share/awk/libintl.awk","mode":33188,"size":238,"sha256":"2b3a65b9053d2f4f08733870ef2cf1b5ee8aeba74dc6b9b1d1610fc0d9ac0eee"},{"path":"/usr/share/awk/noassign.awk","mode":33188,"size":422,"sha256":"7ffc84e6d111aaf56cb0d3756bbcbd73e2510069ee6fc05bc1ea0e412884663e"},{"path":"/usr/share/awk/ord.awk","mode":33188,"size":937,"sha256":"e7d37acc67a101dd2e23c19ed3f9dfd5d01ea93af63b2ebc8679976e1ef051ce"},{"path":"/usr/share/awk/passwd.awk","mode":33188,"size":1199,"sha256":"bdaf71595b473e0cfffaa426f451e1cbeae6d8a9047c5e78cf254b33586ac5eb"},{"path":"/usr/share/awk/processarray.awk","mode":33188,"size":355,"sha256":"ac1e8e8dee8105c5c1ab2a1b87fcb668885473b7e90b7b0c137275742c704166"},{"path":"/usr/share/awk/quicksort.awk","mode":33188,"size":1031,"sha256":"b769b7a892acedcdb98d18c3cf05544d4d85488a0378aaacba0c6e2ddb71bf35"},{"path":"/usr/share/awk/readable.awk","mode":33188,"size":489,"sha256":"06e27abeb78eff929cb1f44256f195fe2d86ebb62814f731f420df286c8f1094"},{"path":"/usr/share/awk/readfile.awk","mode":33188,"size":267,"sha256":"751d619465eb57c9d6314eb2a97e783ff84ff108cd1c4efeff8f62400dd77609"},{"path":"/usr/share/awk/rewind.awk","mode":33188,"size":404,"sha256":"878279434b70956b26eca128a0939c1a14da97b1626fe402eb76d44485fbc268"},{"path":"/usr/share/awk/round.awk","mode":33188,"size":661,"sha256":"28b705d2e2b01cc3ed450cc42e2ff99b058b55ef5a49cbc483aded7bdfa58aff"},{"path":"/usr/share/awk/shellquote.awk","mode":33188,"size":472,"sha256":"78e7df6e31f55536a4c3853f6d54644877aa892ed7fc6e1d4dc9080284d78565"},{"path":"/usr/share/awk/strtonum.awk","mode":33188,"size":1454,"sha256":"abd27d285278e83655617efbd8e09b5f5271dd6ede37847b0ebd6632be2dde74"},{"path":"/usr/share/awk/walkarray.awk","mode":33188,"size":214,"sha256":"3a7f02f135e91bbf1c1cd498ea0e1489802d58c83bb4d112c0a407593db31dd8"},{"path":"/usr/share/awk/zerofile.awk","mode":33188,"size":424,"sha256":"c20a5e00b43fbfb9ea420da93f64422ce13d4aebb3b725e2ac3ba0102f169bee"},{"path":"/usr/share/gawk","mode":41471,"size":14,"sha256":""},{"path":"/usr/share/licenses/gawk/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/gawk/LICENSE.BSD","mode":33188,"size":1508,"sha256":"fea62a56afb45d77d33fd57599d5936d01bdda60d738e869df795a7392b1b320"},{"path":"/usr/share/licenses/gawk/LICENSE.GPLv2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/gawk/LICENSE.LGPLv2","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"gdbm","version":"1.18-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:gdbm:gdbm:1.18-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:gdbm:1.18-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/gdbm@1:1.18-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"gdbm","version":"1.18","epoch":1,"architecture":"x86_64","release":"1.el8","sourceRpm":"gdbm-1.18-1.el8.src.rpm","size":399977,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/gdbm_dump","mode":33261,"size":23904,"sha256":"529f23c0e6c5aa4245fb4933a893a402cd8502272a86d17c9b8acc75937eb9ba"},{"path":"/usr/bin/gdbm_load","mode":33261,"size":28256,"sha256":"e47b85ae815b8c084f5c0ffef24b8c03c115fcb81f2cfaa205cd70d416adb113"},{"path":"/usr/bin/gdbmtool","mode":33261,"size":119952,"sha256":"fc910ba180d88fc4c78d778bdddceb6c613519bf9058ab8b3fc98822f098dd97"},{"path":"/usr/lib/.build-id/45/db0973367371f08b177e4618849b4ecd14e997","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/5c/5d0a0e38974d9f8df2992d8ba744f71947b719","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/d2/64fe52cadc76fab3943dfed0b92676b0647e91","mode":41471,"size":29,"sha256":""}]}},{"name":"gdbm-libs","version":"1.18-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:gdbm-libs:gdbm-libs:1.18-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:gdbm-libs:1.18-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/gdbm-libs@1:1.18-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"gdbm-libs","version":"1.18","epoch":1,"architecture":"x86_64","release":"1.el8","sourceRpm":"gdbm-1.18-1.el8.src.rpm","size":135248,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/2f/593dc3f676e5512d9bc03c9f1303288a8d699c","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/70/58d003f39b5794bc6f4a408bba5fd94a9763a3","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib64/libgdbm.so.6","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libgdbm.so.6.0.0","mode":33261,"size":77816,"sha256":"71377112fa0caa789139e1ce3023f3c1c35f870016e5fcfe03c46b4c3fc451e1"},{"path":"/usr/lib64/libgdbm_compat.so.4","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib64/libgdbm_compat.so.4.0.0","mode":33261,"size":22360,"sha256":"e7d720648d77b465db4f04d3c70e44d1e034f59ae727c4dbd1e3e7f7a7d50ee9"},{"path":"/usr/share/licenses/gdbm-libs/COPYING","mode":33188,"size":35072,"sha256":"690d762f2e8e149ab1e2d6a409a3853b6151a2533b2382fae549a176d6bedecf"}]}},{"name":"glib2","version":"2.56.4-8.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:glib2:glib2:2.56.4-8.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:glib2:2.56.4-8.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/glib2@0:2.56.4-8.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"glib2","version":"2.56.4","epoch":0,"architecture":"x86_64","release":"8.el8","sourceRpm":"glib2-2.56.4-8.el8.src.rpm","size":12272168,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/gapplication","mode":33261,"size":20976,"sha256":"cec26da86b3c3105f682c5bcf315eda945126b2592b467e77af705715e993621"},{"path":"/usr/bin/gdbus","mode":33261,"size":49936,"sha256":"795032ffa0e37b46b2823aed16591ad0c26938cc36369f0b878945b1c513119b"},{"path":"/usr/bin/gio","mode":33261,"size":87432,"sha256":"7e53178d7288abcce546f8dd912e3b84299dbaffb93c4efbc788e9a78e9a7f86"},{"path":"/usr/bin/gio-querymodules-64","mode":33261,"size":16832,"sha256":"deff748c68a6e4851c795e4bd0a7951c0335091f622d199d4935861224d3a7d6"},{"path":"/usr/bin/glib-compile-schemas","mode":33261,"size":50200,"sha256":"310346d8cfde7d74005c83ed84ae798c11d33eedab52f731cc7bd5eaf175dc04"},{"path":"/usr/bin/gsettings","mode":33261,"size":29352,"sha256":"8fcf18071d58ea9f14af031c4f295043ee1bcf18fb8f6f68a57ddfd40b675d06"},{"path":"/usr/lib/.build-id/22/7e9b717683eb904d4a09fcd27ffb15c6e22686","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/27/a54b624fceffb68fc4163d6a2a1982b2c4016e","mode":41471,"size":48,"sha256":""},{"path":"/usr/lib/.build-id/2f/603cfb651dfed0dbdff74d7abb5308399747ec","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/3b/ea76bd288a76f1f61d41e601696aed5c398876","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/58/f989a97b7d84e636e5885db27a42281581baef","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/7b/8cbc1fc1ce1397e6bd398b2193cd75616b4c3d","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/7b/e761d4c8935cb72273ea8ed17ab98e07e13d28","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/9c/6010bcc879212dd8c540f5bd75790b1a39c04f","mode":41471,"size":48,"sha256":""},{"path":"/usr/lib/.build-id/b5/77f1ed5446eaeede79a1d56029c6a910f4a8ff","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/cd/0b41685298dd8671d0db65a8ace3e5042fd248","mode":41471,"size":48,"sha256":""},{"path":"/usr/lib/.build-id/e2/f09e484ced3d8a4efa32735852ebb4d5cc50e4","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib64/libgio-2.0.so.0","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib64/libgio-2.0.so.0.5600.4","mode":33261,"size":1765968,"sha256":"adbaaa7b4bb66d64f62d429d400bb8b7e85b3b3be4737239d8b1cf67e393186d"},{"path":"/usr/lib64/libglib-2.0.so.0","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib64/libglib-2.0.so.0.5600.4","mode":33261,"size":1168056,"sha256":"a9d05c962bb5a6eed8472b53769cf08be4e2c53108256bd4c13dac7564bceccc"},{"path":"/usr/lib64/libgmodule-2.0.so.0","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib64/libgmodule-2.0.so.0.5600.4","mode":33261,"size":15944,"sha256":"df96d083e12e7d3383e07ed5307b152b07012433a5eede671072b7fd1825abd9"},{"path":"/usr/lib64/libgobject-2.0.so.0","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib64/libgobject-2.0.so.0.5600.4","mode":33261,"size":347536,"sha256":"52dbf8a679e6bfa37e9ac38b404ee3b49f6cc1f47dc6df993091d9ba7e1ffa1a"},{"path":"/usr/lib64/libgthread-2.0.so.0","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib64/libgthread-2.0.so.0.5600.4","mode":33261,"size":7512,"sha256":"efafc11c9a803a77ae8f079976ea61740b3eaf1ec796c584cb51674ab957d780"},{"path":"/usr/share/bash-completion/completions/gapplication","mode":33188,"size":1389,"sha256":"199885a791120de218784b28d189becea2cdbdd1c297e8a4a92602a969857fe7"},{"path":"/usr/share/bash-completion/completions/gdbus","mode":33188,"size":935,"sha256":"819c76693b994a291c175c3d7a394022b7429644794816071ae40b5ca405105e"},{"path":"/usr/share/bash-completion/completions/gsettings","mode":33188,"size":2829,"sha256":"8b0b278b6e20a401e94afb6164f99f73ee49af70e12e6c7c054a48fc8dccb552"},{"path":"/usr/share/licenses/glib2/COPYING","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"},{"path":"/usr/share/locale/en_CA/LC_MESSAGES/glib20.mo","mode":33188,"size":80096,"sha256":"52e840a49e7106cbfa4adb0400f8d357105a8e68aea944dda1023dee325e3b62"},{"path":"/usr/share/locale/en_GB/LC_MESSAGES/glib20.mo","mode":33188,"size":118994,"sha256":"9b9b761311cfde7115dc4b986c45c567dc7445c01a5fdacbd464200e64b77a2a"}]}},{"name":"glibc","version":"2.28-101.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:glibc:glibc:2.28-101.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:glibc:2.28-101.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/glibc@0:2.28-101.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"glibc","version":"2.28","epoch":0,"architecture":"x86_64","release":"101.el8","sourceRpm":"glibc-2.28-101.el8.src.rpm","size":17885631,"license":"LGPLv2+ and LGPLv2+ with exceptions and GPLv2+ and GPLv2+ with exceptions and BSD and Inner-Net and ISC and Public Domain and GFDL","vendor":"CentOS","files":[{"path":"/etc/ld.so.cache","mode":33188,"size":0,"sha256":""},{"path":"/etc/ld.so.conf","mode":33188,"size":28,"sha256":"239c865e4c0746a01f82b03d38d620853bab2a2ba8e81d6f5606c503e0ea379f"},{"path":"/etc/nsswitch.conf","mode":33188,"size":2197,"sha256":"eaecde680c4130f71a86bdd41e1deb39d5f30d490efa0d237db822caa0df8640"},{"path":"/etc/rpc","mode":33188,"size":1634,"sha256":"3b24a975dcde688434258566813a83ce256a4c73efd7a8a9c3998327b0b4de68"},{"path":"/usr/lib/.build-id/00/c5a995c589153a569688ec12906ecdaf01560e","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/01/d455c18746bf99e6f71a628eb77b40d1ab787d","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/02/41c7b4e28f9a6f82e0d4c6e05d58a16656536c","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/02/aac1ddb856c7a55ae8a2145248509d08325f1a","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/06/bf4da48282c35b254f6af20f58b7d5b6193fbe","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/06/f9d0dfd39cbf699ca11336d3424bed8fe165b8","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/09/bb7e91722005b16d6313205c4d8883f1c1bfeb","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/0b/c263134082b5a5ea7692cec31f3486669457b9","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/0d/4a93941a2a3aa855e2d9d28f101bf7e663f5d2","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/0f/83d52b1b6af056f47eed28e20419e63e1568db","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/10/bc40a87d15322f3d7838f63c41ac2651c4f903","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/11/e7606c250be8366474d7979c21cd421578efde","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/12/065cdd3b39e235ec6ab4e6ce05248eab1a22bd","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/12/1a4c43f41be0be80b2b9adccc86869161b8991","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/12/31eb804962ed5ff0e3b324ba9ed43314d97dba","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/12/470d75451fac3aefec84cb5ed43dca5323c932","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/13/785585df9e233f77a01388708232f11a424c1d","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/13/c2d445aab125168c2a2f69fb9b2e4e75b39523","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/14/140c3d828b10a4dcc7b7c7d5588b3444478623","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/14/3705d882be767a2f3ea11d1f4e8631db361933","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/14/de15070b3284d4fceaa4ed8691b482c37d0aee","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/15/52e8d18539af3bf595e9168106e2cf5ff9af3a","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/15/a45d9fdaae1da1bf09a350c06c52b43ec4695c","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/16/90a538ae663c76d62276aa54083f8e3a7139aa","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/17/59a6708e312339a16dbe32fae430acb2644740","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/19/37f0b91b82b70f3fe0f97ddb6180e27040430e","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/19/51e93133e5705c0556e56ffa770125b6f65273","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/1a/b1cd05c645a5375447996e14744f9369e6cab9","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/1a/cf520e445c9f4ec6ea4b9c7150bdd90336e5a9","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/1b/55da05ea334fec7948b56a3df6533ffe2e37d3","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/1b/71f56d95d71ffdae3ed1081baddac7964c993e","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/1c/1b3c7979160d201b3e47bd600cdb255e3d1866","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/1c/3ec84cfabec646ef61af40a059aac22a687374","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/1c/b2e43bc10fafbd102d74a9bf7f59256c54b96b","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/1c/b73f59b1c806f1668ac6168cab7999270dd118","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/1d/24b15d6ac5ec82dab88fd51069e43d4a1f997a","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/1e/303ba69668f7d7fc27355b1f465f8ceae28154","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/1e/fd656687a267c08991712f10ef2423d05a0831","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/20/491b5d45fb662d5400855809e8930eaf955edb","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/20/56ea8226f1485e89b6ddc2741a2b810b9e9f83","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/20/712e0213ca73fbe5fd41c1f20cf33a2963c663","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/20/83884b7ca9445631033b9c6c722535291ec612","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/21/b046147f405fb675dc8f2439e11b1425361159","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/22/b6c29ebfd0887f2996c0b0e1fb1679dc379007","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/22/f1ec5a530600336c5861f33fe1be47bd1ee96c","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/24/2b95f2bc235c7df55d7b7db117766e67c9d2ca","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/24/b0454f218458d8d8ddabf845c5c3b203113ef9","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/26/47cc1bc909c9fcce91d8c0f3fc99fb8d06bcce","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/26/cc9b5c95bf87f62537950f00486b9b088f65a0","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/29/13703eea3c346f8831b89964da572b8c6fa278","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/29/c178c009a6e1ca744bd5a21acaa30234bfd407","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/2b/00ece352e5bc5625d4eb1f18393b2f88a6c179","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/2c/08ed7ba74ddb3645d57053247312efb64099cb","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/2c/537ba811f5aa338f86afc0b990b1005b934488","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/2c/810db1e6c989d277812b81a78f2f2f9d4c7a7c","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/2d/aa8a1086d00500191ec5467abbc897255cfa28","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/2d/b84ef45d98e9a4c999c0405f555db8fa49d7aa","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/2e/9f9f2500c5e8aeeb112d755a4177f5b96d4891","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/31/a507caa25b0e6a6efe05e48d7ff23447e552ac","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/31/bbcc2fc44edec9a13d58b2d91c859e986fea3d","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/35/a582e3d5c6cbd4eaaddd6aabca21258a7d5fcb","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/36/3589335e8a664e8fe406001aa6918f2efc6213","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/36/7058be989dbb9c741589a34fcea25daa543cd2","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/38/a3dfd87d6a1206b4ebd296847d699cb7d1a4ee","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/39/1a8b0820221bf6f7d3409375f8fbe56a60813a","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/39/c43eb9296c192baecd5b5440de1f83876d5965","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/3a/1f462e07237c757c1bd2be00a4a44a4485e9db","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/3d/26fc8b485d0850e58fe65135aecc1b7c7ac408","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/3f/265b85db0e5d1c5f67d4ffc12a5e9484a42356","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/3f/a941896f4442a56bc249e52099f574a4ac8964","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/40/106e92521651b1e1323ac692047ad4e751b401","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/40/12da86edfe6cfbc36f697ad1088ee7796b40a8","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/40/fd3c24ede9dcafac06bbebcd8d0c4a30a99184","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/41/5a58a87b3bd78d39bd5bd924e276c7bfc3b406","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/42/59b1e7f18fd424efba3aa00b6d91c803ddbaff","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/42/a33bc2b5a3ad4da56cca15f2f66b34f6eb01aa","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/43/92daa88c67c2006fce76fdfc24a2b135950881","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/44/75d191ae3efad79b028afe6b21710259726121","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/45/b1658f4ff5a6eea4dd50232fa4fef5c6425323","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/4a/6e94390f6ca96ed2a19ebdae5d651e71caefc2","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/4b/5180778cbaf25b6322c8d711651ca0afb2aeac","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/4b/55cbd1385b57169f09a51fe32b1441a1b2f792","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/4f/495822f654e364dcb7bb7a9e430e5d73a48b91","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/4f/67edb358b03450eb954c1d0be2fc0813b50c29","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/50/250ec3c308578756aed6fdd83ac218ad24cdfb","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/50/ab6047d861484b25798dc7eb7decc264a6c294","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/50/d86d885ce54e83af2e519eb5fcc7de701be198","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/51/34b8e7ad70b3200eb2aba1a53a7016599f65ab","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/51/d6edda3a72530e557da2a1c6c37f3ca148aaa7","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/52/d620cc6c6f69c25d9837aa3d7e337ba5c27fac","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/53/ec1697135aeb6d8b8b74f3c92393af97a54bc5","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/58/8ced556a94bb0eefa68c58db43ffed4110b10a","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/5a/7e7480869f7141d20d4846379ac645c3a4c3f9","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/5b/a33466f8bd4f24844a703b61c9ac21d7422985","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/60/3453304142a0bfa731195f5fc0b5ce7e310fa0","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/61/98ac00884e7433a24f62a0f4cb9f79aae405f0","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/61/b0c71456368e347e3013e7e3cd8441f8e72e97","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/62/3344e84fc4facd5bf64141bac6ee949a437eb9","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/62/4a92f52fbdc1f739cf80327cc83e83144f22b2","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/62/5fdfa3d4406fa7b98efa39b5f45b1096c6526c","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/63/44f2168afeb081cc0d5ef5371bcec4a9fbd7ff","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/63/8a751047099a71a51894d0708a1cce92d21029","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/63/d5bfe68e9071b52c69d22ad4264c69304fed2d","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/65/7f762ef5ed71c9ef9c5c32e4d9cb935865b504","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/68/3724b92370063b24a1b73e0e148f023ed26670","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/69/3eaa5f4374b9a1821e7409b4ec9fa86a3786f6","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/6a/12d885fda3dd20b27766f5e920869495dca343","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/6b/4b2e57b3cf6d5e8f67f9ae2bed0c50ade0b941","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/6d/468d512d4ff632f75087f7f67c84a26675b918","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/6f/4bc33c8b7722d08777c9e4583e6ee571109e0f","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/72/e7baddd1fddcf4cd9f8e0a7d7e0f3b7968c945","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/73/c75bf6a77e9e154371d835729940c09603767c","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/74/43e371d30cd3c158c4fd700714cb9d2140dcaa","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/74/59c61464f482e85de3909d4a3ece9d2a19e8be","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/74/742bfc41e91feb28cb0aef4284cd102ad4b3b5","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/75/5564517106c76117b49910f0f8f34f01652938","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/76/f931c67e47a2a1374a0170a28f9629947f56ef","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/79/12abf0910723fdb8c9bba1562b2b1a20978d03","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/79/3eed80c0193c012d402e1280d9488b1c828a13","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/79/6b9336c7aa1fa1bd9071fff5b61a3e055c53cd","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/79/7524fdd863132d5cc8225c517cfe68c368a7e0","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/7b/23024fc7cbe8ef2960d1e36ccfc235c73f927d","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/7c/2b09f4f5b2a60ae4a42a6562d1f278396df8b8","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/7c/dcda152dfe84dc684abc7a71eaaef6c00f4a64","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/7c/e52ed569d2f3e00647d9a6811542230958a09c","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/7d/a004922df0f6f82fb8d75e56f69140654f2423","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/7e/ef510b6917b0f0ecb9a2534a3db36d563dc0c9","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/7f/b1f125fa3742b3df99f58561307373b8344689","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/81/c1b4153b2554bb720c85badd9b840d636ab016","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/81/f9dccfdd948d5a946e5a894e15dc70efaf9d0b","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/83/1219580640962d42d473aff1481536edbf4137","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/83/fff7e286172b1db86e4f976ec9793806a45685","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/84/9437dd01f27c1e4c5236774643d1e448999b3b","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/84/c02eb556c8052f3cb57b311d022d0127266658","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/84/e1fa8f5d2cbb8e07d36a63900891fa9d7f3fd8","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/85/0043f623e78d894a0f397a8c69310db6109723","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/85/16f9ee18b5c60fdc61ea7d8b46b5e2b38ea4a7","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/85/66c26908a17ab8b1b93f4a7a13953cbb2020c5","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/85/8735f67721bca81a63d83b290cd349815802ef","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/86/69aee85135281de089335c2c94d2a89ff6c961","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/87/415e64bc33f23de887684a8aec65e8d8df5f2f","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/89/8630859cbeef3efdd38ade03fcbc96e589d543","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/8b/5d28e9bf9ce0f568a5376c7503f139dd86ff79","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/8c/6ff412bd42d85fe224f6cde4cd8000cb11ca2e","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/8c/8f054034f54ec6a1eaa1ce58cde3a8e9172277","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/8e/f26b8e1ba1bec553d97304fe8588f9c64fa605","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/8f/4e2107c52cb9035321c1156cfce1b8151952f3","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/90/8a3c4837c68097a79ce5bf70fc3c6e5cb70680","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/92/47083471dd15d03938e09978f326a07e50cc4b","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/92/ad88d2e59935239e7e98561d2692fad745acd5","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/94/407ada81301fda27e4032ccd8243639b8ee78b","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/94/84c002ab835575363b8db16d5b16913f7b7610","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/94/c6e211f544d7822ed5192211a1ca9d256805c5","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/96/63fe29637f1f3134beff1ba1ad3dc0fc0aa191","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/97/831137eb73aaebb12a305a5069bca3027c591c","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/98/2580d5381a62f5352ca08c29bc64c0bba33f8c","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/98/a26e0b5b23a1699853988dc3659cf3660d7d61","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/99/a322da9867e8be1879630b1575624c5137aff2","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/99/b969be235c3b71511aa50c24c556abbced244b","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/9a/1f7e81d585cedd491b8441b5a06113c9c70ef6","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/9a/23641ef851557b901e606b0357620e3c10cb25","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/9a/36454d89871c963079adcb3756b63d02202078","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/9a/378914b945c9a81be69d44a0205f0c023a5691","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/9c/ec285f9c52045d5c897570a1f91659930c1117","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/9d/2e60547d5dd1c5152958af8888b48c0aa5e4ee","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/9d/3ed1f902075504a1a8aaa6c498b5bf455be8fd","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/9e/474a399b55e54846630a928797ef26f4a4952c","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/9e/f1e47a2eef95b0255bd7bb9731e82f00ae9d8c","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/9f/7ee39bead128f3aedbd79dbb017382f5243530","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/9f/b5ccfe57a543e76139bde0506566a1e7fa21d0","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/9f/dd1e25ac3aac9aa97c414f25fabd7158c69031","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/a1/9ce0eb4e7dfecfebdd032f91d297f0a316091c","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/a2/376f3b5912ea344025bd1bed92af165f988c2c","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/a3/1f721327d09391010f3a97d24b1c85eed4804d","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/a3/fbc51587b89041c0132217392761c8420a2678","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/a4/05555bf99194b687d1fcb45154da53a9b501df","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/a4/92fec5ccfd3c8fc5e2622f565e42d6723c894e","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/a5/05d74da3ff9642d2a6c42e6e972fcc34bb6f47","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/a9/7c2352ff91a022ddab8a87de365fab60904ef3","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/aa/d6aadf05499654ba3fe1dc04cb27e15a80cf52","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/ab/92e46c173f90bd1ae2906e3f2859ca82e35c64","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/ac/cf0c77e2bec7f3c3340aa6e6c6a6c4c703ad15","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/ad/0d491416e162619217f6041fc73cf9cf2be2c8","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/ad/d38c8fdb8304af0ff5802662a05718f5ba50ef","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/ae/0719dff9e5612afcdd849223c5dc26fea78a4a","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/af/15a36d75c41954a70e37e84b5f9185e29846d2","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/af/523e138ede7cbf00cc2bfb0d38c94abe086a97","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/b0/4953f358f468bce94bc56327f692de6161b4e1","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/b0/5e860f98d930be079abbace29c10a467607646","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/b2/ceaeda0c88b3569b572179fff146fd206c9a1a","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/b4/60e2ac29cd345e391ff4610136bd34122a1625","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/b4/ea85cf39db22e7248d1c86634505e64df9f809","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/b5/4efc22b698871a86a55bebeb8eb9979eb42c08","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/b5/7439bbb229e3221541fcf537db911a501b181c","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/b5/dfa097a44ce615a42d574a305fab6f88f4c9af","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/b6/3416e0bbf6fb2be142970df9482e48eedc2fbd","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/b6/496ccfda77e420073c4b32ed95561a2b8cff25","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/b6/68a76b55a0d82162363978583cc17698c3f17d","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/b7/279f55f7a81d13a64d96c0fc0ebfdba887351b","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/b7/f4f2defbb8620e2f7ec8a0343f009a41e7d34f","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/ba/5b664e273b0df7b8bc345932e1c4c3b37a643f","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/bc/b6a05beeee5947c260b0c17e85d7f2d28930d5","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/bd/4933b12c35f170ef1fd8c434a8068e48de18e4","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/bd/8fd198b7faf3159de8d208f7b9da50e3bb258b","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/bd/bec42758beaec651520dc545c06571002bfdc9","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/be/1aedc7d2770044ffa77fe5adc8c56a3b5740d4","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/be/8a32b2faf25e9f6bfffdf45557bbcd5b04feb1","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/bf/b479d690c7949e351b211c3b26b443a243fe55","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/bf/b9ff2ca29f2f1e65f87ddb1f14e8fd1268424c","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/c0/378dd7f72747636c94c930c830c69e87a40063","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/c2/6729095ccfd327f00bc75b03fdc14dd70ca29e","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/c2/89ce68ad8e8b46792aa5208ec2fc99688e0425","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/c3/523495e11a180fc1515a045684f5d6d0090d48","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/c3/ea52dfdab2719accd9d879969dda718b468eb3","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/c3/eb8c0f35081ceb91dcec092e172a97b128c7f5","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/c5/57b32bd71ac0e2dfd3ec7dd8e12e86edb38996","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/c7/258feabcd446128c047c3bf6650a13e1e2511f","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/c7/4b1fb2772c2b014c9f85ce6053c2fe81b70dfc","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/c7/9b7ca916ab1a537ccfb8eb9ba358a9892fe69c","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/c8/4c2900e352ca38b0a9bc5f0682258524b2f8e8","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/c8/8db02d5bd62e0dcdb3e99bb29525564492d101","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/c8/bf0f512b7313831c5dd2dda5158b3f0abff5f4","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/c9/aab3a2008cab1640bd82b6696705fa677fb68a","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/ca/62c15ac82fb1e64249669ddf03c58f415d876b","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/ca/c7d0a2a167de527d89b0f1bdd7fbad626e0f24","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/cc/1185d1dd805bfd534269908cdf88a88feace93","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/cd/3b4f3f98cf443da2624d3f62479bea6146a8b3","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/ce/2697a86214d3df87e38c28222e0ccb912ea8f5","mode":41471,"size":48,"sha256":""},{"path":"/usr/lib/.build-id/ce/821aa7a062a6eb2732035b66c3c3351ba16fac","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/d0/33cc4530ed4f410b932814354db1ff80c1c92a","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/d0/fc6ec6a85a6c1054671731c6af56a823467191","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/d1/683e5ba3462d50a2aa165f4e885e6bbd2d5541","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/d1/c6cd24a8820d2163664bbab04cb9758fe53a3d","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/d1/dae9d35c7b4b42dc2c55a3c025506428c046d4","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/d5/f90de11e2695a8e4f641b443471399e8d614f5","mode":41471,"size":51,"sha256":""},{"path":"/usr/lib/.build-id/d5/f90de11e2695a8e4f641b443471399e8d614f5.1","mode":41471,"size":51,"sha256":""},{"path":"/usr/lib/.build-id/d5/f90de11e2695a8e4f641b443471399e8d614f5.2","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/d6/bb8839ce823f0b7a137d08140ec5e7abbbe696","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/d8/5f05783eb8e5d47bdb035eb3787b55be9309de","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/d8/73c14b4bcad5bb75c7f2afeee6599268b3616e","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/d8/e5b959d3cb03b38960f67e248ad9e6cc99bf7a","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/d9/4a2725956841d38ee64a44f8044f8c844950a1","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/d9/4e304df603659795e66305c231b0eaa9341aa3","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/da/61fb8c886d06491ebc4ab869d70d19138780d4","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/dd/75edf58317edcb4140e9a3015b0ad793937ee7","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/de/a1b2450442d5ec62081384cae3013fb32ab126","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/de/a1da12131d855b3f6bc388ad7c21adbbb57fdf","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/de/e9fac226575c3ef3c53ab3b1e7790e6a77189b","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/e0/688f6aaa85bdc721e367010a897846eecf174b","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/e1/516bb676eb5e4ec849fae8c698bd2764786cb7","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/e4/975d12860dd55f058579916278df633ff28005","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/e5/73c7b4ee0331210ebdad69f02645bcd35efd4b","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/e5/76a1f7d9400d2f0888d10f510c00b50b26306c","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/e5/e07930a68e6ef3dd5581cc6412667843b7b4c2","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/e7/4b115832d297f8828a4424379d3cb1eb49b813","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/eb/aefec902627a60dd23f71a9950576974ce080d","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/ec/4976c107e04ad355d43585ac12276552f12934","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/ec/868a65c1ec3b698ce633a3c980dc7fdde16103","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/ed/16aebf7ab56bf4c386dd46ad46de1b21f48086","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/ed/6dbc0b180ea73ab3cb7fc25b329eb45f264e22","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/ee/3413d587f6520e56b2d214da1bf64f0e122b1d","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/ef/75978a309bb119ab1deb212b81dbbc0ab8aa5c","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/ef/c1aeb7852c9135766448857caeafd5e760b8bf","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/f0/669ea8db17e25e0e7338e1f78e8d9063601f7b","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/f0/a4bf0b38b6cb79b04f9e7bb9a04298e6727efb","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/f0/af73cbc0f93ed1d96b7a747c8425f1bbc75b74","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/f3/0c9198dd9b9a170def10a253df516aa12c9afa","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/f3/f1d9dcaf9735ad3b2d5bcd828c458a81c29eac","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/f3/f4a441d172cf6de3eca6bb9f29fd8fc95a4d82","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/f6/0516c4cead48a440791b7868b4e99fd056c148","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/f8/1792bab6aac38d08181f350e90d2885b420767","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/f9/1c45327b5ecf7a307abe0615f917f031ddf052","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/fa/2d12a7c7705ca66d6af13384a5b7c1d9209ee2","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/fa/abf32121d7cdbc2138fd5226b02203758599e1","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/fc/3b394f79d4d3f0c314b380203aadcdf7175cb1","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/fd/c147493de1d9e02ded83a66f714def5bd09075","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/ff/fc08701aa11f8d8200295fb015c9928eeb8632","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/audit/sotruss-lib.so","mode":33261,"size":16320,"sha256":"3713a68da3e729fb983958d27a4b1c79ca6a7dbc3cb5860ac38105ff48bf39f1"},{"path":"/usr/lib64/gconv/ANSI_X3.110.so","mode":33261,"size":27448,"sha256":"1205c0116c2fbcabbb11e13dc301e750a25c3615127c46d25f27f166a783d927"},{"path":"/usr/lib64/gconv/ARMSCII-8.so","mode":33261,"size":14880,"sha256":"259e1d2fb47a0468b5cb301b747fbb6a94b5591b49a464cd2b463ed7efd1049f"},{"path":"/usr/lib64/gconv/ASMO_449.so","mode":33261,"size":14880,"sha256":"5bb53d913d3da5e20af583f50b8cee38fd0a2e507a7e92f12fd6feb1527ab80c"},{"path":"/usr/lib64/gconv/BIG5.so","mode":33261,"size":93232,"sha256":"15ab48c765fd60ec03cf23e102685f8ac1bd8bef38c7bf83a1f3ee2cb1e9115d"},{"path":"/usr/lib64/gconv/BIG5HKSCS.so","mode":33261,"size":240232,"sha256":"5a206e6805c270873ae643c4aea7b0d230fbf1e59a35e6c59f23a72b0a169c8f"},{"path":"/usr/lib64/gconv/BRF.so","mode":33261,"size":14824,"sha256":"efd0030026fc87ad853152651a5eee4925a1b481221c291cc08b32deb7a69416"},{"path":"/usr/lib64/gconv/CP10007.so","mode":33261,"size":14864,"sha256":"2e60947bb64a6eea6d3e65a6e5fe2de7e2d6639bc55c898cac70ae97f49c55f2"},{"path":"/usr/lib64/gconv/CP1125.so","mode":33261,"size":14856,"sha256":"750dcb754305709aa23b6d7515a1049ee8eb5831b23d00228199ac504810bcfa"},{"path":"/usr/lib64/gconv/CP1250.so","mode":33261,"size":14856,"sha256":"0a57c93b6d7bc8dbf7cd2c07a08754706acd97ad51a1afcb26f80d0a7dfaf243"},{"path":"/usr/lib64/gconv/CP1251.so","mode":33261,"size":14856,"sha256":"45d0e7785c0c969604d16200a23540899ce641eb38bd5a2b0a37df93995b20d8"},{"path":"/usr/lib64/gconv/CP1252.so","mode":33261,"size":14856,"sha256":"acdc3491486df814c9148a9a500d1b3e22e369148801b0e8e1ebb33875959828"},{"path":"/usr/lib64/gconv/CP1253.so","mode":33261,"size":14856,"sha256":"f51d0213a996ae64fd41975558bcd319b8513c6a395c64f319bb113a1131782a"},{"path":"/usr/lib64/gconv/CP1254.so","mode":33261,"size":14856,"sha256":"8399189e8a5c0a8fab7a9543e6faf44883799a5546fd0a149e72b0b81ad773f2"},{"path":"/usr/lib64/gconv/CP1255.so","mode":33261,"size":19080,"sha256":"1f6f0c7ae470beeedea74f8aa3cfa32a4745f83c085314893b6ddad843ae368b"},{"path":"/usr/lib64/gconv/CP1256.so","mode":33261,"size":14856,"sha256":"df3eea85345656e412582c155ae728fa76465c7f8b219f99d131993a21ecb2d5"},{"path":"/usr/lib64/gconv/CP1257.so","mode":33261,"size":14856,"sha256":"f3419d382458d430456d1d86632c05120b4b5425b9bc08e40f1fda7f7acd49df"},{"path":"/usr/lib64/gconv/CP1258.so","mode":33261,"size":23176,"sha256":"5a116e2b52da40a17a2082529e454151b4374cd1d940443c7cf3212eba66a829"},{"path":"/usr/lib64/gconv/CP737.so","mode":33261,"size":14840,"sha256":"f4a83ed3b0b8af25f227b450db91aa42b708d412ba670d681f19d70261198463"},{"path":"/usr/lib64/gconv/CP770.so","mode":33261,"size":14840,"sha256":"07fd5fafb78ae3a124db93de822d9a029d170739e5e3a88b4c507f6cf61646ac"},{"path":"/usr/lib64/gconv/CP771.so","mode":33261,"size":14840,"sha256":"6438d145810ce81bc8e4e5e8a93df85cebe78e345dbf49740a018ee32e39299b"},{"path":"/usr/lib64/gconv/CP772.so","mode":33261,"size":14840,"sha256":"bce775fdde2b8e8a3aae1cd1a5f1620d7ee95a7ddd63503d9f91cc0912037338"},{"path":"/usr/lib64/gconv/CP773.so","mode":33261,"size":14840,"sha256":"9a384c9dd7dfbf831c0888cdfc55846bc077a114ab1b9e2f64578e780363bc2d"},{"path":"/usr/lib64/gconv/CP774.so","mode":33261,"size":14840,"sha256":"3b5547d609439d7829a12976107222116b158cffd1f015f687cae473b5c2802a"},{"path":"/usr/lib64/gconv/CP775.so","mode":33261,"size":14840,"sha256":"1e76e4ec2e05ed15e1fb2cf7df7ba759c01b55f8774414cb6b6481abe2d97080"},{"path":"/usr/lib64/gconv/CP932.so","mode":33261,"size":101048,"sha256":"b3701c8812e49da2e7502a42dfafea6c881446462f1828fdff6cc954facd4a3a"},{"path":"/usr/lib64/gconv/CSN_369103.so","mode":33261,"size":14896,"sha256":"97d0f21e5c0b1177b28906cb50f85267b368d1d7376666d4cbbcd54ae23ea8c9"},{"path":"/usr/lib64/gconv/CWI.so","mode":33261,"size":14824,"sha256":"d7c30b519becb87b4f9178506b8b6a2993b3754f4946050e6cfa02d022df39b8"},{"path":"/usr/lib64/gconv/DEC-MCS.so","mode":33261,"size":14880,"sha256":"ab99fa4dce32356bb347d28f7a0dab2895acbe3772ad5ac41ce67ce6e91a50f6"},{"path":"/usr/lib64/gconv/EBCDIC-AT-DE-A.so","mode":33261,"size":14928,"sha256":"76c9cb3290764fc938d7998a6c4b1dc51a9cf68728fdc47dd980732440eca36f"},{"path":"/usr/lib64/gconv/EBCDIC-AT-DE.so","mode":33261,"size":14904,"sha256":"e30bbcbd896ba6405fed86162ab9d94d5fe572cd0985e5a8f37e939ce5c31ce5"},{"path":"/usr/lib64/gconv/EBCDIC-CA-FR.so","mode":33261,"size":14904,"sha256":"91aabffeecf28c63d586efaf1a508b4d92709bba1518f574dfdde5b055d75d8f"},{"path":"/usr/lib64/gconv/EBCDIC-DK-NO-A.so","mode":33261,"size":14928,"sha256":"451cd688d9f0881c21d77fc8c725b2d4b4557c52c12a3b672ac0dafcbb92093e"},{"path":"/usr/lib64/gconv/EBCDIC-DK-NO.so","mode":33261,"size":14904,"sha256":"63598ead3aa79cd0cbcd738fedb7d02849c32b90e00eb00ea159481799d1f30e"},{"path":"/usr/lib64/gconv/EBCDIC-ES-A.so","mode":33261,"size":14928,"sha256":"6566b28b23a88ce14cf5f2c30633968fd8b3c11bef5543ec599d286fc7144e51"},{"path":"/usr/lib64/gconv/EBCDIC-ES-S.so","mode":33261,"size":14888,"sha256":"81fd30615ee0638b215fd6acb7e4c713ad19ee8274f9b60252eed16d1749be62"},{"path":"/usr/lib64/gconv/EBCDIC-ES.so","mode":33261,"size":14896,"sha256":"1ad1ec13d358961c3a5065e213b87b03d5720258d7c6c8edc037285dd60e6e89"},{"path":"/usr/lib64/gconv/EBCDIC-FI-SE-A.so","mode":33261,"size":14928,"sha256":"8bb2e8003c7e3171d778a460efe37b533413b6ba0f2d9630d92a77def0321597"},{"path":"/usr/lib64/gconv/EBCDIC-FI-SE.so","mode":33261,"size":14904,"sha256":"ca2efeaae82d0298ae44066561cfb34e630592fb5b6a86a4b76267f0710f00ef"},{"path":"/usr/lib64/gconv/EBCDIC-FR.so","mode":33261,"size":14864,"sha256":"59b8aeb95b1efb33f60f746f00e5296c37df462eef2df6cc369a80975638d1eb"},{"path":"/usr/lib64/gconv/EBCDIC-IS-FRISS.so","mode":33261,"size":14976,"sha256":"c6ef73d6e6c729b7258e557e1075881f38e14ba21fd8279ba6215ee9731e8cfe"},{"path":"/usr/lib64/gconv/EBCDIC-IT.so","mode":33261,"size":14864,"sha256":"46ec1616df856b4188d05b43094b548825c31fc71b4a09c031227ffd5e769e4c"},{"path":"/usr/lib64/gconv/EBCDIC-PT.so","mode":33261,"size":14864,"sha256":"432016aa6bf458e52eb44831a6ad5cdc6e72f488728199256a6b7433c35a4007"},{"path":"/usr/lib64/gconv/EBCDIC-UK.so","mode":33261,"size":14896,"sha256":"81efd217ec202303028172f5b0254be6da293f616c8b5761c84c5c7a62def7cf"},{"path":"/usr/lib64/gconv/EBCDIC-US.so","mode":33261,"size":14864,"sha256":"e6933965538028b28ed75ee0378e4b4b7f3df9e7c8eaf809cb663749b800a8b4"},{"path":"/usr/lib64/gconv/ECMA-CYRILLIC.so","mode":33261,"size":14944,"sha256":"1699d1c6bb0ae6f20655030273269b617ad682a0509ee25c01180963fd20a5ea"},{"path":"/usr/lib64/gconv/EUC-CN.so","mode":33261,"size":23528,"sha256":"caf1a3e23c8410e7f34405866b4cd2246b5f79aebca9ebc90cde13ad1d1f862d"},{"path":"/usr/lib64/gconv/EUC-JISX0213.so","mode":33261,"size":23416,"sha256":"1d17b0313a70d65e97777e7f8afb4b46d1a33593f5c015cc4522dc254d415de4"},{"path":"/usr/lib64/gconv/EUC-JP-MS.so","mode":33261,"size":92952,"sha256":"a2c497cf1bf88b1b2b1717845641526b2b07f378188de219a16a22efd4c4fd85"},{"path":"/usr/lib64/gconv/EUC-JP.so","mode":33261,"size":19416,"sha256":"a763710070e85755114f0bc1493a3db774ac127ce7b15f42cf6e98d7edc83de1"},{"path":"/usr/lib64/gconv/EUC-KR.so","mode":33261,"size":19144,"sha256":"a3b774dd0d0ec509dc998e5c7f30ba510ca1f7443b04e2cc7ff4d05fce2ed86f"},{"path":"/usr/lib64/gconv/EUC-TW.so","mode":33261,"size":28376,"sha256":"146c9f6c7aa17a6bed25d8eba5370851cfa4a2ad093cfd0e6c03239dc4d2d202"},{"path":"/usr/lib64/gconv/GB18030.so","mode":33261,"size":182928,"sha256":"5a749d318932e61164c30812441b7ac9798c20f9d633dd2031e905bdcc24fbed"},{"path":"/usr/lib64/gconv/GBBIG5.so","mode":33261,"size":59680,"sha256":"a42a6c6b222635178dfa8819d7f92726087599dfa22f29fe81a0697efa130bbc"},{"path":"/usr/lib64/gconv/GBGBK.so","mode":33261,"size":14592,"sha256":"68f0f8a264fdb159a68c304e1ffb822236240e974d7b50571535268b18db23a0"},{"path":"/usr/lib64/gconv/GBK.so","mode":33261,"size":121800,"sha256":"d2383a2ef8d84cecaeb6561a32ecb39548158995453ba3df2ae88f06d5cc2dd0"},{"path":"/usr/lib64/gconv/GEORGIAN-ACADEMY.so","mode":33261,"size":14984,"sha256":"a58e90ceee51338e8dd4c22b5673b5a27a79033845c007d7388a216b65f8466b"},{"path":"/usr/lib64/gconv/GEORGIAN-PS.so","mode":33261,"size":14928,"sha256":"e183bad792c5b89a505b199388e51bc03d30ef448cb4997ab571b359cec6aa69"},{"path":"/usr/lib64/gconv/GOST_19768-74.so","mode":33261,"size":14944,"sha256":"44f63f9abffac1f3bc58cfd9b56302191c9686c17c0e7a5bc6455b87e0ab36bb"},{"path":"/usr/lib64/gconv/GREEK-CCITT.so","mode":33261,"size":14928,"sha256":"ce0a447d48ce125259ebc85d27fcea90fbc6ae5b338764f3247abba3268cdc25"},{"path":"/usr/lib64/gconv/GREEK7-OLD.so","mode":33261,"size":14912,"sha256":"f15ddc64c05a91fde048f93196e9323241778e9cbba1bf609d6908dfb3f7d08e"},{"path":"/usr/lib64/gconv/GREEK7.so","mode":33261,"size":14856,"sha256":"a1e728e0a4b484879789796ad9d3e1e416d07056dd6034fd1f4de97f686e0367"},{"path":"/usr/lib64/gconv/HP-GREEK8.so","mode":33261,"size":14896,"sha256":"bc322a18b853f0ec4e06f00d21c2543a6114a8e214ce9f26ad14a4c37ad5b4ee"},{"path":"/usr/lib64/gconv/HP-ROMAN8.so","mode":33261,"size":14896,"sha256":"7d58c94aeb0ec9e844ece35e9a021a765d3039e63188e62a5f23cce79257a61e"},{"path":"/usr/lib64/gconv/HP-ROMAN9.so","mode":33261,"size":14896,"sha256":"fe7bb19d424a8d8f421812f467d6d54fcb308a4ef1c67193bcf2e91e4937f75a"},{"path":"/usr/lib64/gconv/HP-THAI8.so","mode":33261,"size":14888,"sha256":"3b930946cf2f8a0ea79229705e4b96ab7881943f7a8c532e2ce9902094bb0760"},{"path":"/usr/lib64/gconv/HP-TURKISH8.so","mode":33261,"size":14928,"sha256":"d678ed98c7ce6074e1bb90cc297205b565fb4f8895e7ea372d6f4c8152bd4590"},{"path":"/usr/lib64/gconv/IBM037.so","mode":33261,"size":14816,"sha256":"2bf0af69e8e79c2dd5615243a58206549482cecce74b488b00e050e6636cc8b1"},{"path":"/usr/lib64/gconv/IBM038.so","mode":33261,"size":14816,"sha256":"fb2cbe6a517fdf24ddd87acc77856106a9a4b36f1d8e4236b6e82ad7cea8ae8f"},{"path":"/usr/lib64/gconv/IBM1004.so","mode":33261,"size":14864,"sha256":"08283aba23cee529a33685e2b59ab8b160a3e7ac858c003090209d3c96945a8c"},{"path":"/usr/lib64/gconv/IBM1008.so","mode":33261,"size":14864,"sha256":"2129f6e3e9b4aaaa7e68aa7261ca81a483fbeab0d1517d9dc1f88b39ad6cf01c"},{"path":"/usr/lib64/gconv/IBM1008_420.so","mode":33261,"size":14592,"sha256":"84c21edff9eedec7011de4ac49e945ded74fa241caea1adad48e7e49bae96229"},{"path":"/usr/lib64/gconv/IBM1025.so","mode":33261,"size":14864,"sha256":"618d8863ade1c5459d05ced82900e46055beef9ff477f9aa48ab9321d4b24014"},{"path":"/usr/lib64/gconv/IBM1026.so","mode":33261,"size":14864,"sha256":"2cb2c20d6d189795dfd59b2c3c0587b69904df3064fb57a55b2676ae63395d9f"},{"path":"/usr/lib64/gconv/IBM1046.so","mode":33261,"size":14864,"sha256":"9b4e4e023b2834685f4042db472b76772c7556460a21f56686b5af3ce3a612a8"},{"path":"/usr/lib64/gconv/IBM1047.so","mode":33261,"size":14832,"sha256":"627dc8cfe1c9b57a7e918d4687a411849c1ec7a0cc6261e640d924d1fd58da61"},{"path":"/usr/lib64/gconv/IBM1097.so","mode":33261,"size":14864,"sha256":"e11193271483b9fc00c22b1bb0e4a544ab2b65e467432d5f81773f10f39161e9"},{"path":"/usr/lib64/gconv/IBM1112.so","mode":33261,"size":14864,"sha256":"d0771dc91d64d0f685962fa44f06b5d9dd49fdcfad619dd54499847266a0e825"},{"path":"/usr/lib64/gconv/IBM1122.so","mode":33261,"size":14864,"sha256":"c4de37ae4bdbb87f0ade5ba82fa36447b1fb9cf4038996be80e896331d21d42f"},{"path":"/usr/lib64/gconv/IBM1123.so","mode":33261,"size":14864,"sha256":"b29dde90e7a59e862d4103b9d3fd449dedf2635a10b7f520a018fba9ea462a95"},{"path":"/usr/lib64/gconv/IBM1124.so","mode":33261,"size":14864,"sha256":"41133481c1425428939b3979da95f8d8a0a2cbc9cdc058d09bba81f200f54a1e"},{"path":"/usr/lib64/gconv/IBM1129.so","mode":33261,"size":14864,"sha256":"8cd28926269e802285be910d3dd8de62701ee96e9cd3fbf3d571442357cb4f5c"},{"path":"/usr/lib64/gconv/IBM1130.so","mode":33261,"size":14864,"sha256":"b9e29dd4787406844ef9202c4d48926c044d04123c19bd6fe802965442a7647e"},{"path":"/usr/lib64/gconv/IBM1132.so","mode":33261,"size":14864,"sha256":"b035a422ea481f731a4f4343daac1b33e0a6c83d3235d753bbbdf187e7205155"},{"path":"/usr/lib64/gconv/IBM1133.so","mode":33261,"size":14864,"sha256":"f2e4ef470b3e09912d06907f58eca4a7e0ee30f984a2bf809820f29f7ab98269"},{"path":"/usr/lib64/gconv/IBM1137.so","mode":33261,"size":14864,"sha256":"99351a991b19ee98a7fd542845d6d74fbdb936fd44c1b1e980c222e0fde4980c"},{"path":"/usr/lib64/gconv/IBM1140.so","mode":33261,"size":14864,"sha256":"39a575311fe4409cb7211b40e75d3025b1d7e31c9a7ce36a0916f42ac0decf6c"},{"path":"/usr/lib64/gconv/IBM1141.so","mode":33261,"size":14864,"sha256":"c0fafac0f3805f349149d55ed8c1e1136a9abe871069ac0945d759918f3f83bc"},{"path":"/usr/lib64/gconv/IBM1142.so","mode":33261,"size":14864,"sha256":"9de34104c24313a4b998aa3fae405e6317eca6a545479d4e9bb77b2f916cae2f"},{"path":"/usr/lib64/gconv/IBM1143.so","mode":33261,"size":14864,"sha256":"70a0d655db1e8cb2ff79656c271055dc1f98b069920304d211d77a5ee7e97488"},{"path":"/usr/lib64/gconv/IBM1144.so","mode":33261,"size":14864,"sha256":"6fadbf6865612ccae99e2397411b5f33f913f4f26eeb3df5010342acc367c599"},{"path":"/usr/lib64/gconv/IBM1145.so","mode":33261,"size":14864,"sha256":"9d33f86dd36b9656a21afbe3bbaba2c739f5b547db31e148073a2697ec6eb986"},{"path":"/usr/lib64/gconv/IBM1146.so","mode":33261,"size":14864,"sha256":"824e888c9d33e073ffad7869470821740e9dcc3d29e8b2d9e9747a01eb44e6ae"},{"path":"/usr/lib64/gconv/IBM1147.so","mode":33261,"size":14864,"sha256":"35e0ad5e620d5adba8ab376c74b672fc83f0e047746ca62bad28adeedc9bd37e"},{"path":"/usr/lib64/gconv/IBM1148.so","mode":33261,"size":14864,"sha256":"17c6b32cd7dc3553bbf4e28be0fe7f0a5b0207714f37d01ebbf221b2b9159b90"},{"path":"/usr/lib64/gconv/IBM1149.so","mode":33261,"size":14864,"sha256":"85cde014dcc1f52e9c7e3fcc4a8c29aac69957f398e68feceeaaa2ec36fba6ce"},{"path":"/usr/lib64/gconv/IBM1153.so","mode":33261,"size":14864,"sha256":"5e2bd406c2cbfb84f73b511f95e5f58ab203d9457734781abadfacb3ea8816d7"},{"path":"/usr/lib64/gconv/IBM1154.so","mode":33261,"size":14864,"sha256":"851d84dd49b6db349b074078b80ba86aafe8bfae36647c0cdb44f10203d49475"},{"path":"/usr/lib64/gconv/IBM1155.so","mode":33261,"size":14864,"sha256":"ac6f9603a46f3f1938640e02a81863de5a90882a87b63d86802e2bb5659f22b1"},{"path":"/usr/lib64/gconv/IBM1156.so","mode":33261,"size":14864,"sha256":"688fc7e1edb854144a17da839ee29c9fbd836efac400fc42856718d2a0c3212c"},{"path":"/usr/lib64/gconv/IBM1157.so","mode":33261,"size":14864,"sha256":"c810a299c0db31aaa5e4d32078fe005b109986a5597fcef12b0297593d2a62e6"},{"path":"/usr/lib64/gconv/IBM1158.so","mode":33261,"size":14864,"sha256":"7083183f1f8896a01061978e8ed295357ecfba2a7d36cf1b950d449219dfc672"},{"path":"/usr/lib64/gconv/IBM1160.so","mode":33261,"size":14864,"sha256":"451037b1df5419210b241516ba1c2305e3a827e8c3b7b195948c204e6d705ddd"},{"path":"/usr/lib64/gconv/IBM1161.so","mode":33261,"size":14864,"sha256":"1748b5c1a1208588258edd94afd7db4c5c6a6902864a791f3afe004f7998c3b1"},{"path":"/usr/lib64/gconv/IBM1162.so","mode":33261,"size":14864,"sha256":"5b3aa87042ad87ca11d45dbcce028670ee8d9ad6d14433f61fcd01aaebc71aed"},{"path":"/usr/lib64/gconv/IBM1163.so","mode":33261,"size":14864,"sha256":"0ca4b579a216776eee6b041bf1faf0fb48070353ee3b4836816e76cfcf990b3e"},{"path":"/usr/lib64/gconv/IBM1164.so","mode":33261,"size":14864,"sha256":"c1475208876deda2d1b05f2eb8ac857af23097a0de8ae890e64a384c4ec930cf"},{"path":"/usr/lib64/gconv/IBM1166.so","mode":33261,"size":14864,"sha256":"89650ff6395513b524a3374f009bc0730af3ca1c805f2ac54dc391fb35a5f369"},{"path":"/usr/lib64/gconv/IBM1167.so","mode":33261,"size":14864,"sha256":"10c093535969b08ccd51c96f07ca10f71b0b73615ec06a9325c8c9417a2805b4"},{"path":"/usr/lib64/gconv/IBM12712.so","mode":33261,"size":14880,"sha256":"c59e1182333f466b6f007bfcc1c321b4a12bcb17fafaf3a5c12590b3eff6fcca"},{"path":"/usr/lib64/gconv/IBM1364.so","mode":33261,"size":154184,"sha256":"f3b695fe69bfc2d7f3fd54bd2632ff58468c4c1c84b0bdefaebde514460a8cc0"},{"path":"/usr/lib64/gconv/IBM1371.so","mode":33261,"size":133704,"sha256":"1600b511e0f3e1856fa944d3050b11ac3b10d887c6236f9356bc093d7e68c7c0"},{"path":"/usr/lib64/gconv/IBM1388.so","mode":33261,"size":178760,"sha256":"05a4a9496efbb2668914b3e3804143f8ef8444cc9c76f0261fca85e77746a875"},{"path":"/usr/lib64/gconv/IBM1390.so","mode":33261,"size":236208,"sha256":"4d484e624ae5dc856640e42da801b3ec315eec2947d4bea2b5e68a3ff44e32af"},{"path":"/usr/lib64/gconv/IBM1399.so","mode":33261,"size":236208,"sha256":"89d1928c09434d53cd128b79ad80e71f5300c596bc14f559436109939fdfad39"},{"path":"/usr/lib64/gconv/IBM16804.so","mode":33261,"size":14880,"sha256":"ad84de613537ecc9ff24d60a8a55f1bdeb790c795afb95a5efc3702604c25c06"},{"path":"/usr/lib64/gconv/IBM256.so","mode":33261,"size":14856,"sha256":"6ea96f7ae609a0e24b157073da6e8ef8f7bf017a2334ac0bf34ef9c0f0d4fddd"},{"path":"/usr/lib64/gconv/IBM273.so","mode":33261,"size":14816,"sha256":"9c45527a548f95a3fd015a32a6bc69a42a82996a0cb270d9961bf6a1d00024ea"},{"path":"/usr/lib64/gconv/IBM274.so","mode":33261,"size":14816,"sha256":"78f0e5a32d4475853ec2521b8a670c7f9a13a917ac802b7759a7d4d0a5a295d8"},{"path":"/usr/lib64/gconv/IBM275.so","mode":33261,"size":14816,"sha256":"d4c8ea19530899e4e6cdb938a184badd838167872023f90605cc2498c2649163"},{"path":"/usr/lib64/gconv/IBM277.so","mode":33261,"size":14856,"sha256":"193ba85505049b4cb80ce6c1a6eed13cb8903e35e59c4266a2aa8f29e171a52c"},{"path":"/usr/lib64/gconv/IBM278.so","mode":33261,"size":14856,"sha256":"5a2f92ff1d6b0b347d014f5be638affe90423f471b18c9cb0d88f30ef84a2264"},{"path":"/usr/lib64/gconv/IBM280.so","mode":33261,"size":14856,"sha256":"0aa6266ea3b9520bd0ab61af70bf5d9569b64843bb391f740f9a1aa0461ae49a"},{"path":"/usr/lib64/gconv/IBM281.so","mode":33261,"size":14856,"sha256":"b98c27d59a811f0440192d6fc678d675e5c3f68a4354b7becaa6a9f463830885"},{"path":"/usr/lib64/gconv/IBM284.so","mode":33261,"size":14856,"sha256":"0b444e2e4196426d463702294babdef34fbd658f8d850db4a6cd9ae37713e8ee"},{"path":"/usr/lib64/gconv/IBM285.so","mode":33261,"size":14856,"sha256":"090bed1587216638c0f799a14b39825a77facaed63b148b906c2d4a6c94f9a15"},{"path":"/usr/lib64/gconv/IBM290.so","mode":33261,"size":14856,"sha256":"4c0d9f3252fa794cc8ee443ee1333dc6d91a79f43b2a5796296ae390e1a31783"},{"path":"/usr/lib64/gconv/IBM297.so","mode":33261,"size":14856,"sha256":"2775158213110d2f237226b7265f681fadfe52322423ce3633d6629a6d11d54e"},{"path":"/usr/lib64/gconv/IBM420.so","mode":33261,"size":14856,"sha256":"43e3456c717298d78a0897a267bfafe5f34d06444d9317c7b4b09bb0045f5281"},{"path":"/usr/lib64/gconv/IBM423.so","mode":33261,"size":14816,"sha256":"25a6040e333d58b6b54a271c792828f8e5aedac77dd7073854fb46247c1f72c0"},{"path":"/usr/lib64/gconv/IBM424.so","mode":33261,"size":14856,"sha256":"a54bf1288b4d7ab36b83098de2ba6c8ba6cdd640fd07c97d305c1362004849b3"},{"path":"/usr/lib64/gconv/IBM437.so","mode":33261,"size":14856,"sha256":"22f205633a53df1448f7e66c8bc9982c86e0268f5aac26a4dc6ec77237d56180"},{"path":"/usr/lib64/gconv/IBM4517.so","mode":33261,"size":14864,"sha256":"5167f515fdf9851671ef4aaf6e453d8de1d2f1f6647a06456503f4ccfeaaac34"},{"path":"/usr/lib64/gconv/IBM4899.so","mode":33261,"size":14864,"sha256":"02c39094eebeaa5546ecf6f220980e62b49c0e77ff6b58e98c6103ce00c10f14"},{"path":"/usr/lib64/gconv/IBM4909.so","mode":33261,"size":14864,"sha256":"4aae8fa9629ac255d12eba525cc58f1c7e4344fa2c1f6542792cf847856d81a6"},{"path":"/usr/lib64/gconv/IBM4971.so","mode":33261,"size":14864,"sha256":"68b6b4f4bf9b335946dc8ab28b383c0c216344296b0721c5ebde3a0fc0bcb8bb"},{"path":"/usr/lib64/gconv/IBM500.so","mode":33261,"size":14816,"sha256":"2869c8d9b98a2c9df43fc9c82b502858d431f3c52472e0274ec96721a95da420"},{"path":"/usr/lib64/gconv/IBM5347.so","mode":33261,"size":14864,"sha256":"923cace0a69c1da1853b1c8494251252474620dfcaee446d6388f23766ef107a"},{"path":"/usr/lib64/gconv/IBM803.so","mode":33261,"size":14856,"sha256":"603a92767acbea4782970057cf7282bf885dfe7d79e39839f2f98c527a23285d"},{"path":"/usr/lib64/gconv/IBM850.so","mode":33261,"size":14856,"sha256":"c1633136da6d64c31280fc07f9c90220ee8dfd0537b38f5449543fc02744a1fb"},{"path":"/usr/lib64/gconv/IBM851.so","mode":33261,"size":14856,"sha256":"4a636ffd19aa674b9c55086feb63a283ab6875c5653ed9cc985306f341750043"},{"path":"/usr/lib64/gconv/IBM852.so","mode":33261,"size":14856,"sha256":"0e12c1cdd2d69aa0772f0f70c8c8fcc77c9bf244001df92d8420212f5f38cf19"},{"path":"/usr/lib64/gconv/IBM855.so","mode":33261,"size":14856,"sha256":"b194594ecb07dbb23740b03f49c858f6f419a5723dcdcd14121791b467359c5e"},{"path":"/usr/lib64/gconv/IBM856.so","mode":33261,"size":14856,"sha256":"6709e1da8437f9a72f99fe3a2b9ef4f426dd7a925e838fdab1d6e7ae547d897d"},{"path":"/usr/lib64/gconv/IBM857.so","mode":33261,"size":14856,"sha256":"bd4396cc3f5701a4cc3d396f459e5576b114919aad1085682b274bbe7f46605b"},{"path":"/usr/lib64/gconv/IBM858.so","mode":33261,"size":14856,"sha256":"975365c8dc39966bb8482fee6b9f12dfe3abc26c7bfa21db5830af941a886278"},{"path":"/usr/lib64/gconv/IBM860.so","mode":33261,"size":14856,"sha256":"2f2bd4a665f85e21f98192efeac7d2a56cedfc84fa128582a61cd5a09ba3fbfa"},{"path":"/usr/lib64/gconv/IBM861.so","mode":33261,"size":14856,"sha256":"a65b27db512120ae3e5746fbbf5fd4668a2b1fe9f0c25a4bfb32467202fd0b09"},{"path":"/usr/lib64/gconv/IBM862.so","mode":33261,"size":14856,"sha256":"c285f10b46ea65528a31ddc3623782a392c12d2c79ae97a745355a52490c5037"},{"path":"/usr/lib64/gconv/IBM863.so","mode":33261,"size":14856,"sha256":"f54c22c53811e8a9611b2084b931da4393581104512a759641699b6ca577ef8f"},{"path":"/usr/lib64/gconv/IBM864.so","mode":33261,"size":14856,"sha256":"90695d14ae14306aec0221eab855e6df0965bab6dbcef78344dd70b1a1bdedd9"},{"path":"/usr/lib64/gconv/IBM865.so","mode":33261,"size":14856,"sha256":"e599b04517b66c2541a33f5511675343915294be6a5fb3538dbc5618551d0995"},{"path":"/usr/lib64/gconv/IBM866.so","mode":33261,"size":14856,"sha256":"542b9ce9dcbc452cfe442e6db3bddaac39b40c24181252d32fd4a33eb0703955"},{"path":"/usr/lib64/gconv/IBM866NAV.so","mode":33261,"size":14888,"sha256":"e4eed8695e9b62da6450f53a241b7fddf95173bad16bb83b2da2de7d86525368"},{"path":"/usr/lib64/gconv/IBM868.so","mode":33261,"size":14856,"sha256":"5cf3c74ff710658ca7467fc6c6cdb846abb7a78727d1d0650025269c817ce392"},{"path":"/usr/lib64/gconv/IBM869.so","mode":33261,"size":14856,"sha256":"3ed7891a7539f9296e53d1288efa7be0539466575616dd3cf5b0d3b48fb313c6"},{"path":"/usr/lib64/gconv/IBM870.so","mode":33261,"size":14816,"sha256":"4b9fcd666769661631860557c86b61fea34a9ff3463d481ae03b5352a9bf9d3c"},{"path":"/usr/lib64/gconv/IBM871.so","mode":33261,"size":14816,"sha256":"64082d08b199190534b510c99be55c469b52403d66b25a21416679ff2429521d"},{"path":"/usr/lib64/gconv/IBM874.so","mode":33261,"size":14856,"sha256":"49ea79974c12fd3f5d26f55d8009f89f8bda8bf5f2eee8c5d66065cff294d08d"},{"path":"/usr/lib64/gconv/IBM875.so","mode":33261,"size":14856,"sha256":"a190d947544b1cb5ce4c6911c8c2feefab9a004fb3e8e270291de1779abcc10f"},{"path":"/usr/lib64/gconv/IBM880.so","mode":33261,"size":14856,"sha256":"7363026875e5bbf2cb8f0b76363974911a21609a4e79b885f117df1180b368d7"},{"path":"/usr/lib64/gconv/IBM891.so","mode":33261,"size":14816,"sha256":"ae6e58c26d9e97fd20a46efb5b1f9075cffb0cc676ec3d5f2ee806e810e73042"},{"path":"/usr/lib64/gconv/IBM901.so","mode":33261,"size":14856,"sha256":"52389d94d8d8e104b6e965ff6706aa51330ac22e634ab70850228fd2a51db9d4"},{"path":"/usr/lib64/gconv/IBM902.so","mode":33261,"size":14856,"sha256":"d63f3407b71e98866714443f4568334720ac6b9ce05df5aaeed2679174289513"},{"path":"/usr/lib64/gconv/IBM903.so","mode":33261,"size":14816,"sha256":"abdc53a994125133a25d5734f78c19a2e35e823bd477d85664fe2bde1bd8bd7d"},{"path":"/usr/lib64/gconv/IBM9030.so","mode":33261,"size":14864,"sha256":"1ee9287bd442b2409ae32d2ff3c36d7fc2a9f722f186ffc7b21ce207e513c982"},{"path":"/usr/lib64/gconv/IBM904.so","mode":33261,"size":14816,"sha256":"cb6642600cd28067e82df344e09bce1c87a8a6c11cb961101dfeecb561cc7913"},{"path":"/usr/lib64/gconv/IBM905.so","mode":33261,"size":14816,"sha256":"d46664d290dfa234dc9bcad722c72573e9f96a56096b2e7e4e2bf900b4c935cd"},{"path":"/usr/lib64/gconv/IBM9066.so","mode":33261,"size":14864,"sha256":"3a212c2e0066c196cde828a588fbe90c2cb2be65a54a5cb0fcde3b94367d687c"},{"path":"/usr/lib64/gconv/IBM918.so","mode":33261,"size":14856,"sha256":"8afe1a4038a127e73e2405d95f395c77a569e6a8233b097b277af95781b2e32f"},{"path":"/usr/lib64/gconv/IBM921.so","mode":33261,"size":14856,"sha256":"4ce17d31b7b65770a42aa8513980e740bc9709534fd3d173ce45c134a3b44701"},{"path":"/usr/lib64/gconv/IBM922.so","mode":33261,"size":14856,"sha256":"f493268545f32424fed1f5bd8f0e6c26743815a2e3d7ee3eabccb214846c6e29"},{"path":"/usr/lib64/gconv/IBM930.so","mode":33261,"size":100984,"sha256":"f3a11df90dcd64cae248f55e1aa40ec2cde797dee74ef24749ec317ee7144e78"},{"path":"/usr/lib64/gconv/IBM932.so","mode":33261,"size":76512,"sha256":"cb017467be5036d17653f453f40e46263d9848b9b033f2b79f5d32a05425ff8b"},{"path":"/usr/lib64/gconv/IBM933.so","mode":33261,"size":121464,"sha256":"c9b0a3ac1a40461a9489ba2e46105078f68eb63e17b6e081a4e6520677f1cbcf"},{"path":"/usr/lib64/gconv/IBM935.so","mode":33261,"size":88696,"sha256":"9623f3bdd9172e49b1fb58da48cd8745c45694e5861758db66be3b2f591d6559"},{"path":"/usr/lib64/gconv/IBM937.so","mode":33261,"size":117320,"sha256":"768855670df4ef257002aaca3491d8b0da5a67328d8bdbab9067675186277caf"},{"path":"/usr/lib64/gconv/IBM939.so","mode":33261,"size":100984,"sha256":"eeb367dd0ce940fbed75f88a77cc4476bfde1fed68a2e5e930e1531ce36cc963"},{"path":"/usr/lib64/gconv/IBM943.so","mode":33261,"size":76512,"sha256":"78985cc0b9a47ff52d3f5a61b04116710d11e2cee3ed9477777c26f05647ab30"},{"path":"/usr/lib64/gconv/IBM9448.so","mode":33261,"size":14864,"sha256":"9b1b12b396e6ac0068cfa243f78a205f4e2a18b8b954642cfa0225affa481f74"},{"path":"/usr/lib64/gconv/IEC_P27-1.so","mode":33261,"size":14896,"sha256":"71659aaa868da7d3dc69e73172651e5df6c34b013d01e06c9c218288e724d6d9"},{"path":"/usr/lib64/gconv/INIS-8.so","mode":33261,"size":14864,"sha256":"09f792f165646e51357f8d31bf4fc878581986932d9d598e9ce5f8d5eb0ee7d5"},{"path":"/usr/lib64/gconv/INIS-CYRILLIC.so","mode":33261,"size":14944,"sha256":"02ce2e773488dd367bcac76b824d5d51aa926bd4bc3f8fc7df8e0b37e9c7e020"},{"path":"/usr/lib64/gconv/INIS.so","mode":33261,"size":14800,"sha256":"6893cc5c77ae50ddc54c128dbb096aa4f557c4a872722549b6af6bef8d6ccc43"},{"path":"/usr/lib64/gconv/ISIRI-3342.so","mode":33261,"size":14912,"sha256":"03b6c03a54e2af73e85a479236311c61d3b9334d58797f16b16e0f784519047f"},{"path":"/usr/lib64/gconv/ISO-2022-CN-EXT.so","mode":33261,"size":45424,"sha256":"e57d14864c0979f2c323f436ca609bf2ca7a33345bb77c4ce57b0a21d4753954"},{"path":"/usr/lib64/gconv/ISO-2022-CN.so","mode":33261,"size":40752,"sha256":"4cda6a8639576cb2d49f210ccc660a7b4b7c4f019bf0d0b3e81325eed68e11ba"},{"path":"/usr/lib64/gconv/ISO-2022-JP-3.so","mode":33261,"size":31704,"sha256":"6bed47428499aeb8f18a456421de53fe1c45282866a84b024f54c2e290e64c52"},{"path":"/usr/lib64/gconv/ISO-2022-JP.so","mode":33261,"size":49408,"sha256":"7a0756980ac780922ec2c78df8908fe6f34964bd358a27f9493a8304ab4ae048"},{"path":"/usr/lib64/gconv/ISO-2022-KR.so","mode":33261,"size":19056,"sha256":"4afc7c27776712fe20c1fbeb9b7d2697490e8ee4ebd310283bfb87b2cb900ba9"},{"path":"/usr/lib64/gconv/ISO-IR-197.so","mode":33261,"size":14912,"sha256":"72765c44f7528e2f241e1a157d261fac129c4ca98cfdf06be5bf4477423297eb"},{"path":"/usr/lib64/gconv/ISO-IR-209.so","mode":33261,"size":14912,"sha256":"0185daafe6f4b03be2315dcc2d8fd697abb16d146f4cec1a15ab364df4c56bf3"},{"path":"/usr/lib64/gconv/ISO646.so","mode":33261,"size":23184,"sha256":"8b78746f46f2d449c0e1bba4425e7555d734eecd5b06c1e36ff96976bd482191"},{"path":"/usr/lib64/gconv/ISO8859-1.so","mode":33261,"size":14800,"sha256":"cf4cd591532dd64a8057499eaa245940d6451c27a2c06d2a44089b62a778d645"},{"path":"/usr/lib64/gconv/ISO8859-10.so","mode":33261,"size":14912,"sha256":"0cb36b13c2b4f163adc1ad36f162dbe84602fe189392de73fab396d800edc7d5"},{"path":"/usr/lib64/gconv/ISO8859-11.so","mode":33261,"size":14912,"sha256":"c76084366d68599fe47082e1eabed21eab96d82fbe306c569800c6ed310ebcb7"},{"path":"/usr/lib64/gconv/ISO8859-13.so","mode":33261,"size":14912,"sha256":"40c98c8d8d16f8d10697e9b33d5150d44021d62849cc444051863ec9cbe702c2"},{"path":"/usr/lib64/gconv/ISO8859-14.so","mode":33261,"size":14912,"sha256":"8c7922de9c6d0d716714e81b593d50ba8e4f6e47542493f93488d07360266411"},{"path":"/usr/lib64/gconv/ISO8859-15.so","mode":33261,"size":14912,"sha256":"1439a70e526a0dcfd3a1f0c21eeb075cec52a5e3b01c9cef38e95acecf602556"},{"path":"/usr/lib64/gconv/ISO8859-16.so","mode":33261,"size":14912,"sha256":"34e805e68b804aa301efb6bddba4abb7abdc0d6edf1a335f8365bf827a23506c"},{"path":"/usr/lib64/gconv/ISO8859-2.so","mode":33261,"size":14864,"sha256":"e847aae449b8e03c6d9be3db9c35aa1f9a8e1d933a60d7b31bf16a01a930cf17"},{"path":"/usr/lib64/gconv/ISO8859-3.so","mode":33261,"size":14864,"sha256":"9131a8777f2c862a42f56a21e2667ff488d166a000bec4f33bf8625a602fa11d"},{"path":"/usr/lib64/gconv/ISO8859-4.so","mode":33261,"size":14864,"sha256":"e8d9cec46bbe2615bcd8702b7d62b3a4a678a6afbd852dca583a302843a23ce3"},{"path":"/usr/lib64/gconv/ISO8859-5.so","mode":33261,"size":14896,"sha256":"c1f536c6dc192e52097388b01473fb3464b607297310eee9f790eb861a3c3e99"},{"path":"/usr/lib64/gconv/ISO8859-6.so","mode":33261,"size":18960,"sha256":"c9e6d48ff93280cfbd10245714b405714de2eb3a150df86e38231b4c5e0f8a61"},{"path":"/usr/lib64/gconv/ISO8859-7.so","mode":33261,"size":14896,"sha256":"e929ec7282465bf692360f5e85393c56f0f00c0c0f0ce75e57af2107222e0a58"},{"path":"/usr/lib64/gconv/ISO8859-8.so","mode":33261,"size":14896,"sha256":"297df943cb33d0b2faa81228d0896375f41b4f70c4156f0f5205793ae21eb8e3"},{"path":"/usr/lib64/gconv/ISO8859-9.so","mode":33261,"size":14864,"sha256":"14be131847830c2050f1d47fd7f4504e12106e79864f3e1d5ac213d4cf6d54e8"},{"path":"/usr/lib64/gconv/ISO8859-9E.so","mode":33261,"size":14912,"sha256":"c7a8c400044dd0dc19e4f20aac02bc621ec51ee7e8c512d0437c0b0721d99990"},{"path":"/usr/lib64/gconv/ISO_10367-BOX.so","mode":33261,"size":14944,"sha256":"24e157f431e5658f1e565fb42bedb358000e36a715478dcc15e90d4210953908"},{"path":"/usr/lib64/gconv/ISO_11548-1.so","mode":33261,"size":14824,"sha256":"cf309f3a9ae9a84162f80a99419b5fd45bf5234a8f73808b368455aac5f50178"},{"path":"/usr/lib64/gconv/ISO_2033.so","mode":33261,"size":14880,"sha256":"cf8bd36721f631e43d230756342067681b2c30cf402bd31ecc10514c55cb6eb7"},{"path":"/usr/lib64/gconv/ISO_5427-EXT.so","mode":33261,"size":14936,"sha256":"38317e7460e0f8936aedadf1fc7cb258e49404bfdde874b0770521afc6d2e5b0"},{"path":"/usr/lib64/gconv/ISO_5427.so","mode":33261,"size":14880,"sha256":"57af157e3589ab8c669f5a7ad8d45039a1500de697e162eadec5677b2eea9ac6"},{"path":"/usr/lib64/gconv/ISO_5428.so","mode":33261,"size":14880,"sha256":"b838db82c0918474f6195cd5501f526ee1289fe39846e377d203267bf6d79233"},{"path":"/usr/lib64/gconv/ISO_6937-2.so","mode":33261,"size":27320,"sha256":"1b0619956ace1aeddb8b1e9becf4af013e0b0ba60ffe26b811469721dc38bedb"},{"path":"/usr/lib64/gconv/ISO_6937.so","mode":33261,"size":27280,"sha256":"cf5858eabc1cbb54f3112aaed72dff05b34908ecb04d41a2eb7885ecf84579c3"},{"path":"/usr/lib64/gconv/JOHAB.so","mode":33261,"size":23712,"sha256":"7b4d31e9567f464dda6ce4c9ea4c56cc8e52047a688bd75090e6f968f764c813"},{"path":"/usr/lib64/gconv/KOI-8.so","mode":33261,"size":14816,"sha256":"3e7d295774887ff76179589939c8007d679f7a30ac2d83733541a9edcdb98b83"},{"path":"/usr/lib64/gconv/KOI8-R.so","mode":33261,"size":14864,"sha256":"f2bdd4dcd407297f6ac55176aee7dc185cb42f65b68168ac9c7819efa5b00017"},{"path":"/usr/lib64/gconv/KOI8-RU.so","mode":33261,"size":14880,"sha256":"5d6ed2d99a1f34976b6cf3ddb0f714a921282466454456ecef13d36fa8d0962d"},{"path":"/usr/lib64/gconv/KOI8-T.so","mode":33261,"size":14864,"sha256":"1d5f46ba567949f615997199945a03751cfa248adc9463656b5d412156d05805"},{"path":"/usr/lib64/gconv/KOI8-U.so","mode":33261,"size":14864,"sha256":"3d39539bd9f3592fec025a73955db83ed7592ca093bb19f493b946c2d5e5dd3e"},{"path":"/usr/lib64/gconv/LATIN-GREEK-1.so","mode":33261,"size":14944,"sha256":"c951ce5ea4e214600d34c7ca3fc16834b8f7937a7923fd5e78f394e7796783e8"},{"path":"/usr/lib64/gconv/LATIN-GREEK.so","mode":33261,"size":14928,"sha256":"93b0ab7cfc0b255e21424318c129121544c162842f09d86835304ca457a777ca"},{"path":"/usr/lib64/gconv/MAC-CENTRALEUROPE.so","mode":33261,"size":14992,"sha256":"e3acbee7fc6d852278ed01e5eb0069e1a2a135b9e424488747a97be4183f1b59"},{"path":"/usr/lib64/gconv/MAC-IS.so","mode":33261,"size":14864,"sha256":"ff760c792ed306a3f5a163cb3c385a1c1944c17f2eef4e2bb4bf17f1a77a797e"},{"path":"/usr/lib64/gconv/MAC-SAMI.so","mode":33261,"size":14888,"sha256":"2ed77c4b39f93892ce5616f6269f88b8817b4cbb9106f43d9092e4c1a55c596a"},{"path":"/usr/lib64/gconv/MAC-UK.so","mode":33261,"size":14864,"sha256":"38bd2d1e2586391579d9eaab7cb5d3f910b68e0f933c02f10b05cef4cd207ee0"},{"path":"/usr/lib64/gconv/MACINTOSH.so","mode":33261,"size":14888,"sha256":"f6ab8fbd035e8bf3db4561c311c6453711d81263122d45e50d9ed2d3c949c0b5"},{"path":"/usr/lib64/gconv/MIK.so","mode":33261,"size":14824,"sha256":"e24420230086ca45d63f8bea95dea16c4793046074984d148ff199225a5ce316"},{"path":"/usr/lib64/gconv/NATS-DANO.so","mode":33261,"size":14896,"sha256":"0985d206a7bbbe9d82d89a610c4b310585d4ceb2e9cd5743c07cf192d8ddb0fe"},{"path":"/usr/lib64/gconv/NATS-SEFI.so","mode":33261,"size":14896,"sha256":"5f494799c38ae1c3442e996ee867d487b8d2794d65028c23f1f9dae34b5e6875"},{"path":"/usr/lib64/gconv/PT154.so","mode":33261,"size":14840,"sha256":"6025c68a21f4d4cc6c716b602e55a494a0d2138e2f7e70ea21630a2979a516de"},{"path":"/usr/lib64/gconv/RK1048.so","mode":33261,"size":14856,"sha256":"f2b2e2e592f8e512496153a236251e1bbcf4fc05ae9aa78853498ea82b3342ba"},{"path":"/usr/lib64/gconv/SAMI-WS2.so","mode":33261,"size":14888,"sha256":"69de72a14504065afb50ab0f3f8e2a86024248f82cba648103233065f326ffa2"},{"path":"/usr/lib64/gconv/SHIFT_JISX0213.so","mode":33261,"size":23424,"sha256":"1e893ac5044bf754be738d3812f5ec034e91c6293f4d1f59ccac948ae90192db"},{"path":"/usr/lib64/gconv/SJIS.so","mode":33261,"size":101096,"sha256":"1e7b53258a3722505d9f74fdd84fdab8f792a926b660f6cef8f5dade9f2dbb9d"},{"path":"/usr/lib64/gconv/T.61.so","mode":33261,"size":23144,"sha256":"43819e7dd61e74aa02ddf780fd8a64407387bdd1d0873593f5907811b88d4fb8"},{"path":"/usr/lib64/gconv/TCVN5712-1.so","mode":33261,"size":19192,"sha256":"7f405081d5834c5339d103658f972526cd9e545319c31dbef32fe080b4200e13"},{"path":"/usr/lib64/gconv/TIS-620.so","mode":33261,"size":14880,"sha256":"cbaa18587f9696be0ce81dbaeba8354ea5c6b2fbc920e4e54d2a865fe59215b7"},{"path":"/usr/lib64/gconv/TSCII.so","mode":33261,"size":27176,"sha256":"5fe8e384d123c3d2df2da13e865a010c71fa2e4d84f80da8bf5ae9d87c7a08d6"},{"path":"/usr/lib64/gconv/UHC.so","mode":33261,"size":76536,"sha256":"0cf8c8578e02f921576cf44d5ead7b1a57b358ce1ad19451c5a13d120bcd55ec"},{"path":"/usr/lib64/gconv/UNICODE.so","mode":33261,"size":14912,"sha256":"4392ad4e6cbf2e38828fe34685ec3e8bf0af8a2f9482f248018e99974bff57e7"},{"path":"/usr/lib64/gconv/UTF-16.so","mode":33261,"size":19064,"sha256":"5cfa8cccd6d862cb0cb72d5deb6f2d44e863ee05afbf70677d998db1a247c374"},{"path":"/usr/lib64/gconv/UTF-32.so","mode":33261,"size":14968,"sha256":"0e4e26bb4e9bfb50664ce2855ffc6c13565bbbf32129ae2e4feaf2d08f1dda8e"},{"path":"/usr/lib64/gconv/UTF-7.so","mode":33261,"size":23208,"sha256":"874f9a6e59a16a3d3d25059fbf0be9331ab6f6ac8a5a51b284477917bb2c93b6"},{"path":"/usr/lib64/gconv/VISCII.so","mode":33261,"size":14856,"sha256":"7bd97e0eb9979a1d0b821edec0df45632ab97b835c30ec4126a248eed8286d49"},{"path":"/usr/lib64/gconv/gconv-modules","mode":33188,"size":56427,"sha256":"dd4a05d445c5be37354e709b517882909184c9234507774b07e7f1071999c19f"},{"path":"/usr/lib64/gconv/gconv-modules.cache","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/lib64/gconv/libCNS.so","mode":33261,"size":474872,"sha256":"e79205caa307cf47632dd9c09768b6358a5d0fdf1b57e99a25fafba59444eeab"},{"path":"/usr/lib64/gconv/libGB.so","mode":33261,"size":71496,"sha256":"65fea10b228bebfc3b3aa5bae6357e688b2a7fd373a9fc9e08a901f835a86fcd"},{"path":"/usr/lib64/gconv/libISOIR165.so","mode":33261,"size":63024,"sha256":"0721bfec6c6f4f96acea3470531c93c66ce0d78d9e7d3b3d0e2514dac5975002"},{"path":"/usr/lib64/gconv/libJIS.so","mode":33261,"size":106496,"sha256":"1709ab5f3c91047f09fd4d04419dfadb20d293a20b75b88655a9aab1d15f3f06"},{"path":"/usr/lib64/gconv/libJISX0213.so","mode":33261,"size":124552,"sha256":"44c109ca6fc8f95bca57e77d772a377e30475ec673ef7bb6aab6ddc27427cbcf"},{"path":"/usr/lib64/gconv/libKSC.so","mode":33261,"size":50792,"sha256":"1733d70fac07cf4b61af477e82953c636ada9230268d33ffbb21c852997c65ba"},{"path":"/usr/lib64/libmemusage.so","mode":33261,"size":27392,"sha256":"87e59da8f926382c3344b1ed01d64b5749e43ef62a0754bfc35055430124e78d"},{"path":"/usr/lib64/libpcprofile.so","mode":33261,"size":11312,"sha256":"1aff9b756f1cf1a6434522bcc29e65a468780539aa6fe1c510ccac7809c18e60"},{"path":"/usr/libexec/getconf/POSIX_V6_LP64_OFF64","mode":33261,"size":39064,"sha256":"f741546280799a01bbeed9ab35b1676196aac890e563e4800658ad180f629506"},{"path":"/usr/libexec/getconf/POSIX_V7_LP64_OFF64","mode":33261,"size":39064,"sha256":"f741546280799a01bbeed9ab35b1676196aac890e563e4800658ad180f629506"},{"path":"/usr/libexec/getconf/XBS5_LP64_OFF64","mode":33261,"size":39064,"sha256":"f741546280799a01bbeed9ab35b1676196aac890e563e4800658ad180f629506"},{"path":"/usr/sbin/iconvconfig","mode":33261,"size":49760,"sha256":"f1f50c533b5cefd30b9ecc7469be99f936bf1b2d760160918e269ebb175f23c0"},{"path":"/usr/share/licenses/glibc/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/glibc/COPYING.LIB","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"},{"path":"/usr/share/licenses/glibc/LICENSES","mode":33188,"size":18941,"sha256":"35bdb41dc0bcb10702ddacbd51ec4c0fe6fb3129f734e8c85fc02e4d3eb0ce3f"},{"path":"/var/cache/ldconfig/aux-cache","mode":33152,"size":0,"sha256":""}]}},{"name":"glibc-common","version":"2.28-101.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:glibc-common:glibc-common:2.28-101.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:glibc-common:2.28-101.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/glibc-common@0:2.28-101.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"glibc-common","version":"2.28","epoch":0,"architecture":"x86_64","release":"101.el8","sourceRpm":"glibc-2.28-101.el8.src.rpm","size":9531204,"license":"LGPLv2+ and LGPLv2+ with exceptions and GPLv2+ and GPLv2+ with exceptions and BSD and Inner-Net and ISC and Public Domain and GFDL","vendor":"CentOS","files":[{"path":"/usr/bin/catchsegv","mode":33261,"size":3283,"sha256":"8e59795b8077c647749fc60ebc5aca6489008f5fad216fe698d52a2e607e9c72"},{"path":"/usr/bin/gencat","mode":33261,"size":35544,"sha256":"202e090b901014acc838771601ff1e511e2ef908b66c8c86a736c19c08156563"},{"path":"/usr/bin/getconf","mode":33261,"size":39064,"sha256":"f741546280799a01bbeed9ab35b1676196aac890e563e4800658ad180f629506"},{"path":"/usr/bin/getent","mode":33261,"size":49416,"sha256":"cbc6c4fed573f3af88b8f6d619b4057bd505399d240eddae37bc70d92611f00e"},{"path":"/usr/bin/iconv","mode":33261,"size":94856,"sha256":"edbbbbd70c9a44776687d99ce60b6b2e626de6c9c558738a10869123601e5ef5"},{"path":"/usr/bin/ldd","mode":33261,"size":5441,"sha256":"8db39aa6d8727f788f0c4ffcd882a64068f0362bea9ffe38de828f2c5583a705"},{"path":"/usr/bin/locale","mode":33261,"size":78000,"sha256":"5dc52d9cf1456d4f27eb5567009e13e48597863ecb4d5cabe33aa7c3ce0eb518"},{"path":"/usr/bin/localedef","mode":33261,"size":390760,"sha256":"b20cb7108cbd9e202dbf0645600d2d22f79a765c193479ca7b2660aa2f8cb702"},{"path":"/usr/bin/makedb","mode":33261,"size":38016,"sha256":"1d70920dee0aa80d430b88644c6031a37e7cf7184b001ed228d2faa210979d4a"},{"path":"/usr/bin/pldd","mode":33261,"size":25768,"sha256":"55bb4f3afde6bd43de35b7f4160cb552cc2a0c0b6c2ac84ceffe9facffb29d4a"},{"path":"/usr/bin/sotruss","mode":33261,"size":4281,"sha256":"af68e860ba180298f5245e09addd18cf9362c39ef7bb53e1b8bd4110f6ee8947"},{"path":"/usr/bin/sprof","mode":33261,"size":38968,"sha256":"55704f724a793b392a41e4131ac5ad0b4d068200ad9e0eb02f25dce39b572588"},{"path":"/usr/bin/tzselect","mode":33261,"size":15370,"sha256":"830199fe1d50c1a4d82b38673c0567dcde097fed14efa3888ba98bcdcef66fe6"},{"path":"/usr/lib/.build-id/18/b4db17c49a137709ca83d50ad00b0a76d2471f","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/2f/79c16a414bfedb7b74522d49b0a07765891be0","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/40/87e607d566b9ebaa2c46ac5a0ee85318e16716","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/57/d4d38334b8d2d1e1c18855978127dde2c1ea29","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/69/3e1bd175105296e5e2902b78fa7b42e62e2547","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/8d/6bc3554303e8fee7ed9b4e3c5c1ed8f8b2286e","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/9e/aeab7b1319210577777d81876b97893a41369e","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/a2/4056c1aacab900521bd2996e7756fdcad7821b","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/be/03772bab41f1304287660390b0922f72b2b0b8","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/c1/8fc6aacee96ef38d4053965effa7ab236e752a","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/c1/c5abbce0a7da6019229f7dc9726a495149b1a5","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/d5/f90de11e2695a8e4f641b443471399e8d614f5.3","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/locale/C.utf8/LC_ADDRESS","mode":33188,"size":131,"sha256":"e56fdac7f4d70bdb7517a9a3c98bbfefef52fcfb082d3a49c26eec93fd8f9d9d"},{"path":"/usr/lib/locale/C.utf8/LC_COLLATE","mode":33188,"size":6949250,"sha256":"7ac04f3f6e159488d62861b22cb7bf4e5c83a51d2961dcfcd103a6723cefb051"},{"path":"/usr/lib/locale/C.utf8/LC_CTYPE","mode":33188,"size":337024,"sha256":"8d1401ee710ca9f0e123e38dff897dd26138cb118960c8239bfe76baaa4c25a1"},{"path":"/usr/lib/locale/C.utf8/LC_IDENTIFICATION","mode":33188,"size":252,"sha256":"4d7144ea8176f0291754f5287bb06f3ab11803e0c178e84741fdc935c4b73f0a"},{"path":"/usr/lib/locale/C.utf8/LC_MEASUREMENT","mode":33188,"size":23,"sha256":"bb14a6f2cbd5092a755e8f272079822d3e842620dd4542a8dfa1e5e72fc6115b"},{"path":"/usr/lib/locale/C.utf8/LC_MESSAGES/SYS_LC_MESSAGES","mode":33188,"size":53,"sha256":"94b0b5b9478be3d07699972940961cdfa6c7fd86e4d4601b11a6be2268e4dbad"},{"path":"/usr/lib/locale/C.utf8/LC_MONETARY","mode":33188,"size":282,"sha256":"5b4d493a4960092900dea714839a694a9aa3f445a0f03b50c9bc16a788e6eeff"},{"path":"/usr/lib/locale/C.utf8/LC_NAME","mode":33188,"size":62,"sha256":"14507aad9f806112e464b9ca94c93b2e4d759ddc612b5f87922d7cac7170697d"},{"path":"/usr/lib/locale/C.utf8/LC_NUMERIC","mode":33188,"size":50,"sha256":"f5976e6b3e6b24dfe03caad6a5b98d894d8110d8bd15507e690fd60fd3e04ab2"},{"path":"/usr/lib/locale/C.utf8/LC_PAPER","mode":33188,"size":34,"sha256":"cde048b81e2a026517cc707c906aebbd50f5ee3957b6f0c1c04699dffcb7c015"},{"path":"/usr/lib/locale/C.utf8/LC_TELEPHONE","mode":33188,"size":47,"sha256":"f4caf0d12844219b65ba42edc7ec2f5ac1b2fc36a3c88c28887457275daca1ee"},{"path":"/usr/lib/locale/C.utf8/LC_TIME","mode":33188,"size":3360,"sha256":"5bcce4e0710a2e0ad24b195bf65073d3d9fee0d011b40bd080d2e033f69272d5"},{"path":"/usr/sbin/build-locale-archive","mode":33216,"size":1316968,"sha256":"68443b123f8ed90f3e68d6b4c0437d8397b269da2d4ac5fbac4017f3ab916a20"},{"path":"/usr/sbin/zdump","mode":33261,"size":29648,"sha256":"d9750c936c02b6669767e9b44d2d911edf2a6e174bb6a4e3bf4687ef91a7eac8"},{"path":"/usr/sbin/zic","mode":33261,"size":68912,"sha256":"d89fb14cacf3e56ad0beab93ebdb670e0b8ad124f682775e221248b50dbfcb5e"},{"path":"/usr/share/locale/locale.alias","mode":33188,"size":2997,"sha256":"ef71c6302d6d2254d52588f2a076e6224117a024a1494e3b78be469cfe708e05"}]}},{"name":"glibc-minimal-langpack","version":"2.28-101.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:glibc-minimal-langpack:glibc-minimal-langpack:2.28-101.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:glibc-minimal-langpack:2.28-101.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/glibc-minimal-langpack@0:2.28-101.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"glibc-minimal-langpack","version":"2.28","epoch":0,"architecture":"x86_64","release":"101.el8","sourceRpm":"glibc-2.28-101.el8.src.rpm","size":0,"license":"LGPLv2+ and LGPLv2+ with exceptions and GPLv2+ and GPLv2+ with exceptions and BSD and Inner-Net and ISC and Public Domain and GFDL","vendor":"CentOS","files":[]}},{"name":"gmp","version":"6.1.2-10.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:gmp:gmp:6.1.2-10.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:gmp:6.1.2-10.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/gmp@1:6.1.2-10.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"gmp","version":"6.1.2","epoch":1,"architecture":"x86_64","release":"10.el8","sourceRpm":"gmp-6.1.2-10.el8.src.rpm","size":1678740,"license":"LGPLv3+ or GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/a8/04dab0a63ed12490219bd81b82618a92a1bbac","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/fipscheck/libgmp.so.10.3.2.hmac","mode":33188,"size":65,"sha256":"2b1f64e61e5af450f7806e3b3a379ddb89522f7dcc393e71dcdb97d3a767e871"},{"path":"/usr/lib64/fipscheck/libgmp.so.10.hmac","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libgmp.so.10","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libgmp.so.10.3.2","mode":33261,"size":1541856,"sha256":"7e17c3657e98cc6cc63be5d010808ba6ec250f6816ef47bde5fc3d3bb19d5b35"},{"path":"/usr/share/licenses/gmp/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/gmp/COPYING.LESSERv3","mode":33188,"size":7639,"sha256":"a853c2ffec17057872340eee242ae4d96cbf2b520ae27d903e1b2fef1a5f9d1c"},{"path":"/usr/share/licenses/gmp/COPYINGv2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/gmp/COPYINGv3","mode":33188,"size":35150,"sha256":"e6037104443f9a7829b2aa7c5370d0789a7bda3ca65a0b904cdc0c2e285d9195"}]}},{"name":"gnupg2","version":"2.2.9-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:gnupg2:gnupg2:2.2.9-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:gnupg2:2.2.9-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/gnupg2@0:2.2.9-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"gnupg2","version":"2.2.9","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"gnupg2-2.2.9-1.el8.src.rpm","size":9632671,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/dirmngr","mode":33261,"size":607040,"sha256":"1bd5cf3951930cecb8c155d859343ed2cfdf6da9e5bc585859031862002e1a13"},{"path":"/usr/bin/dirmngr-client","mode":33261,"size":126976,"sha256":"85c23fe4c1b6f762bbeaaddd4862667fcfa5ffc0e25eb32e3481933e5f2a3b06"},{"path":"/usr/bin/g13","mode":33261,"size":234872,"sha256":"f676a0e7a013de6748c7788e7abc08335a3a0463ed25d4d1a7c48d20f7ac8a50"},{"path":"/usr/bin/gpg","mode":33261,"size":1114968,"sha256":"3e3bdae619253ba6df0bcf60e3e18c94add7fd39068540ee9e57d46505e5cc25"},{"path":"/usr/bin/gpg-agent","mode":33261,"size":442016,"sha256":"13d9638fcf3eb60bc985403bc5872d45d1e583e14942babd8e513147ded4d6b8"},{"path":"/usr/bin/gpg-connect-agent","mode":33261,"size":179480,"sha256":"87cc29d2530b869e69519d26f08e1858021ca93a6249b5b8b9caaa1c4f412def"},{"path":"/usr/bin/gpg-zip","mode":33261,"size":3447,"sha256":"cae8a1d471cfe3b2242793d3a3e9df19588004fb7783d65dd88a24fda12d5eaa"},{"path":"/usr/bin/gpg2","mode":41471,"size":3,"sha256":""},{"path":"/usr/bin/gpgconf","mode":33261,"size":184080,"sha256":"e3a5ff458a90f339fc9889fc1d69da506b284c01b9cfe90a216fcc780d18519a"},{"path":"/usr/bin/gpgparsemail","mode":33261,"size":30472,"sha256":"87b41c9801c31d693f497b88eed1e7e23f351cb1eab310afb1d2d692ccc436a6"},{"path":"/usr/bin/gpgsplit","mode":33261,"size":94704,"sha256":"7a924eff8a16724fdeb2c8a9e2406e968323e54e2ce2cf5ef1ea2e120d69c925"},{"path":"/usr/bin/gpgv","mode":33261,"size":484056,"sha256":"13e194c4cebc77bc30e9533afa869f7f48db903deb5cb6f99b6712404c50ecae"},{"path":"/usr/bin/gpgv2","mode":41471,"size":4,"sha256":""},{"path":"/usr/bin/watchgnupg","mode":33261,"size":17536,"sha256":"e75018b7b6d6bef9b208ed476ef32ca8dad532a6ca891cfbe9eabc3a584a8d7f"},{"path":"/usr/lib/.build-id/0d/cce787362f98afb15dc69a87040e8ac010922b","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/15/0321bdde56a332cc4e8d1d9f34f560c191566f","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/3c/50ca814e6d3dc5a0e8933f44d1e7177d50b148","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/3c/f235c89b1f98864f56bc884664c07c96f28d91","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/55/538d9cd90672cac192cca035e6e7eb3492328e","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/60/680e6a200c23f079ae7d74a9bfaefac44de920","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/61/721183b40da0cfe360f59e6e22e217e002c4e0","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/6e/46ace9f8780610d3e0cf9599a10a743bacb0d8","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/77/b95c1b0b214ffda651593f763338b7ae751cdf","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/87/2b7832cb37a60cda7b6a4de6e272d2089d3fa1","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/91/2e2b6a774d9d960e5762b6cf98cc2dcf0d3d85","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/a3/f6809917d319f07832e5bf4a099a4a758f2936","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/dc/e10e2f63e628e0588ce9436d40f898e1b62238","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/df/cac4229acc6131bae7e38d45d590800643275e","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/e9/8ffe497c531dcdb9978e2da585d2c6b8cb14a0","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/ec/82fea42b8eaa0f15a6c69b6a5a2c0259f378ef","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/f4/e821bc38478f157a4a245eda1e99e387e8995d","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/f8/7c660946f628bdba6b36bbce189d40c22d0032","mode":41471,"size":32,"sha256":""},{"path":"/usr/libexec/dirmngr_ldap","mode":33261,"size":95424,"sha256":"df500ac5cd5c8c12eb9130e70e4df772e2679bfcdd118b06b6fa7d8e70835bf6"},{"path":"/usr/libexec/gpg-check-pattern","mode":33261,"size":121432,"sha256":"285a9620713bc4057ef796966042ecfe4a968e6ea1a1aaabbb625bb23fafe6c3"},{"path":"/usr/libexec/gpg-preset-passphrase","mode":33261,"size":96144,"sha256":"12689a9db25f24cafeb96536cdec1709f616b856018611065deb0fbd0fb86a76"},{"path":"/usr/libexec/gpg-protect-tool","mode":33261,"size":215216,"sha256":"b9c3566fb2d7160b0b32dd8d889a63eb87d4707fd9d1bfd4cb10b3dc9408ae92"},{"path":"/usr/libexec/gpg-wks-client","mode":33261,"size":236152,"sha256":"fdc6998523d0e1ebb2d0909b1ee870ae9e217066e23c1954f3b382e9338cfe7c"},{"path":"/usr/libexec/scdaemon","mode":33261,"size":462832,"sha256":"1eab99056c35c5bfdf26af889b3eb8bb92e7cd5fcae17d4e0f03e895cabccbb6"},{"path":"/usr/sbin/addgnupghome","mode":33261,"size":3078,"sha256":"950f180008a1e62a16f8ceda0f6e3e9d7ed4489bffb1bf436dfdd497e3a91c0c"},{"path":"/usr/sbin/applygnupgdefaults","mode":33261,"size":2217,"sha256":"fd3dd5e998504628720e5047af75f2af198f016bc75ee5f8f6eabd735972cfe2"},{"path":"/usr/sbin/g13-syshelp","mode":33261,"size":207856,"sha256":"2ca17650a91fae0d6bdf8dc95009b9b76b36a3bf48122ce31b57598df540f305"},{"path":"/usr/share/gnupg/distsigkey.gpg","mode":33188,"size":3267,"sha256":"8948f10369646847016a5f49035cc14c106572e218800de588338564e9a669e3"},{"path":"/usr/share/gnupg/help.be.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.ca.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.cs.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.da.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.de.txt","mode":33188,"size":9013,"sha256":"bf3782730db603ef4bddba546330d7d69b211c22213adc6d3791e2a8802f35fe"},{"path":"/usr/share/gnupg/help.el.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.eo.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.es.txt","mode":33188,"size":7632,"sha256":"db9a70fce6bed52532b856323f4d4a6a47b7def90f83d145e5757c2ebf2c36ad"},{"path":"/usr/share/gnupg/help.et.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.fi.txt","mode":33188,"size":7744,"sha256":"8d89ec6367705a10152ba4f82a0e623851beeb031d097dd47e731f692bc03574"},{"path":"/usr/share/gnupg/help.fr.txt","mode":33188,"size":7797,"sha256":"abad0bbc97849bf71917ca59f579db0a7caea436f523ab592294b4ce80826c4b"},{"path":"/usr/share/gnupg/help.gl.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.hu.txt","mode":33188,"size":8205,"sha256":"3eeea50fdd123a14d07b0df485cf390facfc1954b0ea82c8ae0d2c175393dff9"},{"path":"/usr/share/gnupg/help.id.txt","mode":33188,"size":7535,"sha256":"d8b7ecd6463697591c771a71aaccdc3daac5c90325990fd491b2967396287895"},{"path":"/usr/share/gnupg/help.it.txt","mode":33188,"size":7691,"sha256":"d75e4557580c0f681a5507ac7b3c0e64365f8ce6d5b37dc6221964631ac69c8a"},{"path":"/usr/share/gnupg/help.ja.txt","mode":33188,"size":13621,"sha256":"563af5e649fbe9eddc91461543dce1a2376c019afb2a8f78fc7e7d3e6e3b0453"},{"path":"/usr/share/gnupg/help.nb.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.pl.txt","mode":33188,"size":7535,"sha256":"1c44b176a46cc16b4fbd200b42c6f9d93c054fec1ec9bb3750b3e44e0d464ef5"},{"path":"/usr/share/gnupg/help.pt.txt","mode":33188,"size":7873,"sha256":"cbc2f41b6550d1c933158caac917a3fb8b967c0a6cd10af534ad31c3b0a4f87c"},{"path":"/usr/share/gnupg/help.pt_BR.txt","mode":33188,"size":7876,"sha256":"2f941a1b6e5b5172fddc4ac62a112cb3d7981dbcbcc5de3f706084210e35d265"},{"path":"/usr/share/gnupg/help.ro.txt","mode":33188,"size":8112,"sha256":"9a2898d1358e4faef974ceb3c515b214fb63e1e30c9fc75d18b4dec1e6fb1350"},{"path":"/usr/share/gnupg/help.ru.txt","mode":33188,"size":17735,"sha256":"6fba5ee88300f8599c18bacb0b5bbf6518c16c03b536e8ee12b832fe7bc72686"},{"path":"/usr/share/gnupg/help.sk.txt","mode":33188,"size":8085,"sha256":"bb6d9916028dd5a14e6ef45d5724ceac4906b1ed5275b6d49e9460006435afbc"},{"path":"/usr/share/gnupg/help.sv.txt","mode":33188,"size":9741,"sha256":"05cdf5a33891882a1b96e007c0ac8dc9f99592f3667f79d83904a38e38e8bbe2"},{"path":"/usr/share/gnupg/help.tr.txt","mode":33188,"size":7651,"sha256":"9c51e8863bee4699fff0bce77ff5aad420daee802b30d92633705f509a933502"},{"path":"/usr/share/gnupg/help.txt","mode":33188,"size":13052,"sha256":"a83cde33912331f7d68cd1074997e95ce3c57c27185424cdb84d98d460a9e2dc"},{"path":"/usr/share/gnupg/help.zh_CN.txt","mode":33188,"size":7071,"sha256":"7bc19422e1c5031a034042ea6e6b8d5ec81857ff9ee4605e505a40105227f90e"},{"path":"/usr/share/gnupg/help.zh_TW.txt","mode":33188,"size":7102,"sha256":"1b745d2293bdfa5154ce1278236ac258f442caee7d328317c7e475880c261edb"},{"path":"/usr/share/gnupg/sks-keyservers.netCA.pem","mode":33188,"size":1984,"sha256":"0666ee848e03a48f3ea7bb008dbe9d63dfde280af82fb4412a04bf4e24cab36b"},{"path":"/usr/share/licenses/gnupg2/COPYING","mode":33188,"size":35069,"sha256":"bc2d6664f6276fa0a72d57633b3ae68dc7dcb677b71018bf08c8e93e509f1357"}]}},{"name":"gnutls","version":"3.6.8-10.el8_2","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:gnutls:gnutls:3.6.8-10.el8_2:*:*:*:*:*:*:*","cpe:2.3:a:*:gnutls:3.6.8-10.el8_2:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/gnutls@0:3.6.8-10.el8_2?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"gnutls","version":"3.6.8","epoch":0,"architecture":"x86_64","release":"10.el8_2","sourceRpm":"gnutls-3.6.8-10.el8_2.src.rpm","size":2687449,"license":"GPLv3+ and LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/30/28de1d994d480dddb52d168eeb6e1444055ef3","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib64/.libgnutls.so.30.24.0.hmac","mode":33188,"size":65,"sha256":"e51b37ec20d31ebeff7b17e0bcbf8b5cfc687c33712e79a8e6cc585526fc0413"},{"path":"/usr/lib64/.libgnutls.so.30.hmac","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib64/libgnutls.so.30","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib64/libgnutls.so.30.24.0","mode":33261,"size":1834040,"sha256":"85dd9ee6a43be30bd925566a0e4e5d5f0bc4524248211944a539862b7ffe9a6c"},{"path":"/usr/share/licenses/gnutls/COPYING","mode":33188,"size":35151,"sha256":"e79e9c8a0c85d735ff98185918ec94ed7d175efc377012787aebcf3b80f0d90b"},{"path":"/usr/share/licenses/gnutls/COPYING.LESSER","mode":33188,"size":26432,"sha256":"6095e9ffa777dd22839f7801aa845b31c9ed07f3d6bf8a26dc5d2dec8ccc0ef3"},{"path":"/usr/share/licenses/gnutls/LICENSE","mode":33188,"size":936,"sha256":"3e043d77917e48e262301b8f880812fcd82236482630a421d555a38804eee643"}]}},{"name":"gpg","version":"1.10.0","type":"python","foundBy":"python-package-cataloger","locations":[{"path":"/usr/lib64/python3.6/site-packages/gpg-1.10.0-py3.6.egg-info","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":["LGPL2.1+ (the library), GPL2+ (tests and examples)"],"language":"python","cpes":["cpe:2.3:a:gpg:gpg:1.10.0:*:*:*:*:python:*:*","cpe:2.3:a:python-gpg:gpg:1.10.0:*:*:*:*:python:*:*","cpe:2.3:a:*:gpg:1.10.0:*:*:*:*:python:*:*","cpe:2.3:a:gpg:gpg:1.10.0:*:*:*:*:*:*:*","cpe:2.3:a:python-gpg:gpg:1.10.0:*:*:*:*:*:*:*","cpe:2.3:a:*:gpg:1.10.0:*:*:*:*:*:*:*"],"purl":"pkg:pypi/gpg@1.10.0","metadataType":"PythonPackageMetadata","metadata":{"name":"gpg","version":"1.10.0","license":"LGPL2.1+ (the library), GPL2+ (tests and examples)","author":"The GnuPG hackers","authorEmail":"gnupg-devel@gnupg.org","platform":"UNKNOWN","sitePackagesRootPath":"/usr/lib64/python3.6"}},{"name":"gpgme","version":"1.10.0-6.el8.0.1","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:gpgme:gpgme:1.10.0-6.el8.0.1:*:*:*:*:*:*:*","cpe:2.3:a:*:gpgme:1.10.0-6.el8.0.1:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/gpgme@0:1.10.0-6.el8.0.1?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"gpgme","version":"1.10.0","epoch":0,"architecture":"x86_64","release":"6.el8.0.1","sourceRpm":"gpgme-1.10.0-6.el8.0.1.src.rpm","size":741097,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/e9/a48cb7461e8bad07481ce617d49cbe204e819b","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libgpgme.so.11","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libgpgme.so.11.19.0","mode":33261,"size":331648,"sha256":"7150ea7cb9b3d988ddd5dbbcc9459c24e16270df30b10696dc7726f7f4101621"},{"path":"/usr/share/licenses/gpgme/COPYING","mode":33188,"size":17992,"sha256":"32b1062f7da84967e7019d01ab805935caa7ab7321a7ced0e30ebe75e5df1670"},{"path":"/usr/share/licenses/gpgme/COPYING.LESSER","mode":33188,"size":26536,"sha256":"ca0061fc1381a3ab242310e4b3f56389f28e3d460eb2fd822ed7a21c6f030532"}]}},{"name":"grep","version":"3.1-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:grep:grep:3.1-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:grep:3.1-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/grep@0:3.1-6.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"grep","version":"3.1","epoch":0,"architecture":"x86_64","release":"6.el8","sourceRpm":"grep-3.1-6.el8.src.rpm","size":835205,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/etc/GREP_COLORS","mode":33188,"size":94,"sha256":"e94e50735e137e769b40e230f019d5be755571129e0f7669c4570bb45c5c162e"},{"path":"/etc/profile.d/colorgrep.csh","mode":33188,"size":196,"sha256":"74d270fe4476fdcba60df7d00c808e11681ac918f335c951cba4f118532a4b8c"},{"path":"/etc/profile.d/colorgrep.sh","mode":33188,"size":201,"sha256":"89008d115c5bbd783b985d8cab18e935978c83e362043ffc981063ffed74e1c7"},{"path":"/usr/bin/egrep","mode":33261,"size":28,"sha256":"f7c621ae0ceb26a76802743830bc469288996f64342901ae5292950ff713e981"},{"path":"/usr/bin/fgrep","mode":33261,"size":28,"sha256":"5c8b1486de899cdd010d3cacde94579999cb82d0be9ec8c131b1b56886cfd36b"},{"path":"/usr/bin/grep","mode":33261,"size":198280,"sha256":"b99c0a18e353d125de71fc7626d4835d7c92cd8f9d804b75272c5bb95997342a"},{"path":"/usr/lib/.build-id/b9/87fcca282a2f74af37adcf643ed4fd074be51c","mode":41471,"size":24,"sha256":""},{"path":"/usr/libexec/grepconf.sh","mode":33261,"size":253,"sha256":"8940897293b3261b51af2783be99e4861dc060989b249eb1c0ad2bf7a717a2a5"},{"path":"/usr/share/licenses/grep/COPYING","mode":33188,"size":35148,"sha256":"ca372a7d92560b1fa9f6d832b440e8bcd62d9adfa8870c98287deab66d98310e"}]}},{"name":"gzip","version":"1.9-9.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:gzip:gzip:1.9-9.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:gzip:1.9-9.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/gzip@0:1.9-9.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"gzip","version":"1.9","epoch":0,"architecture":"x86_64","release":"9.el8","sourceRpm":"gzip-1.9-9.el8.src.rpm","size":426515,"license":"GPLv3+ and GFDL","vendor":"CentOS","files":[{"path":"/etc/profile.d/colorzgrep.csh","mode":33188,"size":216,"sha256":"61da8a541c165502ac1258589686fd072a3f08e50838c45616e4d014fa9153ba"},{"path":"/etc/profile.d/colorzgrep.sh","mode":33188,"size":220,"sha256":"873ff1677c3430a2d90fa6257ddd5b511cc480cf7098b1cfbb246b5af9044a82"},{"path":"/usr/bin/gunzip","mode":33261,"size":2345,"sha256":"0011d06d8822b2097140be7ef6bbfaf0e01b9519a179644c6593a56f2bf5f903"},{"path":"/usr/bin/gzexe","mode":33261,"size":6375,"sha256":"99bf533f0fbc345e4885d525e26ee732a001255ae47167268e7ea482f4d6af5c"},{"path":"/usr/bin/gzip","mode":33261,"size":170544,"sha256":"424fb3892facae3687694009a2f0d268ab71bb98f997b912e0a1951c71b17930"},{"path":"/usr/bin/zcat","mode":33261,"size":1983,"sha256":"4cdce728b8d9c53e855853a2414b7d93251f632cc7bc34bcf0bf688f2da74ecf"},{"path":"/usr/bin/zcmp","mode":33261,"size":1677,"sha256":"dbfb20b6ae482c2f7f8365e3fe71f42266ef2c56e77f0787ad2f094083550a36"},{"path":"/usr/bin/zdiff","mode":33261,"size":5879,"sha256":"1bf1cef165c5265317d9bba07a58a28899fffe331ffa52a87d483e482d539296"},{"path":"/usr/bin/zegrep","mode":33261,"size":29,"sha256":"67ee7fadec7ea53b4c1f8cfc3c81427b29c0b1381e80b55642617620c84d0bcc"},{"path":"/usr/bin/zfgrep","mode":33261,"size":29,"sha256":"87ab5f4c7cb344e409d614d1a69cc156b3b1053d6ae0b59d8e2c2131f3e63e5a"},{"path":"/usr/bin/zforce","mode":33261,"size":2080,"sha256":"136b8f154b0c63d346af66498254e3aec25731d0897f80081d9e8819ff79da31"},{"path":"/usr/bin/zgrep","mode":33261,"size":7591,"sha256":"1e187b48e5a29009b682be0dc73e651000e801bf5f168cfee6b0a132e02c3611"},{"path":"/usr/bin/zless","mode":33261,"size":2205,"sha256":"d877394651502655a165962d79514bd67e3193f935aeacfea0baa22864739c75"},{"path":"/usr/bin/zmore","mode":33261,"size":1841,"sha256":"c1700b78ebb87a4806ca6e249abc66ffb18d89913349781b771cf39b9cf09aab"},{"path":"/usr/bin/znew","mode":33261,"size":4552,"sha256":"60cbb9f5388ebadd7dae2c9d9d061ef999818b18e324bdca9315ecea2771e1ac"},{"path":"/usr/lib/.build-id/d1/3c5d680c050adc9f780b5b5b0dc305c55cd098","mode":41471,"size":24,"sha256":""},{"path":"/usr/share/licenses/gzip/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/gzip/fdl-1.3.txt","mode":33188,"size":22962,"sha256":"4748f03ed2dbcc14cde6ebc30799899c403e356a7465dc30fcf2b80c45fc0059"}]}},{"name":"hostname","version":"3.20-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:hostname:hostname:3.20-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:hostname:3.20-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/hostname@0:3.20-6.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"hostname","version":"3.20","epoch":0,"architecture":"x86_64","release":"6.el8","sourceRpm":"hostname-3.20-6.el8.src.rpm","size":43979,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/dnsdomainname","mode":41471,"size":8,"sha256":""},{"path":"/usr/bin/domainname","mode":41471,"size":8,"sha256":""},{"path":"/usr/bin/hostname","mode":33261,"size":21664,"sha256":"26532eeae676157e70231d911474e48d31085b5f2e511ce908349dbb02f0f69c"},{"path":"/usr/bin/nisdomainname","mode":41471,"size":8,"sha256":""},{"path":"/usr/bin/ypdomainname","mode":41471,"size":8,"sha256":""},{"path":"/usr/lib/.build-id/a8/a7ee9d5002492edfc62e3e2e44149e981f9866","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/systemd/system/nis-domainname.service","mode":33188,"size":378,"sha256":"571aea8d633c0a9a08a453a387768cfa7e819c52a0cf6302036c0cc8711907ee"},{"path":"/usr/libexec/hostname/nis-domainname","mode":33261,"size":166,"sha256":"e34871863f59e9f0eee4674217d11d4ae46fe20b6496170787f0e45170997a4a"},{"path":"/usr/share/licenses/hostname/gpl-2.0.txt","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"ima-evm-utils","version":"1.1-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:ima-evm-utils:ima-evm-utils:1.1-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:ima-evm-utils:1.1-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/ima-evm-utils@0:1.1-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"ima-evm-utils","version":"1.1","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"ima-evm-utils-1.1-5.el8.src.rpm","size":123538,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/usr/bin/evmctl","mode":33261,"size":52224,"sha256":"1b420df1fca420ad83c9defef2e351c0bc61f8e3d2b6ba5a469e528f16a9e5bd"},{"path":"/usr/lib/.build-id/18/f4a9dca4c5233be259afb9b6ef481d5cecf3a5","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/6e/fce98266ddf2c06d7805a433d5eb90f53eab98","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib64/libimaevm.so.0","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libimaevm.so.0.0.0","mode":33261,"size":31512,"sha256":"7164ed3d512b639e0cbeb70a512fc9122fb06d4aa63cc9d123b492772889987d"},{"path":"/usr/share/licenses/ima-evm-utils/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"info","version":"6.5-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:info:info:6.5-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:info:6.5-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/info@0:6.5-6.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"info","version":"6.5","epoch":0,"architecture":"x86_64","release":"6.el8","sourceRpm":"texinfo-6.5-6.el8.src.rpm","size":386513,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/info","mode":33261,"size":255920,"sha256":"107314e28551bd60df3f7e5c44f71bdb2c15503a6123c7ee6e61aca1922a6ec0"},{"path":"/usr/lib/.build-id/4a/3b988936c3bcd9d20936e314d479123b3e7c1f","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/90/e70b4e00d05b911fe4d53fcb63b7325e5ab342","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/rpm/macros.d/macros.info","mode":33188,"size":390,"sha256":"7e1a04691c1409a0ab699a2362eeb2dc1124570dbb65453acd8c30a3bcf06be8"},{"path":"/usr/sbin/fix-info-dir","mode":33261,"size":7976,"sha256":"db24f2f10b71b03f498f7da204d26b2695abdfa275142ed3fe6ad6c96c1a2c80"},{"path":"/usr/share/info/dir","mode":33188,"size":1426,"sha256":""},{"path":"/usr/share/info/dir.old","mode":33188,"size":0,"sha256":""},{"path":"/usr/share/licenses/info/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"}]}},{"name":"ipcalc","version":"0.2.4-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:ipcalc:ipcalc:0.2.4-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:ipcalc:0.2.4-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/ipcalc@0:0.2.4-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"ipcalc","version":"0.2.4","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"ipcalc-0.2.4-4.el8.src.rpm","size":67705,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/ipcalc","mode":33261,"size":45560,"sha256":"b1d7e7eb1ad306fe02a1009893b8769bc6cc2d096aa01f61e84b176f257bca9e"},{"path":"/usr/lib/.build-id/c0/be6f3d4ebd6a80c26fce2936e576b7e48f2203","mode":41471,"size":26,"sha256":""},{"path":"/usr/share/licenses/ipcalc/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"iproute","version":"5.3.0-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:iproute:iproute:5.3.0-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:iproute:5.3.0-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/iproute@0:5.3.0-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"iproute","version":"5.3.0","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"iproute-5.3.0-1.el8.src.rpm","size":1894954,"license":"GPLv2+ and Public Domain","vendor":"CentOS","files":[{"path":"/etc/iproute2/bpf_pinning","mode":33188,"size":85,"sha256":"beb2c6dbeb8c7bcc056a7ebaad1c213bc7204b63f2e7e2d47f0e64f5c8b6ce22"},{"path":"/etc/iproute2/ematch_map","mode":33188,"size":81,"sha256":"0b1d73102310eedcb0b6a6f1b104c40d9d7a33ab5150c88a4698d0d6ab2b8659"},{"path":"/etc/iproute2/group","mode":33188,"size":31,"sha256":"422704225f2cdc53e6a5387a3a35a4bcfd8eabd40e4bc143dfb82ffb5571acd9"},{"path":"/etc/iproute2/nl_protos","mode":33188,"size":262,"sha256":"ca77fbc6bfbc56c9b4c4780b7b336da24ceaf3af3b657937e3076aa48c5d460b"},{"path":"/etc/iproute2/rt_dsfield","mode":33188,"size":735,"sha256":"5baf6453cd30fa05aa3c3ba134e4f5c214f75fcc0c5a51a0faaa86b3f06a962b"},{"path":"/etc/iproute2/rt_protos","mode":33188,"size":201,"sha256":"27930b58e402c31974c446c77cd89f79ff6c9ac3632a694490322af13b0e4003"},{"path":"/etc/iproute2/rt_realms","mode":33188,"size":112,"sha256":"2f0bfd37d31eb05e75b42908d0eeb61bc3394ba4e5a5f110ed3ae2e5fb9e92af"},{"path":"/etc/iproute2/rt_scopes","mode":33188,"size":92,"sha256":"a84a4480b5925624c5ac3ff059faf9af42858e7f9224c06270df3f15baacc9c1"},{"path":"/etc/iproute2/rt_tables","mode":33188,"size":87,"sha256":"08c418b8469951cd5c59da91e4b116cd62cb125478dfac12e5f5067d4d07ad3f"},{"path":"/usr/lib/.build-id/1f/cc22ef386401f95bf26a91a96e845b146bf8ab","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/20/73e1a10f3910f86068ce7a0374afa3721bf4bc","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/22/b8672cf76f72ba902cd6981c7de0e7aaa28541","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/25/93346beaedae366a8e03d0c6aed18b65ba1072","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/42/7b655678a32b8a986c6753d3eeec2e238db857","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/65/2817f71f5d71935610f469e95f380d08b2d335","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/73/289e6c27f4627e21ca561c175758f8adf14e4a","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/98/a1a8ffca49ff2c0ca4fe82425f664ce8e32fdc","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/a9/d54d4bff058ac58dde2c7148e58aeee424d8d6","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/c7/d078e25bc11ec906ec58dfd2808024c462239e","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/d6/2877be6bf0d80d5adf4c33b35b6b62643219f7","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/de/f0b27a5cb2464890fb986869a593d54d09e0f0","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/ed/88c493e1622f8085f1b79a7b1c49e98968cc18","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/f0/a9126efbbb44c135823ecd3fc76cc33c55051a","mode":41471,"size":25,"sha256":""},{"path":"/usr/sbin/arpd","mode":33261,"size":76208,"sha256":"085d3876f0f4c04f407feef5570db6f4cab3687c02131916032880150b7b1c9f"},{"path":"/usr/sbin/bridge","mode":33261,"size":105464,"sha256":"2fcee0a9e1a06b6149ee24098579e38992e4f153d796377772d4ef8d7b2fe6bb"},{"path":"/usr/sbin/ctstat","mode":41471,"size":6,"sha256":""},{"path":"/usr/sbin/devlink","mode":33261,"size":143176,"sha256":"6c9e41bf2c906ee49f16226bddc02f9b8ed74bacf0864a3d43316bf2f11b7792"},{"path":"/usr/sbin/genl","mode":33261,"size":80208,"sha256":"091d677910b0174bb097936cc211016466a33bbb503140d262e83b4d689fd1bb"},{"path":"/usr/sbin/ifcfg","mode":33261,"size":3109,"sha256":"9350a73955a7f842fa9ccfa2584e01faeabad0f0ed0a672df5489bf83b01e8b4"},{"path":"/usr/sbin/ifstat","mode":33261,"size":84472,"sha256":"f8d3a3f0900d256c61fc0214cff614aefdb79160e5c2348656a34464e59370d9"},{"path":"/usr/sbin/ip","mode":33261,"size":608824,"sha256":"c5a6fba182322a9e896e904054d0c97cc88b4fd4b4786c562a3bde8a5e91db4c"},{"path":"/usr/sbin/lnstat","mode":33261,"size":25712,"sha256":"3ebd71e5ec6366b01102fe11e4ec05e6e1d371a209973d9b5229c53800cb7df3"},{"path":"/usr/sbin/nstat","mode":33261,"size":76256,"sha256":"e1c5d7dba7613b4fe8e06cab2586b299235d5692017b03e94c77acf769fa2b33"},{"path":"/usr/sbin/rdma","mode":33261,"size":130760,"sha256":"bf0f260aff406c38a8bc23de3523cd6e60721b0df06fea834c426eee1fff61a5"},{"path":"/usr/sbin/routef","mode":33261,"size":208,"sha256":"64db4b55649a6da6be27517add0c75d326e37b699d7f01cf6aea1f2befdab4dd"},{"path":"/usr/sbin/routel","mode":33261,"size":1656,"sha256":"54b636e35ddcb7d332be25971008cd146616acfac998d06e43985fcc30247e82"},{"path":"/usr/sbin/rtacct","mode":33261,"size":43688,"sha256":"34edec6a991b499fe3c42aec0d38a558b8618595ea1212f626899a41e1f20fd8"},{"path":"/usr/sbin/rtmon","mode":33261,"size":80080,"sha256":"b46caa6d96f6db2ac43ea8a9f72c0e3fbbe6c354aa8b03270e94fbcd0a688b18"},{"path":"/usr/sbin/rtpr","mode":33261,"size":70,"sha256":"460f62731a619cf47de57c70673fb5ae39d97d9906dc8694f8e94b40a6b0be8f"},{"path":"/usr/sbin/rtstat","mode":41471,"size":6,"sha256":""},{"path":"/usr/sbin/ss","mode":33261,"size":170048,"sha256":"498c08822542ff1fc985003bd0569d636ea12428dbef9fca05ccd875d6c7c5ce"},{"path":"/usr/sbin/tipc","mode":33261,"size":126520,"sha256":"2c5c4c05fc13ce569377b3c8c0de42b1ff75d8a26e36cd8ae88ca6be54558113"},{"path":"/usr/share/licenses/iproute/COPYING","mode":33188,"size":18011,"sha256":"e6d6a009505e345fe949e1310334fcb0747f28dae2856759de102ab66b722cb4"}]}},{"name":"iptables-libs","version":"1.8.4-10.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:iptables-libs:iptables-libs:1.8.4-10.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:iptables-libs:1.8.4-10.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/iptables-libs@0:1.8.4-10.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"iptables-libs","version":"1.8.4","epoch":0,"architecture":"x86_64","release":"10.el8","sourceRpm":"iptables-1.8.4-10.el8.src.rpm","size":201888,"license":"GPLv2 and Artistic 2.0 and ISC","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/09/a9043ecfbdd56f181e68fcc44a93e0e061c9a7","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/5a/da8dadd60ecda73dc29377c01f5ff329173b2d","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/6c/21f689df2d6ece6577b83b9ef179b27dff0294","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/ef/99d4799972383a04a532504503bc4cf199c19f","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/f0/99923958d783befb92c3563045eb22061714bf","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/ff/4ccb01f4ba9c69c68a21f2fec5f161a430e02a","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libip4tc.so.0","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libip4tc.so.0.1.0","mode":33261,"size":33240,"sha256":"098ea79a69af7f9c6f517ba9f59e8a13be4865466725be9b09886b8a986d374e"},{"path":"/usr/lib64/libip4tc.so.2","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libip4tc.so.2.0.0","mode":33261,"size":33240,"sha256":"ba1d19435b69465ca16d2bbdd135924023e8d62505469156e7aa2be3b89b2c3c"},{"path":"/usr/lib64/libip6tc.so.0","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libip6tc.so.0.1.0","mode":33261,"size":33256,"sha256":"ab5c84d6192ddf07ee237ee65372ed52ba48b42fa4d8a15f4d3a2206582e324e"},{"path":"/usr/lib64/libip6tc.so.2","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libip6tc.so.2.0.0","mode":33261,"size":33256,"sha256":"04795b2ee580befbd39bd33ed0792e8f3135578c492fd17e874104b29b9892df"},{"path":"/usr/lib64/libiptc.so.0","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libiptc.so.0.0.0","mode":33261,"size":6888,"sha256":"902f21896ba36552388fe584ce374804fbdc383919107506bc91c4b1f99ead83"},{"path":"/usr/lib64/libxtables.so.12","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib64/libxtables.so.12.2.0","mode":33261,"size":62008,"sha256":"9e1fc5218906087e4a1247a3361da4ad8eaa07fb4bcac461363f5ed653c924ec"}]}},{"name":"iputils","version":"20180629-2.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:iputils:iputils:20180629-2.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:iputils:20180629-2.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/iputils@0:20180629-2.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"iputils","version":"20180629","epoch":0,"architecture":"x86_64","release":"2.el8","sourceRpm":"iputils-20180629-2.el8.src.rpm","size":351665,"license":"BSD and GPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/ping","mode":33261,"size":77216,"sha256":"eff2160fb18102431ff6e508949f3b46cbf3d22eb363f7d1ea923248b03dd431"},{"path":"/usr/bin/tracepath","mode":33261,"size":19368,"sha256":"32f1f35242730182a4cc1b1211e748d91a38ed3a28e6d2b4935aead66deaf6c9"},{"path":"/usr/lib/.build-id/01/bdf58f5f97056e9e4ed4d7c5bc94e96b634399","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/35/8b125089e86b0809e6c194c17bf3870eacf45f","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/37/f3ae50e499d4bbc4a3c18da527263fd400a7e2","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/4a/ca05f4af354dde3c7a41b113d128af0a1e0587","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/bf/66b49c73c98c5b6ca551c270776e50174647ca","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/fb/8fe003a40daa1bb0b29f442dae417b84db0c28","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/systemd/system/rdisc.service","mode":33188,"size":208,"sha256":"0295537a7d19875c30a322b3bbe5bc0e35c5e2465c2dd2183a2dc5ff31cc26be"},{"path":"/usr/sbin/arping","mode":33261,"size":32944,"sha256":"2f1569aa027445051c1dbbb4c52125f672458ec85b35df1144ba6022f46f56b0"},{"path":"/usr/sbin/clockdiff","mode":33261,"size":23464,"sha256":"2cc5b3b1ab400b32962c5c650fb1e5314e428bb4a5099961cbb6ba2ffb8c479e"},{"path":"/usr/sbin/ifenslave","mode":33261,"size":28288,"sha256":"7b5aadd22031249f005f8c784b2efe4348da214eabb37f72018e817f518b0fca"},{"path":"/usr/sbin/ping","mode":41471,"size":11,"sha256":""},{"path":"/usr/sbin/ping6","mode":41471,"size":11,"sha256":""},{"path":"/usr/sbin/rdisc","mode":33261,"size":28392,"sha256":"28ad98b4e95ddf3dc5ae74337789e17d04b0ed1675fe4b300090544aa49e2309"},{"path":"/usr/sbin/tracepath","mode":41471,"size":16,"sha256":""},{"path":"/usr/sbin/tracepath6","mode":41471,"size":16,"sha256":""},{"path":"/usr/share/licenses/iputils/bsd.txt","mode":33188,"size":1908,"sha256":"83b81ef928f3de9179105e58bd79516bdcc61b925660f549696dfb406baf637c"},{"path":"/usr/share/licenses/iputils/gpl-2.0.txt","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"json-c","version":"0.13.1-0.2.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:json-c:json-c:0.13.1-0.2.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:json-c:0.13.1-0.2.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/json-c@0:0.13.1-0.2.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"json-c","version":"0.13.1","epoch":0,"architecture":"x86_64","release":"0.2.el8","sourceRpm":"json-c-0.13.1-0.2.el8.src.rpm","size":73898,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/9e/cc2e06ab47be14fcae8b8d9be20b844dbfac21","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib64/libjson-c.so.4","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libjson-c.so.4.0.0","mode":33261,"size":71528,"sha256":"ca19126115eec234fc1f715efb1a52b219bf25578e3eb96ca0727f0fa71e0239"},{"path":"/usr/share/licenses/json-c/AUTHORS","mode":33188,"size":165,"sha256":"499d85c7f2c4c38eba61c3d5c505e16f7cce370a149c788d270c915ee3d6f474"},{"path":"/usr/share/licenses/json-c/COPYING","mode":33188,"size":2205,"sha256":"74c1e6ca5eba76b54d0ad00d4815c8315c1b3bc45ff99de61d103dc92486284c"}]}},{"name":"kexec-tools","version":"2.0.20-14.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:kexec-tools:kexec-tools:2.0.20-14.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:kexec-tools:2.0.20-14.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/kexec-tools@0:2.0.20-14.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"kexec-tools","version":"2.0.20","epoch":0,"architecture":"x86_64","release":"14.el8","sourceRpm":"kexec-tools-2.0.20-14.el8.src.rpm","size":1222009,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/etc/kdump.conf","mode":33188,"size":7916,"sha256":"abfbeae87e381d3b00b767ddd6d6cb80ce962bd2d622e276113dbdb83c573700"},{"path":"/etc/makedumpfile.conf.sample","mode":33188,"size":5122,"sha256":"b789d52eeff476170729617551bd35df0a4a5ab22ed80a55cd4356f9b96fab7c"},{"path":"/etc/sysconfig/kdump","mode":33188,"size":1746,"sha256":"b7fc12c35adc95dfd184fc69ba6d3a6b6120a84f02722a2b578e644ba442b543"},{"path":"/usr/bin/kdumpctl","mode":33261,"size":30409,"sha256":"15420470167328ec92f4c41b9898c1d161e879c8b3c805b4bf2c80065afd7c26"},{"path":"/usr/lib/.build-id/36/438ff85c3b4256e1626d01b41ac846d5ad94fc","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/39/4793bd51e551713a31f35d0f3a653bd6050c90","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/be/19aa9e20baba7e80b086befc1b5a4231cdf83e","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/f5/c7127b93edd0b5695928d1651b9656e592267a","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/dracut/modules.d/99earlykdump/early-kdump.sh","mode":33261,"size":1690,"sha256":"615a5497d1c586796ad2163d174f74b151b1dbaa87597a64e5e24727dc4ae2e0"},{"path":"/usr/lib/dracut/modules.d/99earlykdump/module-setup.sh","mode":33261,"size":1879,"sha256":"f819b213de84fda98b2859af7c7beaa8e6aa92400106751dc5e73a878699bae4"},{"path":"/usr/lib/dracut/modules.d/99kdumpbase/kdump-capture.service","mode":33188,"size":945,"sha256":"e29e6e34a69281d6f149ef08fee7b6f8f79ae3911a0ffaf233cabe6898307f4b"},{"path":"/usr/lib/dracut/modules.d/99kdumpbase/kdump-emergency.service","mode":33188,"size":905,"sha256":"38c89025ea2856ef3d66aa18623728e0b7dbf9d8ce5b23e733fddb6361337ea7"},{"path":"/usr/lib/dracut/modules.d/99kdumpbase/kdump-emergency.target","mode":33188,"size":451,"sha256":"75d3637d8829009015f9ac0b6b2b93b260f6700f3bf930155080906b696d4720"},{"path":"/usr/lib/dracut/modules.d/99kdumpbase/kdump-error-handler.service","mode":33188,"size":993,"sha256":"9965668ed5f9d7c95c65a27e44b40469c4978011504123334e76cdcfaa150de9"},{"path":"/usr/lib/dracut/modules.d/99kdumpbase/kdump-error-handler.sh","mode":33261,"size":145,"sha256":"23bb509940a9ecc3944bb88526b974f49cfb7d6c133fe11615d8d4604141e4c9"},{"path":"/usr/lib/dracut/modules.d/99kdumpbase/kdump.sh","mode":33261,"size":5526,"sha256":"b025e38d43f9e5d83a498417251c27a6c0f9bfbe6f31dfab00d29133558ac4da"},{"path":"/usr/lib/dracut/modules.d/99kdumpbase/module-setup.sh","mode":33261,"size":27557,"sha256":"9fcd671d36684413ddf892677b8adc67efaba506e3393c2afb001dced8668c76"},{"path":"/usr/lib/dracut/modules.d/99kdumpbase/monitor_dd_progress","mode":33188,"size":482,"sha256":"2e343a54c032f6af0d5f7b5fb49f2d90057b2a234625fe7ee6c1afb21cb5c435"},{"path":"/usr/lib/kdump/kdump-lib-initramfs.sh","mode":33188,"size":6421,"sha256":"0d7d97771b790882170f598e0cbed449edbc672a833ca3e3c3616f61d0185bc7"},{"path":"/usr/lib/kdump/kdump-lib.sh","mode":33261,"size":18810,"sha256":"eed104ced26a3afed610ae50a86c44a4e7ad519a8ddbef99651eca90bac5bbb0"},{"path":"/usr/lib/systemd/system-generators/kdump-dep-generator.sh","mode":33261,"size":504,"sha256":"f660e26df9c4843340093a294bcd41a68a71cea48314b5d1a3553bba5038bbbc"},{"path":"/usr/lib/systemd/system/kdump.service","mode":33188,"size":349,"sha256":"ed8d22fafa6cfafaddcfd9fec82e3fa7fa42aa0366f69676fafa97e200b0506a"},{"path":"/usr/lib/udev/kdump-udev-throttler","mode":33261,"size":1444,"sha256":"125d538a59172f779b40ea32fea1e4eb50d849f25eb2537a48328d4401136679"},{"path":"/usr/lib/udev/rules.d/98-kexec.rules","mode":33188,"size":695,"sha256":"c4e3768d55cf3c6e617670f22d4e6f0e0bbc13c278a6c6fba88533f6a25106b8"},{"path":"/usr/lib64/eppic_makedumpfile.so","mode":33261,"size":340368,"sha256":"0a2159fc3f27363736d299b8b6c65bfa8347ecd2c52347820a3543cd9de4e5ce"},{"path":"/usr/sbin/kexec","mode":33261,"size":196080,"sha256":"f2f52991d53b11d6255324746a7bd417f6586d886a7deff28668a1f1480dc84f"},{"path":"/usr/sbin/makedumpfile","mode":33261,"size":414944,"sha256":"842a2059dde5e76a105805d60e104aef63c83ef88aaed6c56a7b5dfb95e8ba2c"},{"path":"/usr/sbin/mkdumprd","mode":33261,"size":12653,"sha256":"52c771ae2b9ffa042feaa92091092121380d97fbdcb2070feb58bd54991bf227"},{"path":"/usr/sbin/vmcore-dmesg","mode":33261,"size":21280,"sha256":"86f2ca2f207e825daea04d1b206678603f4e1add0d85cc5ea52bc4ca3407e0dc"},{"path":"/usr/share/licenses/kexec-tools/COPYING","mode":33188,"size":18008,"sha256":"fa5fc1d1eec39532ea517518eeefd7b6e3c14341a55e5880a0e2a49eee47a5b7"},{"path":"/usr/share/makedumpfile/eppic_scripts/README","mode":33188,"size":9613,"sha256":"13742f4f8ca0fbac7fcb32d00f3c3573de49458fc4b744a815023d163bd00257"},{"path":"/usr/share/makedumpfile/eppic_scripts/ap_messages_3_10_to_4_8.c","mode":33188,"size":1476,"sha256":"958a13aef551aec0d87c39dd547d19555533a108d718aa196aa61b6cbd54df3f"},{"path":"/usr/share/makedumpfile/eppic_scripts/dir_names_3_10_to_3_13.c","mode":33188,"size":1154,"sha256":"36bc2522bf7a2a34e174834848b6288fcd8c8802a6e49525232c0f379666d0ba"},{"path":"/usr/share/makedumpfile/eppic_scripts/dir_names_3_14_to_4_8.c","mode":33188,"size":1298,"sha256":"4e4fa43dfe2dfd66ad3f49e401fed48e581d6e391350633f60a8745df4b0cc5d"},{"path":"/usr/share/makedumpfile/eppic_scripts/keyring_3_10_to_4_3.c","mode":33188,"size":843,"sha256":"429d5bd5697f8d658c6933d55663c933531587a1591462a22a8a3c7d36566946"},{"path":"/usr/share/makedumpfile/eppic_scripts/keyring_4_4_to_4_8.c","mode":33188,"size":10806,"sha256":"96f305662687325d9f999fc85499c46331d00c062682fa20ef77a4eeac5f826d"},{"path":"/usr/share/makedumpfile/eppic_scripts/proc_names_3_10_to_4_8.c","mode":33188,"size":665,"sha256":"4022d00ed0cc1990f90f6cbfb6539ca882197b9225de07c71297e8cc5ce0cd03"},{"path":"/usr/share/makedumpfile/eppic_scripts/tcp_sk_buf_3_10_to_4_8.c","mode":33188,"size":1521,"sha256":"02f9ff6537b88a18bc694f6aef93ebaedba26fbde2e7fbf88dee61c791edb945"},{"path":"/usr/share/makedumpfile/eppic_scripts/udp_sk_buf_3_10_to_4_8.c","mode":33188,"size":1588,"sha256":"a46735bc26bde6adc469b13ab0a85e03324633e21e32ebb2784f3d5fa6870a97"},{"path":"/usr/share/makedumpfile/eppic_scripts/unix_sk_buff_3_10_to_4_8.c","mode":33188,"size":1545,"sha256":"b01a3f1ea2c52fd2cc1f8ee8363d4f09b19466195802d1b5a77dd068fda31ae1"},{"path":"/usr/share/makedumpfile/eppic_scripts/vhost_net_buffers_3_10_to_3_18.c","mode":33188,"size":1886,"sha256":"224727f30eebc8ba9c6c2522b2666f17fa09b008ed58662bc6b0161550cff785"},{"path":"/usr/share/makedumpfile/eppic_scripts/vhost_net_buffers_3_19_to_4_8.c","mode":33188,"size":2031,"sha256":"912f16c251bfe9180dfb84f190aa0e85695bcb23be924b60c5eeefd057392741"},{"path":"/usr/share/makedumpfile/eppic_scripts/vhost_scsi_buffers_3_10_to_4_8.c","mode":33188,"size":1300,"sha256":"7a3f5a6a579c32a9c9b32bdb5b8118f481663f807d5142d71ebe83cd84489e86"}]}},{"name":"keyutils-libs","version":"1.5.10-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:keyutils-libs:keyutils-libs:1.5.10-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:keyutils-libs:1.5.10-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/keyutils-libs@0:1.5.10-6.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"keyutils-libs","version":"1.5.10","epoch":0,"architecture":"x86_64","release":"6.el8","sourceRpm":"keyutils-1.5.10-6.el8.src.rpm","size":43926,"license":"GPLv2+ and LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/e3/51f4017fb7c2ffb92f1d6c1603e7fc04e9be81","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib64/libkeyutils.so.1","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libkeyutils.so.1.6","mode":33261,"size":16320,"sha256":"b1e4dd645f486f0b96755910a30cf4dd395ea033f7091e5819eb775128ae0bef"},{"path":"/usr/share/licenses/keyutils-libs/LICENCE.LGPL","mode":33188,"size":26450,"sha256":"0d15593e3a8ad90917f8509b5ac1e4b5e5d196434a68029aa9dc0858a4a4c521"}]}},{"name":"kmod","version":"25-16.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:kmod:kmod:25-16.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:kmod:25-16.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/kmod@0:25-16.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"kmod","version":"25","epoch":0,"architecture":"x86_64","release":"16.el8","sourceRpm":"kmod-25-16.el8.src.rpm","size":243998,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/etc/depmod.d/dist.conf","mode":33188,"size":116,"sha256":"ea02e4313278315e15acc3276a0d87ca5d151faafdb77a6379ca643316ed9f43"},{"path":"/usr/bin/kmod","mode":33261,"size":163640,"sha256":"0c62ea4fe6bdbd406accd278ee03138bfb692534e3e1d8593c27468118897de5"},{"path":"/usr/lib/.build-id/e7/6c9d3a88b7b530dc45f068ef64e0949d47710f","mode":41471,"size":24,"sha256":""},{"path":"/usr/sbin/depmod","mode":41471,"size":11,"sha256":""},{"path":"/usr/sbin/insmod","mode":41471,"size":11,"sha256":""},{"path":"/usr/sbin/lsmod","mode":41471,"size":11,"sha256":""},{"path":"/usr/sbin/modinfo","mode":41471,"size":11,"sha256":""},{"path":"/usr/sbin/modprobe","mode":41471,"size":11,"sha256":""},{"path":"/usr/sbin/rmmod","mode":41471,"size":11,"sha256":""},{"path":"/usr/sbin/weak-modules","mode":33261,"size":34310,"sha256":"3ae7d9f3a5b6bb37435dba6272b90538964bad17fc31db5b05425c3ae13708b0"},{"path":"/usr/share/bash-completion/completions/kmod","mode":33188,"size":3235,"sha256":"b6fcd713807c9a4eacc3100b58b5e89e7d6cbe1253da41f0c8dd1b1f0efbab7e"}]}},{"name":"kmod-libs","version":"25-16.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:kmod-libs:kmod-libs:25-16.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:kmod-libs:25-16.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/kmod-libs@0:25-16.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"kmod-libs","version":"25","epoch":0,"architecture":"x86_64","release":"16.el8","sourceRpm":"kmod-25-16.el8.src.rpm","size":126640,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/dc/efa37171172d46169bb317ecb97b9bf4f452f4","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libkmod.so.2","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libkmod.so.2.3.3","mode":33261,"size":100208,"sha256":"9e5bbd2460484b4a20037ccf9259347004cc7be0b0fd019eac4f81a467b4abf0"},{"path":"/usr/share/licenses/kmod-libs/COPYING","mode":33188,"size":26432,"sha256":"6095e9ffa777dd22839f7801aa845b31c9ed07f3d6bf8a26dc5d2dec8ccc0ef3"}]}},{"name":"krb5-libs","version":"1.17-18.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:krb5-libs:krb5-libs:1.17-18.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:krb5-libs:1.17-18.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/krb5-libs@0:1.17-18.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"krb5-libs","version":"1.17","epoch":0,"architecture":"x86_64","release":"18.el8","sourceRpm":"krb5-1.17-18.el8.src.rpm","size":2259532,"license":"MIT","vendor":"CentOS","files":[{"path":"/etc/krb5.conf","mode":33188,"size":812,"sha256":"003cd0a16a54e9ff1e852cb08b8d5b0b3df17ac8f8cc382537097d82e35251b2"},{"path":"/etc/krb5.conf.d/crypto-policies","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/13/3dda1a79b86728106df8ba4ddc527fd04a009d","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/14/f655babd6d91f3c68ea65a458379d97087e7af","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/19/13a8f5eb9d5318fce1077c4028fe4b215735b9","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/1a/23b5afb0bba5a9aa7294dfde4ae480ccb11b3b","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/22/8f2adfec7c067919f1328e62210050ff81aaa4","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/30/85581054c14bf37eb713fcb701b0e60700b189","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/be/5d3b360ec19afe039012905785421edf09ba0c","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/c3/c46e3f41a2e913ae3ea9b7c90c105641990eed","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/f5/4b1e7dba788c8eed8e17b476ee2698e7e6e513","mode":41471,"size":51,"sha256":""},{"path":"/usr/lib64/krb5/plugins/preauth/spake.so","mode":33261,"size":87488,"sha256":"606c6c38390c57f7e67e44dad4715b5d06893409e29b39cf5b1b67f506d22c7f"},{"path":"/usr/lib64/krb5/plugins/tls/k5tls.so","mode":33261,"size":20216,"sha256":"7dec9302c09444b4aa7f2f0a49c9b136f5f1e246d8f65b63745b64970cedd085"},{"path":"/usr/lib64/libgssapi_krb5.so.2","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libgssapi_krb5.so.2.2","mode":33261,"size":335032,"sha256":"f768542dc43123a170d643abdde688768f06e07968377b297c1e5f7dcb1e0098"},{"path":"/usr/lib64/libgssrpc.so.4","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libgssrpc.so.4.2","mode":33261,"size":138696,"sha256":"45aeb6a57fd68ba17118aee00e950dd325737547957a63f66baf2b1acf115873"},{"path":"/usr/lib64/libk5crypto.so.3","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libk5crypto.so.3.1","mode":33261,"size":117216,"sha256":"bf9ff30ce2b46a96abbd0770de63875590030766e41767529af4ae26284c6849"},{"path":"/usr/lib64/libkdb5.so.9","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib64/libkdb5.so.9.0","mode":33261,"size":83512,"sha256":"0b9a906d9f061a6837d353339f65e56cd2e43748feba29e09730cd5c25792b58"},{"path":"/usr/lib64/libkrad.so.0","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib64/libkrad.so.0.0","mode":33261,"size":45400,"sha256":"9490fc4cee0eb9fe58e07a535929737c4c977e5ef3406965101a93c54d9dd9ce"},{"path":"/usr/lib64/libkrb5.so.3","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib64/libkrb5.so.3.3","mode":33261,"size":997600,"sha256":"b17114cb6fbe2930d53a0851fcb06cbf7ae5b7e6d5dc51b6f047d8983d45937c"},{"path":"/usr/lib64/libkrb5support.so.0","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libkrb5support.so.0.1","mode":33261,"size":71648,"sha256":"320b2d270ca2df553e9330c2ad265cf24d8905f9046e93da48f6ae7add7f7795"},{"path":"/usr/share/licenses/krb5-libs/LICENSE","mode":33188,"size":62857,"sha256":"5149ea464bde245388d313309539e142156d371788ae57bbd4feb223757f6da1"},{"path":"/usr/share/locale/en_US/LC_MESSAGES/mit-krb5.mo","mode":33188,"size":410,"sha256":"77df12674577f3a59f39384ab8b417975995c04fc444376a5b653951d7792549"}]}},{"name":"langpacks-en","version":"1.0-12.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:langpacks-en:langpacks-en:1.0-12.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:langpacks-en:1.0-12.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/langpacks-en@0:1.0-12.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"langpacks-en","version":"1.0","epoch":0,"architecture":"noarch","release":"12.el8","sourceRpm":"langpacks-1.0-12.el8.src.rpm","size":400,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/share/metainfo/org.fedoraproject.LangPack-en.metainfo.xml","mode":33188,"size":400,"sha256":"3d8d5f74443d23b5a2d5f36ffa1937389d8960cdc748a1a1a88d061fd0e6e13b"}]}},{"name":"less","version":"530-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:less:less:530-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:less:530-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/less@0:530-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"less","version":"530","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"less-530-1.el8.src.rpm","size":344874,"license":"GPLv3+ or BSD","vendor":"CentOS","files":[{"path":"/etc/profile.d/less.csh","mode":33188,"size":500,"sha256":"c117d4f9360e5a7c926f7662b647e9f1d06129817bba8386e4e8b27a01d1040b"},{"path":"/etc/profile.d/less.sh","mode":33188,"size":253,"sha256":"7b85508c9181670fe169935310b8c95d7c2573f0318a70cecd12868569aab891"},{"path":"/usr/bin/less","mode":33261,"size":192040,"sha256":"4c4d5641bc4eb7cdd0e464d4bde1befd5e8332677b2da8670dc0920afd5dd59e"},{"path":"/usr/bin/lessecho","mode":33261,"size":13840,"sha256":"3e1abab5eef3bf496ccc8b4cca317465494699c7edc7864b12d12aa67a5fe0e5"},{"path":"/usr/bin/lesskey","mode":33261,"size":23664,"sha256":"acd20d76648d57b1e3d0a8d12ad9a90f1c9cb26ddc7ad24f145c5611472585d8"},{"path":"/usr/bin/lesspipe.sh","mode":33261,"size":3143,"sha256":"ae570b6311fa231d9ec8120327b4f498fce7d13c2bc0a2ed388b1617dda8e2dd"},{"path":"/usr/lib/.build-id/ac/ea63020bb62652ce22905fd6d5188003f65666","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/df/92fcee7c1d0172f74690401ca656675a70eaae","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/e0/74a4afdfc840aeeef3e281cef0a03efb376d68","mode":41471,"size":28,"sha256":""},{"path":"/usr/share/licenses/less/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/less/LICENSE","mode":33188,"size":1271,"sha256":"c1d5ed3903398ca7f0852995a7a5588829f02d3b89c82165fd674285245ac576"}]}},{"name":"libacl","version":"2.2.53-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libacl:libacl:2.2.53-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libacl:2.2.53-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libacl@0:2.2.53-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libacl","version":"2.2.53","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"acl-2.2.53-1.el8.src.rpm","size":59272,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/b0/f738cdb1ed9e14f117f063739a9a4f9afda533","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib64/libacl.so.1","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libacl.so.1.1.2253","mode":33261,"size":59272,"sha256":"a8b756e123eb05d7e2e7c2551506fd095fc45cdc14c2abbd9f7b369fdc403268"}]}},{"name":"libarchive","version":"3.3.2-8.el8_1","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libarchive:libarchive:3.3.2-8.el8_1:*:*:*:*:*:*:*","cpe:2.3:a:*:libarchive:3.3.2-8.el8_1:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libarchive@0:3.3.2-8.el8_1?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libarchive","version":"3.3.2","epoch":0,"architecture":"x86_64","release":"8.el8_1","sourceRpm":"libarchive-3.3.2-8.el8_1.src.rpm","size":1139914,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/d9/83187a05ffbc235a174072f8a9bc5aaf7c617c","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib64/libarchive.so.13","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib64/libarchive.so.13.3.2","mode":33261,"size":1077576,"sha256":"d3af5cffc8215616900c0841f847c0787ae910cd31b70ab75b4cf860347038b2"},{"path":"/usr/share/licenses/libarchive/COPYING","mode":33188,"size":2841,"sha256":"ae6f35cc1979beb316e4d6431fc34c6fc59f0dd126b425c8552bb41c86e4825d"}]}},{"name":"libassuan","version":"2.5.1-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libassuan:libassuan:2.5.1-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libassuan:2.5.1-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libassuan@0:2.5.1-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libassuan","version":"2.5.1","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"libassuan-2.5.1-3.el8.src.rpm","size":202763,"license":"LGPLv2+ and GPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/87/22b69215e3b2fe5787d8298b57148a56199716","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib64/libassuan.so.0","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libassuan.so.0.8.1","mode":33261,"size":92664,"sha256":"7259bce6b4cee2f78d535f13e2a81f9ba9e407088d03a87fe08be2d445ed7aa7"},{"path":"/usr/share/licenses/libassuan/COPYING","mode":33188,"size":35068,"sha256":"fc82ca8b6fdb18d4e3e85cfd8ab58d1bcd3f1b29abe782895abd91d64763f8e7"},{"path":"/usr/share/licenses/libassuan/COPYING.LIB","mode":33188,"size":26527,"sha256":"a9bdde5616ecdd1e980b44f360600ee8783b1f99b8cc83a2beb163a0a390e861"}]}},{"name":"libattr","version":"2.4.48-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libattr:libattr:2.4.48-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libattr:2.4.48-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libattr@0:2.4.48-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libattr","version":"2.4.48","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"attr-2.4.48-3.el8.src.rpm","size":27346,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/etc/xattr.conf","mode":33188,"size":642,"sha256":"c1259ead36165a9477c9e1948500fb1ae58f33140d2c8b9fdf09ae54425d62b6"},{"path":"/usr/lib/.build-id/98/d8bc035ae86b81b4079f7d4ff0069311a34b23","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libattr.so.1","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libattr.so.1.1.2448","mode":33261,"size":26704,"sha256":"086f1aa3aef923c283b634549b38462508432ce39c4805b7846f7dc4a95bcc28"}]}},{"name":"libblkid","version":"2.32.1-22.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libblkid:libblkid:2.32.1-22.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libblkid:2.32.1-22.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libblkid@0:2.32.1-22.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libblkid","version":"2.32.1","epoch":0,"architecture":"x86_64","release":"22.el8","sourceRpm":"util-linux-2.32.1-22.el8.src.rpm","size":339680,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/e1/90c0bf7a9e7873f4c6a3adf40680f26f9257de","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libblkid.so.1","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libblkid.so.1.1.0","mode":33261,"size":339328,"sha256":"ce3cdbb8593928988c92357778ba7b509bd1be85580e613a2c89dece074ae91b"}]}},{"name":"libcap","version":"2.26-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libcap:libcap:2.26-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libcap:2.26-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libcap@0:2.26-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libcap","version":"2.26","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"libcap-2.26-3.el8.src.rpm","size":124170,"license":"GPLv2","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/0b/3ec9ae50bb2a8a9054a5bcc6673be184a756a9","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/72/5782904e33e383edc26939665a5bda08302989","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/7a/0c900039b15b6d16785e4eaa167d2a6d668ffe","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/a2/661353d5b7bce4c6e2e2f3f0134efc6bfcc7ab","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/a4/822ab6e8849deabe322f53db9bd49bf796772f","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/c9/d6714e0cabdbf12eb0338a4b7d419be8ead387","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib64/libcap.so.2","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib64/libcap.so.2.26","mode":33261,"size":24800,"sha256":"afa444a4a3897e79689fc077821889c070cb3bb9471de5f7ebdd5e5b46d50e6b"},{"path":"/usr/lib64/security/pam_cap.so","mode":33261,"size":11488,"sha256":"9f8734568641501dd52dceb47997125249766ac0083495294bac00ac80f1b2cf"},{"path":"/usr/sbin/capsh","mode":33261,"size":24776,"sha256":"883c199c1b363a35511463aafc30dfd5c151f687f451618a5028870a79c017f3"},{"path":"/usr/sbin/getcap","mode":33261,"size":12440,"sha256":"3083f5192e742011a56da69fd432b51660c80c4cca896613e79e6e186169dec0"},{"path":"/usr/sbin/getpcaps","mode":33261,"size":12080,"sha256":"cbac4beb53a241d6e06ca2ae18038d180014220a5aba5b8b4ca53726917e28b1"},{"path":"/usr/sbin/setcap","mode":33261,"size":12096,"sha256":"31fb35fd530f357bc1678ac7bc65091b49bf0621f328c759d41698f44eb50c54"},{"path":"/usr/share/licenses/libcap/License","mode":33188,"size":20240,"sha256":"088cabde4662b4121258d298b0b2967bc1abffa134457ed9bc4a359685ab92bc"}]}},{"name":"libcap-ng","version":"0.7.9-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libcap-ng:libcap-ng:0.7.9-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libcap-ng:0.7.9-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libcap-ng@0:0.7.9-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libcap-ng","version":"0.7.9","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"libcap-ng-0.7.9-5.el8.src.rpm","size":51278,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/28/7e879ad8f7122a5ed8f28f3679037f68a69a82","mode":41471,"size":36,"sha256":""},{"path":"/usr/share/licenses/libcap-ng/COPYING.LIB","mode":33188,"size":26542,"sha256":"f18a0811fa0e220ccbc42f661545e77f0388631e209585ed582a1c693029c6aa"}]}},{"name":"libcom_err","version":"1.45.4-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libcom_err:libcom_err:1.45.4-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libcom_err:1.45.4-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libcom_err@0:1.45.4-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libcom_err","version":"1.45.4","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"e2fsprogs-1.45.4-3.el8.src.rpm","size":61921,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/8c/84ba6a16a2db788d95e16f1b106972ec427462","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libcom_err.so.2","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libcom_err.so.2.1","mode":33261,"size":17336,"sha256":"3776542f56bc1e9836b7dbcc4164cea74fc43f19905d166c6a844e16b3b0437f"},{"path":"/usr/share/licenses/libcom_err/NOTICE","mode":33188,"size":44585,"sha256":"5da5ef153e559c1d990d4c3eedbedd4442db892d37eae1f35fff069de8ec9020"}]}},{"name":"libcomps","version":"0.1.11-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libcomps:libcomps:0.1.11-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libcomps:0.1.11-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libcomps@0:0.1.11-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libcomps","version":"0.1.11","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"libcomps-0.1.11-4.el8.src.rpm","size":217067,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/ea/25d0b2741c9b686527bbf8fb6f95358d4406cc","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib64/libcomps.so.0.1.11","mode":33261,"size":197032,"sha256":"9a066394585ed74255d4827cb2506a2d4eda76dd7790170f76caf7b15becb408"},{"path":"/usr/share/licenses/libcomps/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"libcurl-minimal","version":"7.61.1-12.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libcurl-minimal:libcurl-minimal:7.61.1-12.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libcurl-minimal:7.61.1-12.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libcurl-minimal@0:7.61.1-12.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libcurl-minimal","version":"7.61.1","epoch":0,"architecture":"x86_64","release":"12.el8","sourceRpm":"curl-7.61.1-12.el8.src.rpm","size":551776,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/ad/a97522eaaf1abe3e7f34daa78193bb083a432b","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib64/libcurl.so.4","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libcurl.so.4.5.0","mode":33261,"size":550688,"sha256":"84ab4fc1ce925efe922416d1bdc55d4540f076d9f6cccb2d67a98500af7cd91f"},{"path":"/usr/share/licenses/libcurl-minimal/COPYING","mode":33188,"size":1088,"sha256":"5f3849ec38ddb927e79f514bf948890c41b8d1407286a49609b8fb1585931095"}]}},{"name":"libdb","version":"5.3.28-37.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libdb:libdb:5.3.28-37.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libdb:5.3.28-37.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libdb@0:5.3.28-37.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libdb","version":"5.3.28","epoch":0,"architecture":"x86_64","release":"37.el8","sourceRpm":"libdb-5.3.28-37.el8.src.rpm","size":2515048,"license":"BSD and LGPLv2 and Sleepycat","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/b1/30d9291796baa852f2aedd89e45c1fc07947e1","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib64/libdb-5.3.so","mode":33261,"size":2480968,"sha256":"f0b46e7664e8d832c2366f1a5100f76b91722c4501c950ab4579da36a9c7bda9"},{"path":"/usr/lib64/libdb-5.so","mode":41471,"size":12,"sha256":""},{"path":"/usr/share/licenses/libdb/LICENSE","mode":33188,"size":7310,"sha256":"b78815181a53241f9347c6b47d1031fd669946f863e1edc807a291354cec024b"},{"path":"/usr/share/licenses/libdb/lgpl-2.1.txt","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libdb-utils","version":"5.3.28-37.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libdb-utils:libdb-utils:5.3.28-37.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libdb-utils:5.3.28-37.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libdb-utils@0:5.3.28-37.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libdb-utils","version":"5.3.28","epoch":0,"architecture":"x86_64","release":"37.el8","sourceRpm":"libdb-5.3.28-37.el8.src.rpm","size":536911,"license":"BSD and LGPLv2 and Sleepycat","vendor":"CentOS","files":[{"path":"/usr/bin/db_archive","mode":33261,"size":17280,"sha256":"ef4c11220161d84a71bb5ef14f463bd57a4b214b6d55e9418f641f7a811a991b"},{"path":"/usr/bin/db_checkpoint","mode":33261,"size":23352,"sha256":"253dd83dfb55587a21f2b70dcc7b361088afbe7752fbd9a373727b222ed42567"},{"path":"/usr/bin/db_deadlock","mode":33261,"size":23336,"sha256":"8e9397194af001138fc37f3d30ddbe3697c817b4f85177c2b9746de5c081acd0"},{"path":"/usr/bin/db_dump","mode":33261,"size":23560,"sha256":"a358a5b630c7996a477eda4109233b878378bb0bca6df17567f43283f0f5d359"},{"path":"/usr/bin/db_dump185","mode":33261,"size":132728,"sha256":"e50361b1b8f71d1b233eb6d647d5478fc8543ba6716e42671ad8117ad701b3bd"},{"path":"/usr/bin/db_hotbackup","mode":33261,"size":25624,"sha256":"4f6f23d54185721288c519fdc0dcd993560ee11e6fd34ca8e0ad8006eb647df6"},{"path":"/usr/bin/db_load","mode":33261,"size":36608,"sha256":"6362be7a77ab35713472f432e299c32244f497f042a82df20173fbc57422c148"},{"path":"/usr/bin/db_log_verify","mode":33261,"size":23504,"sha256":"5aea33ee08efdd9c1743bd7ab42372a03a4413dc6f752d0a37633ee256e2eb8e"},{"path":"/usr/bin/db_printlog","mode":33261,"size":63904,"sha256":"e923fa862759bdf1e4f18b5101a5c8976e8cc4c04dfb8575e7dc31c7118863b5"},{"path":"/usr/bin/db_recover","mode":33261,"size":21552,"sha256":"a94f0ec63fcf08bc28f4e58dd0dd98d7025fc1b9f0cef6b009d0d002ce0286ad"},{"path":"/usr/bin/db_replicate","mode":33261,"size":23352,"sha256":"6894674013bf54eab3d853eee0d6322147bb0ffb9db3152edf1b9eeac3ef4524"},{"path":"/usr/bin/db_stat","mode":33261,"size":23408,"sha256":"9fe22ccd46d0113e7a380ad58bc33b393e1cb143047fff1581273b866f60358e"},{"path":"/usr/bin/db_tuner","mode":33261,"size":29912,"sha256":"6785b71758cc817baec047ca4d9a05097eb3e808972ecd0a7d6c1959aa931b08"},{"path":"/usr/bin/db_upgrade","mode":33261,"size":17280,"sha256":"3476af2f02a913acf02f3aeca95f81f14bfe2d5634b4a45f23f4eec643c09b05"},{"path":"/usr/bin/db_verify","mode":33261,"size":23328,"sha256":"f411c4b3535a1e6cc0f30e9421ca17eedaccc84871e66a5db15970cd41b0a6dd"},{"path":"/usr/lib/.build-id/04/caf243f9ac4c3214c9a5e2537ba7f437ddf4f0","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/0b/2f879dcdc5bb9ea37c5a10883c422f65e90b26","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/14/7b88b800c3d10b7b7efa6bf370d448d345dadd","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/1a/423f538e620c7f59cb67920d0eaccbb28a9c1c","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/27/052489858d35d1384853d4c0050dd0c1b22dbd","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/71/96607d788ecf830f9d0b7df969257d941c7029","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/77/d01b32ad2830e2101195da219e0e0599c32f8b","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/94/0c322e4768657b57bbf2cc2969aa4076fe7735","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/99/e7f71e4710aebbd445b29831c8d6409d2e73e0","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/9c/9764b42328e642facb9dd99c136d8c840cffb3","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/ab/9a187b092af667a5b4ff790dfc5845d9a20dbd","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/b7/eb1c22d17010ed27b5629d827ca44be4e3c67f","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/c4/ec6717aaaeaa2c4c5f5174838b5bc8fbd1176c","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/e4/0c8a32976dedac3e417586902d7ed4879f70bc","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/e4/1db4454e9e5f9c45ea8b1672a148f61ba16b1d","mode":41471,"size":28,"sha256":""}]}},{"name":"libdnf","version":"0.39.1-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libdnf:libdnf:0.39.1-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libdnf:0.39.1-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libdnf@0:0.39.1-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libdnf","version":"0.39.1","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"libdnf-0.39.1-5.el8.src.rpm","size":2123733,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/bf/d460c15f366b466f6e4bb517087e7b78b8e272","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib64/libdnf.so.2","mode":33261,"size":1851720,"sha256":"6eed81c7fadb756b30ffba139e713b1cebd44a0142b9a8964378f664ff456534"},{"path":"/usr/lib64/libdnf/plugins/README","mode":33188,"size":194,"sha256":"73532ee155af95978529b5d896ed657ac8823a3ab32959bdde9719b35e6a7ae6"},{"path":"/usr/share/licenses/libdnf/COPYING","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libfdisk","version":"2.32.1-22.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libfdisk:libfdisk:2.32.1-22.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libfdisk:2.32.1-22.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libfdisk@0:2.32.1-22.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libfdisk","version":"2.32.1","epoch":0,"architecture":"x86_64","release":"22.el8","sourceRpm":"util-linux-2.32.1-22.el8.src.rpm","size":438722,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/9c/d6146937ca5458b6f85e91f33b4cdfa5ade752","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libfdisk.so.1","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libfdisk.so.1.1.0","mode":33261,"size":411840,"sha256":"e921d4f9be3bd7dc4a6da6c07cb33f9295bd5e7ff8ac5b053d2eaef03d06b09d"},{"path":"/usr/share/licenses/libfdisk/COPYING","mode":33188,"size":352,"sha256":"a2dc3d3adff705e225aee932ec4c2ac29ee45221cf7566e7b837a6d0d1442966"},{"path":"/usr/share/licenses/libfdisk/COPYING.LGPLv2.1","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libffi","version":"3.1-21.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libffi:libffi:3.1-21.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libffi:3.1-21.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libffi@0:3.1-21.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libffi","version":"3.1","epoch":0,"architecture":"x86_64","release":"21.el8","sourceRpm":"libffi-3.1-21.el8.src.rpm","size":68404,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/6a/a4af1be0871bc681a237eba12db42e5107c3f1","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/libffi.so.6","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libffi.so.6.0.2","mode":33261,"size":51808,"sha256":"81bedb19c7fbf87446cc73eac9abe994843347b62d5f417cfbf189980a5c1b40"},{"path":"/usr/share/licenses/libffi/LICENSE","mode":33188,"size":1132,"sha256":"0f4d7a0bfb83c37465d42dc305f124189196cc0cc2cc8d6f8461103682aebbc5"}]}},{"name":"libgcc","version":"8.3.1-5.el8.0.2","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libgcc:libgcc:8.3.1-5.el8.0.2:*:*:*:*:*:*:*","cpe:2.3:a:*:libgcc:8.3.1-5.el8.0.2:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libgcc@0:8.3.1-5.el8.0.2?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libgcc","version":"8.3.1","epoch":0,"architecture":"x86_64","release":"5.el8.0.2","sourceRpm":"gcc-8.3.1-5.el8.0.2.src.rpm","size":190232,"license":"GPLv3+ and GPLv3+ with exceptions and GPLv2+ with exceptions and LGPLv2+ and BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/8a/c98d4b3b4aa97ddf2f0ecaa415e36eb7f97df1","mode":41471,"size":42,"sha256":""},{"path":"/usr/share/licenses/libgcc/COPYING","mode":33188,"size":18002,"sha256":"231f7edcc7352d7734a96eef0b8030f77982678c516876fcb81e25b32d68564c"},{"path":"/usr/share/licenses/libgcc/COPYING.LIB","mode":33188,"size":26440,"sha256":"32434afcc8666ba060e111d715bfdb6c2d5dd8a35fa4d3ab8ad67d8f850d2f2b"},{"path":"/usr/share/licenses/libgcc/COPYING.RUNTIME","mode":33188,"size":3324,"sha256":"9d6b43ce4d8de0c878bf16b54d8e7a10d9bd42b75178153e3af6a815bdc90f74"},{"path":"/usr/share/licenses/libgcc/COPYING3","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/libgcc/COPYING3.LIB","mode":33188,"size":7639,"sha256":"a853c2ffec17057872340eee242ae4d96cbf2b520ae27d903e1b2fef1a5f9d1c"}]}},{"name":"libgcrypt","version":"1.8.3-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libgcrypt:libgcrypt:1.8.3-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libgcrypt:1.8.3-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libgcrypt@0:1.8.3-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libgcrypt","version":"1.8.3","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"libgcrypt-1.8.3-4.el8.src.rpm","size":1547061,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/etc/gcrypt/random.conf","mode":33188,"size":157,"sha256":"639bd7d4df19f8e810433e7158f2e2c0b8d8034b9276562f255dd13b108403e5"},{"path":"/usr/lib/.build-id/fa/6efc1bcadcdacac72fc0cd6643f22458b37405","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/.libgcrypt.so.20.hmac","mode":33188,"size":65,"sha256":"980aa0d6e72fb8b8a0df069d0579cb6c5993df8d2615a7f6d4ec6b0028b8e815"},{"path":"/usr/lib64/libgcrypt.so.20","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libgcrypt.so.20.2.3","mode":33261,"size":1465680,"sha256":"1997ab868c4b8efaaa5b1c1322c5441954fc84f5ecaf4c55a4645c55e6538498"},{"path":"/usr/share/licenses/libgcrypt/COPYING.LIB","mode":33188,"size":26536,"sha256":"ca0061fc1381a3ab242310e4b3f56389f28e3d460eb2fd822ed7a21c6f030532"}]}},{"name":"libgpg-error","version":"1.31-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libgpg-error:libgpg-error:1.31-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libgpg-error:1.31-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libgpg-error@0:1.31-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libgpg-error","version":"1.31","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"libgpg-error-1.31-1.el8.src.rpm","size":902818,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/gpg-error","mode":33261,"size":34976,"sha256":"b4e8dfff1b89e4362c8761aea7609aa7570d68a377a124db5238eaee41154a42"},{"path":"/usr/lib/.build-id/10/1264fa39fb83eae557555b5e0d6fe0153407e8","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/bb/7f7160a8a0111df58798d38c564c8035a195c1","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib64/libgpg-error.so.0","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib64/libgpg-error.so.0.24.2","mode":33261,"size":145984,"sha256":"d4e115d012cf30a506674f47b55652f67eee3c18168f7c2ea10ca1b58cacbe20"},{"path":"/usr/share/libgpg-error/errorref.txt","mode":33188,"size":35668,"sha256":"3fdf9d4c2ffde9cd9da0aa3f90183608a25bdced8f02e9e92500ec4d77785ed2"},{"path":"/usr/share/licenses/libgpg-error/COPYING","mode":33188,"size":18002,"sha256":"231f7edcc7352d7734a96eef0b8030f77982678c516876fcb81e25b32d68564c"},{"path":"/usr/share/licenses/libgpg-error/COPYING.LIB","mode":33188,"size":26527,"sha256":"a9bdde5616ecdd1e980b44f360600ee8783b1f99b8cc83a2beb163a0a390e861"}]}},{"name":"libidn2","version":"2.2.0-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libidn2:libidn2:2.2.0-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libidn2:2.2.0-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libidn2@0:2.2.0-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libidn2","version":"2.2.0","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"libidn2-2.2.0-1.el8.src.rpm","size":287762,"license":"(GPLv2+ or LGPLv3+) and GPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/b4/941c3d93656ab1fde923aa71884fecb96f1ecd","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libidn2.so.0","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libidn2.so.0.3.6","mode":33261,"size":165624,"sha256":"5a29ff55543867590e861d72faa872ba2cf7bf35730e98189f3036ced3c518c3"},{"path":"/usr/share/licenses/libidn2/COPYING","mode":33188,"size":1555,"sha256":"73483f797a83373fca1b968c11785b98c4fc4803cdc7d3210811ca8b075d6d76"},{"path":"/usr/share/licenses/libidn2/COPYING.LESSERv3","mode":33188,"size":7651,"sha256":"da7eabb7bafdf7d3ae5e9f223aa5bdc1eece45ac569dc21b3b037520b4464768"},{"path":"/usr/share/licenses/libidn2/COPYING.unicode","mode":33188,"size":8782,"sha256":"01d621eef165cf4d3d3dbb737aa0699178d94c6f18cf87e9dde6db3ca7790f46"},{"path":"/usr/share/licenses/libidn2/COPYINGv2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"libkcapi","version":"1.1.1-16_1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libkcapi:libkcapi:1.1.1-16_1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libkcapi:1.1.1-16_1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libkcapi@0:1.1.1-16_1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libkcapi","version":"1.1.1","epoch":0,"architecture":"x86_64","release":"16_1.el8","sourceRpm":"libkcapi-1.1.1-16_1.el8.src.rpm","size":82828,"license":"BSD or GPLv2","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/57/44df5124443e5a47b3f28c7b6bc120d8a21f2f","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/sysctl.d/50-libkcapi-optmem_max.conf","mode":33188,"size":246,"sha256":"d129f7e21b6757b66b715e585d8000d319f47ffa3aac1e1fca97702544ba996c"},{"path":"/usr/share/licenses/libkcapi/COPYING","mode":33188,"size":1774,"sha256":"b0336f8f07a6abf8b0a59d961f53601d7c4a7c09a8137805b730a34a976039f8"},{"path":"/usr/share/licenses/libkcapi/COPYING.bsd","mode":33188,"size":1382,"sha256":"13aa749a5b0a454917a944ed8fffc530b784f5ead522b1aacaf4ec8aa55a6239"},{"path":"/usr/share/licenses/libkcapi/COPYING.gplv2","mode":33188,"size":18011,"sha256":"e6d6a009505e345fe949e1310334fcb0747f28dae2856759de102ab66b722cb4"}]}},{"name":"libkcapi-hmaccalc","version":"1.1.1-16_1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libkcapi-hmaccalc:libkcapi-hmaccalc:1.1.1-16_1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libkcapi-hmaccalc:1.1.1-16_1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libkcapi-hmaccalc@0:1.1.1-16_1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libkcapi-hmaccalc","version":"1.1.1","epoch":0,"architecture":"x86_64","release":"16_1.el8","sourceRpm":"libkcapi-1.1.1-16_1.el8.src.rpm","size":35165,"license":"BSD or GPLv2","vendor":"CentOS","files":[{"path":"/usr/bin/sha1hmac","mode":33261,"size":34520,"sha256":"7773147b4eaaf0e6e2fabcbe8ffb4addc6cceed9b57854230934f6b46d9e38f6"},{"path":"/usr/bin/sha224hmac","mode":33261,"size":34520,"sha256":"7773147b4eaaf0e6e2fabcbe8ffb4addc6cceed9b57854230934f6b46d9e38f6"},{"path":"/usr/bin/sha256hmac","mode":33261,"size":34520,"sha256":"7773147b4eaaf0e6e2fabcbe8ffb4addc6cceed9b57854230934f6b46d9e38f6"},{"path":"/usr/bin/sha384hmac","mode":33261,"size":34520,"sha256":"7773147b4eaaf0e6e2fabcbe8ffb4addc6cceed9b57854230934f6b46d9e38f6"},{"path":"/usr/bin/sha512hmac","mode":33261,"size":34520,"sha256":"7773147b4eaaf0e6e2fabcbe8ffb4addc6cceed9b57854230934f6b46d9e38f6"},{"path":"/usr/lib/.build-id/05/a666af01511a7cba51a0e53be3d2f2ad316f83","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/05/a666af01511a7cba51a0e53be3d2f2ad316f83.1","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/05/a666af01511a7cba51a0e53be3d2f2ad316f83.2","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/05/a666af01511a7cba51a0e53be3d2f2ad316f83.3","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/05/a666af01511a7cba51a0e53be3d2f2ad316f83.4","mode":41471,"size":30,"sha256":""}]}},{"name":"libksba","version":"1.3.5-7.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libksba:libksba:1.3.5-7.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libksba:1.3.5-7.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libksba@0:1.3.5-7.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libksba","version":"1.3.5","epoch":0,"architecture":"x86_64","release":"7.el8","sourceRpm":"libksba-1.3.5-7.el8.src.rpm","size":342935,"license":"(LGPLv3+ or GPLv2+) and GPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/2c/cd379600c89907c62978de30a3ecbdf168283c","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libksba.so.8","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libksba.so.8.11.6","mode":33261,"size":246376,"sha256":"43e505604a3b889263ef68dea58b1b72fab0adfe468760b941683bbcd3c1c942"},{"path":"/usr/share/licenses/libksba/COPYING","mode":33188,"size":198,"sha256":"6197b98c6bf69838c624809c509d84333de1bc847155168c0e84527446a27076"},{"path":"/usr/share/licenses/libksba/COPYING.GPLv2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/libksba/COPYING.GPLv3","mode":33188,"size":35064,"sha256":"0abbff814cd00e2b0b6d08395af2b419c1a92026c4b4adacbb65ccda45fa58cf"},{"path":"/usr/share/licenses/libksba/COPYING.LGPLv3","mode":33188,"size":7651,"sha256":"da7eabb7bafdf7d3ae5e9f223aa5bdc1eece45ac569dc21b3b037520b4464768"}]}},{"name":"libmetalink","version":"0.1.3-7.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libmetalink:libmetalink:0.1.3-7.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libmetalink:0.1.3-7.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libmetalink@0:0.1.3-7.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libmetalink","version":"0.1.3","epoch":0,"architecture":"x86_64","release":"7.el8","sourceRpm":"libmetalink-0.1.3-7.el8.src.rpm","size":76960,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/3c/c23037ce6f44c36f151e64eb50100c3b1d52be","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib64/libmetalink.so.3","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib64/libmetalink.so.3.1.0","mode":33261,"size":74768,"sha256":"a93cdd774d447277911b31fc431cd4900af21466a85fc31f4cfed6b441aa0dfd"},{"path":"/usr/share/licenses/libmetalink/COPYING","mode":33188,"size":1080,"sha256":"eb6fc70929925292e4859c3ca8e34dde5389afd9e47c5826c5a540e3e620d17d"}]}},{"name":"libmnl","version":"1.0.4-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libmnl:libmnl:1.0.4-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libmnl:1.0.4-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libmnl@0:1.0.4-6.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libmnl","version":"1.0.4","epoch":0,"architecture":"x86_64","release":"6.el8","sourceRpm":"libmnl-1.0.4-6.el8.src.rpm","size":53687,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/72/8dfaadd1cf4a41db2e06baa2c6f1c1e2b9deb2","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/libmnl.so.0","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libmnl.so.0.2.0","mode":33261,"size":25936,"sha256":"1831b10a8eca072d8b0a3631f45be53e47d486cddad231ac9a920a5ed41832bc"},{"path":"/usr/share/licenses/libmnl/COPYING","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libmodulemd1","version":"1.8.16-0.2.8.2.1","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libmodulemd1:libmodulemd1:1.8.16-0.2.8.2.1:*:*:*:*:*:*:*","cpe:2.3:a:*:libmodulemd1:1.8.16-0.2.8.2.1:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libmodulemd1@0:1.8.16-0.2.8.2.1?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libmodulemd1","version":"1.8.16","epoch":0,"architecture":"x86_64","release":"0.2.8.2.1","sourceRpm":"libmodulemd-2.8.2-1.el8.src.rpm","size":546039,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/bin/modulemd-validator-v1","mode":33261,"size":17160,"sha256":"dfa1a90bd01cca4a2fee36ae12a129ef34ca4c4973c3e3bbb82c699362a3ec7e"},{"path":"/usr/lib/.build-id/7b/29eef41b4b003955e44a68c917c53e14948c25","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/c4/d92d586cb2f47d0e828a566c56aeb6a63c0995","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib64/girepository-1.0/Modulemd-1.0.typelib","mode":33188,"size":42372,"sha256":"1386c258540933f4a2878257fe663f74ca4989dbde8bdad5eb378794a970cf49"},{"path":"/usr/lib64/libmodulemd.so.1","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libmodulemd.so.1.8.16","mode":33261,"size":481256,"sha256":"2a69293f8fb0aa6069728e4b0c9ec0b0243e495651ef4500e7ffb90cb6db0424"},{"path":"/usr/share/licenses/libmodulemd1/COPYING","mode":33188,"size":1101,"sha256":"40afccd95484d483800c17dd18a734518ba36e832841579a1f21dc94fb73bbdf"}]}},{"name":"libmount","version":"2.32.1-22.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libmount:libmount:2.32.1-22.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libmount:2.32.1-22.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libmount@0:2.32.1-22.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libmount","version":"2.32.1","epoch":0,"architecture":"x86_64","release":"22.el8","sourceRpm":"util-linux-2.32.1-22.el8.src.rpm","size":398154,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/3d/045f0f55963b75acbed78068e2f7e52c684696","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libmount.so.1","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libmount.so.1.1.0","mode":33261,"size":371272,"sha256":"d3bb9aa30cde027f60e951a77b9fa49fd5798d544e96928c919766276487d53a"},{"path":"/usr/share/licenses/libmount/COPYING","mode":33188,"size":352,"sha256":"a2dc3d3adff705e225aee932ec4c2ac29ee45221cf7566e7b837a6d0d1442966"},{"path":"/usr/share/licenses/libmount/COPYING.LGPLv2.1","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libnghttp2","version":"1.33.0-1.el8_0.1","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libnghttp2:libnghttp2:1.33.0-1.el8_0.1:*:*:*:*:*:*:*","cpe:2.3:a:*:libnghttp2:1.33.0-1.el8_0.1:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libnghttp2@0:1.33.0-1.el8_0.1?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libnghttp2","version":"1.33.0","epoch":0,"architecture":"x86_64","release":"1.el8_0.1","sourceRpm":"nghttp2-1.33.0-1.el8_0.1.src.rpm","size":233188,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/65/48ed49b25dd4ed54a8c2ceedb0989ec1ecf008","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib64/libnghttp2.so.14","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libnghttp2.so.14.17.0","mode":33261,"size":232032,"sha256":"409b6a1c2e8e436d2353fe8ed48d8dc1d1b012e283d94d8448bbce8b8ea21ab4"},{"path":"/usr/share/licenses/libnghttp2/COPYING","mode":33188,"size":1156,"sha256":"6b94f3abc1aabd0c72a7c7d92a77f79dda7c8a0cb3df839a97890b4116a2de2a"}]}},{"name":"libnsl2","version":"1.2.0-2.20180605git4a062cf.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libnsl2:libnsl2:1.2.0-2.20180605git4a062cf.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libnsl2:1.2.0-2.20180605git4a062cf.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libnsl2@0:1.2.0-2.20180605git4a062cf.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libnsl2","version":"1.2.0","epoch":0,"architecture":"x86_64","release":"2.20180605git4a062cf.el8","sourceRpm":"libnsl2-1.2.0-2.20180605git4a062cf.el8.src.rpm","size":147122,"license":"BSD and LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/e2/4e23fc5955c8e181c09c283208f74885469b7d","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/libnsl.so.2","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libnsl.so.2.0.0","mode":33261,"size":120592,"sha256":"cdd2cd11210e27f0b955b428330543b783ed348576d75a4a116715e26e68bb5d"},{"path":"/usr/share/licenses/libnsl2/COPYING","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libpcap","version":"1.9.0-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libpcap:libpcap:1.9.0-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libpcap:1.9.0-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libpcap@14:1.9.0-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libpcap","version":"1.9.0","epoch":14,"architecture":"x86_64","release":"3.el8","sourceRpm":"libpcap-1.9.0-3.el8.src.rpm","size":424251,"license":"BSD with advertising","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/a2/c9f6f27bac2db7be4285a1adb0b39e98bcfc16","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libpcap.so.1","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libpcap.so.1.9.0","mode":33261,"size":355456,"sha256":"de2c6ba7df939e2c7313c93661434cb219b519f2c9b96d5d974781dcccef4451"},{"path":"/usr/share/licenses/libpcap/LICENSE","mode":33188,"size":868,"sha256":"8a54594d257e14a5260ac770f1633516cb51e3fc28c40136ce2697014eda7afd"}]}},{"name":"libpwquality","version":"1.4.0-9.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libpwquality:libpwquality:1.4.0-9.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libpwquality:1.4.0-9.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libpwquality@0:1.4.0-9.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libpwquality","version":"1.4.0","epoch":0,"architecture":"x86_64","release":"9.el8","sourceRpm":"libpwquality-1.4.0-9.el8.src.rpm","size":384791,"license":"BSD or GPLv2+","vendor":"CentOS","files":[{"path":"/etc/security/pwquality.conf","mode":33188,"size":2151,"sha256":"77976ab8c2b73c5951600cb43526076c28a650677988df1c9a8e981ea9d65c9f"},{"path":"/usr/bin/pwmake","mode":33261,"size":13360,"sha256":"c621cff46db52738a61af46cf12ccc503573417e8b99869f890bb70d75fd8087"},{"path":"/usr/bin/pwscore","mode":33261,"size":13368,"sha256":"facc9b2befd0a41f7dd39877334e021545b3316970cf22373ee326470be65a24"},{"path":"/usr/lib/.build-id/2e/3e19c2522d09d77928b110730996df9d4c1860","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/5e/951b94daa8a1f9473fd97068fe5c544fcb28ae","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/73/a538ca2adb7862597777fb8e88102ab4e195ab","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/79/8f0b3114f6c1a476869de90b9a445764322605","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib64/libpwquality.so.1","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libpwquality.so.1.0.2","mode":33261,"size":25728,"sha256":"959c4dcc3f02dd5a6626690f588b407f8adb715a6bd492336bea475cb3a22b8d"},{"path":"/usr/lib64/security/pam_pwquality.so","mode":33261,"size":11896,"sha256":"6b1846d9b7b079cb1ef23b4f2369ec2ecfe1191135c51a6ea1e8499632e8201e"},{"path":"/usr/share/licenses/libpwquality/COPYING","mode":33188,"size":20019,"sha256":"aa44d09f651bf99b56253187c7778a240740c767d28453ab7fdc9804c842baee"}]}},{"name":"librepo","version":"1.11.0-2.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:librepo:librepo:1.11.0-2.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:librepo:1.11.0-2.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/librepo@0:1.11.0-2.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"librepo","version":"1.11.0","epoch":0,"architecture":"x86_64","release":"2.el8","sourceRpm":"librepo-1.11.0-2.el8.src.rpm","size":262664,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/6b/4a8cc17ccabba08336fe33304634d6c65b3058","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib64/librepo.so.0","mode":33261,"size":232136,"sha256":"1d2ea01402546ab0bb7d6f8e5a22cfec6794a19bfbcaeb10ff8bfa376d7e66ad"},{"path":"/usr/share/licenses/librepo/COPYING","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libreport-filesystem","version":"2.9.5-10.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libreport-filesystem:libreport-filesystem:2.9.5-10.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libreport-filesystem:2.9.5-10.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libreport-filesystem@0:2.9.5-10.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libreport-filesystem","version":"2.9.5","epoch":0,"architecture":"x86_64","release":"10.el8","sourceRpm":"libreport-2.9.5-10.el8.src.rpm","size":0,"license":"GPLv2+","vendor":"CentOS","files":[]}},{"name":"libseccomp","version":"2.4.1-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libseccomp:libseccomp:2.4.1-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libseccomp:2.4.1-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libseccomp@0:2.4.1-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libseccomp","version":"2.4.1","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"libseccomp-2.4.1-1.el8.src.rpm","size":402960,"license":"LGPLv2","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/48/4c2bb0b4b6b59f1064ffb099ee99b785466b8d","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libseccomp.so.2","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libseccomp.so.2.4.1","mode":33261,"size":366680,"sha256":"9003d9d7f7d903f6201bae85ffefc477ce3b5057d1fc3226295f9f5a4d47b7ef"},{"path":"/usr/share/licenses/libseccomp/LICENSE","mode":33188,"size":24428,"sha256":"102900208eef27b766380135906d431dba87edaa7ec6aa72e6ebd3dd67f3a97b"}]}},{"name":"libselinux","version":"2.9-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libselinux:libselinux:2.9-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libselinux:2.9-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libselinux@0:2.9-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libselinux","version":"2.9","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"libselinux-2.9-3.el8.src.rpm","size":305912,"license":"Public Domain","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/41/a935c4b317ef5c66198049b1f898f86dc574d1","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/tmpfiles.d/libselinux.conf","mode":33188,"size":30,"sha256":"afe23890fb2e12e6756e5d81bad3c3da33f38a95d072731c0422fbeb0b1fa1fc"},{"path":"/usr/lib64/libselinux.so.1","mode":33261,"size":304848,"sha256":"e751ad9f768433ac9a339a35d36c2fdd07dc2cd9d66fb26b3c4f1d46e1d5363c"},{"path":"/usr/share/licenses/libselinux/LICENSE","mode":33188,"size":1034,"sha256":"86657b4c0fe868d7cbd977cb04c63b6c667e08fa51595a7bc846ad4bed8fc364"}]}},{"name":"libsemanage","version":"2.9-2.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libsemanage:libsemanage:2.9-2.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libsemanage:2.9-2.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libsemanage@0:2.9-2.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libsemanage","version":"2.9","epoch":0,"architecture":"x86_64","release":"2.el8","sourceRpm":"libsemanage-2.9-2.el8.src.rpm","size":477962,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/etc/selinux/semanage.conf","mode":33188,"size":2425,"sha256":"68d403bca3d7bd2e90d00cf44622dc0598817197994812e06367df0c239b1204"},{"path":"/usr/lib/.build-id/e7/856494f06e80c229f564ba008279d4d6c4e459","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libsemanage.so.1","mode":33261,"size":444216,"sha256":"9bc98c2f62924e0a8ce46035a6ad37ca699640403c5519be28506553e9adfeb0"},{"path":"/usr/share/licenses/libsemanage/COPYING","mode":33188,"size":26432,"sha256":"6095e9ffa777dd22839f7801aa845b31c9ed07f3d6bf8a26dc5d2dec8ccc0ef3"}]}},{"name":"libsepol","version":"2.9-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libsepol:libsepol:2.9-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libsepol:2.9-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libsepol@0:2.9-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libsepol","version":"2.9","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"libsepol-2.9-1.el8.src.rpm","size":996264,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/d1/42ffe3ba2fe4e29f2d3d726464979381ba9389","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib64/libsepol.so.1","mode":33261,"size":969832,"sha256":"1a91945edbab7b0a955a36b6155f15aa6052d344b79f622b2e192fffe2397f2a"},{"path":"/usr/share/licenses/libsepol/COPYING","mode":33188,"size":26432,"sha256":"6095e9ffa777dd22839f7801aa845b31c9ed07f3d6bf8a26dc5d2dec8ccc0ef3"}]}},{"name":"libsigsegv","version":"2.11-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libsigsegv:libsigsegv:2.11-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libsigsegv:2.11-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libsigsegv@0:2.11-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libsigsegv","version":"2.11","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"libsigsegv-2.11-5.el8.src.rpm","size":47034,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/42/ae5a2692c9ba4b432587f875f59dc9acb5f590","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libsigsegv.so.2","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libsigsegv.so.2.0.4","mode":33261,"size":17920,"sha256":"48380facc040c4b0fc14e19b970dfeb941c74ed20438153398762ea2ce304fad"},{"path":"/usr/share/licenses/libsigsegv/COPYING","mode":33188,"size":18154,"sha256":"8f2983e9a940367f48999881c14775db725ee643bce1e2f1ba195eb629a33cde"}]}},{"name":"libsmartcols","version":"2.32.1-22.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libsmartcols:libsmartcols:2.32.1-22.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libsmartcols:2.32.1-22.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libsmartcols@0:2.32.1-22.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libsmartcols","version":"2.32.1","epoch":0,"architecture":"x86_64","release":"22.el8","sourceRpm":"util-linux-2.32.1-22.el8.src.rpm","size":244258,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/dc/482d630c1b383622441558101420917d313b7f","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib64/libsmartcols.so.1","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libsmartcols.so.1.1.0","mode":33261,"size":217376,"sha256":"4f484274d8e2f83f4d2fd12386d2aa0b4c823be7c07279c16ad7f1eaca44fbe7"},{"path":"/usr/share/licenses/libsmartcols/COPYING","mode":33188,"size":352,"sha256":"a2dc3d3adff705e225aee932ec4c2ac29ee45221cf7566e7b837a6d0d1442966"},{"path":"/usr/share/licenses/libsmartcols/COPYING.LGPLv2.1","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libsolv","version":"0.7.7-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libsolv:libsolv:0.7.7-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libsolv:0.7.7-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libsolv@0:0.7.7-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libsolv","version":"0.7.7","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"libsolv-0.7.7-1.el8.src.rpm","size":789176,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/ce/2bb7c1d037a888124a749a51ef95a086b96db8","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/e8/16cfd75d65a46a34046e46daee1578d72b844f","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/libsolv.so.1","mode":33261,"size":599096,"sha256":"c7fe02cd176048b3cc8a1f37ff31bf009ca541a37143df79f1bc50440b45edbf"},{"path":"/usr/lib64/libsolvext.so.1","mode":33261,"size":187552,"sha256":"c7a3730158f883b1ec15629d8d1d64799a9425b18aaa22c62287995c9543eb30"},{"path":"/usr/share/licenses/libsolv/LICENSE.BSD","mode":33188,"size":1381,"sha256":"57f15acfb29fbef7749779e096a5885c60b716633e34484a21bb717554c0198f"}]}},{"name":"libstdc++","version":"8.3.1-5.el8.0.2","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libstdc++:libstdc++:8.3.1-5.el8.0.2:*:*:*:*:*:*:*","cpe:2.3:a:*:libstdc++:8.3.1-5.el8.0.2:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libstdc++@0:8.3.1-5.el8.0.2?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libstdc++","version":"8.3.1","epoch":0,"architecture":"x86_64","release":"5.el8.0.2","sourceRpm":"gcc-8.3.1-5.el8.0.2.src.rpm","size":1855607,"license":"GPLv3+ and GPLv3+ with exceptions and GPLv2+ with exceptions and LGPLv2+ and BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/a9/e1e5d8b62b99990587a21e324a2d4b6d58c90c","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libstdc++.so.6","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libstdc++.so.6.0.25","mode":33261,"size":1661312,"sha256":"937c858f739dfc9c45a1510022d6f78beddb5696db74b5f8c9077bfd5d279f0f"},{"path":"/usr/share/gcc-8/python/libstdcxx/__init__.py","mode":33188,"size":1,"sha256":"01ba4719c80b6fe911b091a7c05124b64eeece964e09c058ef8f9805daca546b"},{"path":"/usr/share/gcc-8/python/libstdcxx/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":128,"sha256":"0deba3552ffffa97e65e965b41c89fa5dab0160d509c77e32e36851ebe70558c"},{"path":"/usr/share/gcc-8/python/libstdcxx/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":128,"sha256":"0deba3552ffffa97e65e965b41c89fa5dab0160d509c77e32e36851ebe70558c"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/__init__.py","mode":33188,"size":1161,"sha256":"fc792a50d118d5feb068481d0328f89fe8762b7705011910281bfe65c1170c8f"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":586,"sha256":"c8521a8e6b6b9c079db97ea4425e5302852b3e667c518ca89deea6a20397be71"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":586,"sha256":"c8521a8e6b6b9c079db97ea4425e5302852b3e667c518ca89deea6a20397be71"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/__pycache__/printers.cpython-36.opt-1.pyc","mode":33188,"size":57331,"sha256":"a846ab78027975e6f3a1e8719b181e7814354b978a50b580f2e379bd54b7fc07"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/__pycache__/printers.cpython-36.pyc","mode":33188,"size":57331,"sha256":"a846ab78027975e6f3a1e8719b181e7814354b978a50b580f2e379bd54b7fc07"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/__pycache__/xmethods.cpython-36.opt-1.pyc","mode":33188,"size":36279,"sha256":"c7d0cae4dc1a66081c7efc5e4f6401bedc6fd728d06021bead3e71bef5f30083"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/__pycache__/xmethods.cpython-36.pyc","mode":33188,"size":36279,"sha256":"c7d0cae4dc1a66081c7efc5e4f6401bedc6fd728d06021bead3e71bef5f30083"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/printers.py","mode":33188,"size":67991,"sha256":"1e7e02c740c4cc73e5992d39d0f6e8bcf580dbbf52b65f96d70923db2069e800"},{"path":"/usr/share/gcc-8/python/libstdcxx/v6/xmethods.py","mode":33188,"size":27708,"sha256":"627b1b17ddb0a8314bcad3dfcb045ec59d073e33ea16dda320641b30401114fe"},{"path":"/usr/share/gdb/auto-load/usr/lib64/__pycache__/libstdc++.so.6.0.25-gdb.cpython-36.opt-1.pyc","mode":33188,"size":729,"sha256":"6babf709a72bc393bc6bf40bdb35f3ba7abaacf931e082ccd9d709ddb076c94f"},{"path":"/usr/share/gdb/auto-load/usr/lib64/__pycache__/libstdc++.so.6.0.25-gdb.cpython-36.pyc","mode":33188,"size":729,"sha256":"6babf709a72bc393bc6bf40bdb35f3ba7abaacf931e082ccd9d709ddb076c94f"},{"path":"/usr/share/gdb/auto-load/usr/lib64/libstdc++.so.6.0.25-gdb.py","mode":33188,"size":2381,"sha256":"b1c496792876df431c9441a86cd1cf6035d08a86a8b89f20a70fd4c5f07f98a6"}]}},{"name":"libtasn1","version":"4.13-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libtasn1:libtasn1:4.13-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libtasn1:4.13-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libtasn1@0:4.13-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libtasn1","version":"4.13","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"libtasn1-4.13-3.el8.src.rpm","size":168725,"license":"GPLv3+ and LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/af/ae15c2ea3d81a086a1dbadb6bf9c12d55c3136","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libtasn1.so.6","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libtasn1.so.6.5.5","mode":33261,"size":82248,"sha256":"41874c3257ac33dda6d652b519e899f850002af35cb57fcdc9750481ed31c105"},{"path":"/usr/share/licenses/libtasn1/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/libtasn1/COPYING.LIB","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"libtirpc","version":"1.1.4-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libtirpc:libtirpc:1.1.4-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libtirpc:1.1.4-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libtirpc@0:1.1.4-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libtirpc","version":"1.1.4","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"libtirpc-1.1.4-4.el8.src.rpm","size":381964,"license":"SISSL and BSD","vendor":"CentOS","files":[{"path":"/etc/bindresvport.blacklist","mode":33188,"size":429,"sha256":"3eef9865b1123a43ebe87fec9d9379ff0735fe85fc9c46480c548fcb0ef2fe10"},{"path":"/etc/netconfig","mode":33188,"size":767,"sha256":"86ee43cde79ed4afdbcc697d74fe80cb3d9b261feab550f45beeedfba7ff9fbd"},{"path":"/usr/lib/.build-id/65/02626b8974cc694f43fa0c3d60ba4cbc8e835b","mode":41471,"size":35,"sha256":""}]}},{"name":"libunistring","version":"0.9.9-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libunistring:libunistring:0.9.9-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libunistring:0.9.9-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libunistring@0:0.9.9-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libunistring","version":"0.9.9","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"libunistring-0.9.9-3.el8.src.rpm","size":1855932,"license":"GPLv2+ or LGPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/7e/1bce3df3b14ac08a6290d274b481858d172eb0","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib64/libunistring.so.2","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libunistring.so.2.1.0","mode":33261,"size":1805368,"sha256":"05abdd40665a0f8759c91d19e0e5f4aa437002ab76aa9f9a3a790cdf47a34802"},{"path":"/usr/share/licenses/libunistring/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/libunistring/COPYING.LIB","mode":33188,"size":7639,"sha256":"a853c2ffec17057872340eee242ae4d96cbf2b520ae27d903e1b2fef1a5f9d1c"}]}},{"name":"libusbx","version":"1.0.22-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libusbx:libusbx:1.0.22-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libusbx:1.0.22-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libusbx@0:1.0.22-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libusbx","version":"1.0.22","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"libusbx-1.0.22-1.el8.src.rpm","size":151177,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/12/f65981e3c705eec8a724bc4235fa29cdbec5d3","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libusb-1.0.so.0","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libusb-1.0.so.0.1.0","mode":33261,"size":111496,"sha256":"6b2fb66e3e579bbf8085c60ac29894ee77beb154b804cffe4949c4e1ae21f9c2"},{"path":"/usr/share/licenses/libusbx/COPYING","mode":33188,"size":26436,"sha256":"5df07007198989c622f5d41de8d703e7bef3d0e79d62e24332ee739a452af62a"}]}},{"name":"libutempter","version":"1.1.6-14.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libutempter:libutempter:1.1.6-14.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libutempter:1.1.6-14.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libutempter@0:1.1.6-14.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libutempter","version":"1.1.6","epoch":0,"architecture":"x86_64","release":"14.el8","sourceRpm":"libutempter-1.1.6-14.el8.src.rpm","size":52637,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/26/9d01d036b36ab49aa23450dba3d5ea44967026","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/26/d2f5195167325934805bf52d8f702412239100","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libutempter.so.0","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib64/libutempter.so.1.1.6","mode":33261,"size":12120,"sha256":"88f4e7a82a5e9db831cc7a988f29c74a03136493c5ccdcfdbd43576b0742f7ec"},{"path":"/usr/libexec/utempter/utempter","mode":34249,"size":13344,"sha256":"71b75ae9c4973e96840956e8decf8e138afaa101ce73690cac317a942837a139"},{"path":"/usr/share/licenses/libutempter/COPYING","mode":33188,"size":26527,"sha256":"a9bdde5616ecdd1e980b44f360600ee8783b1f99b8cc83a2beb163a0a390e861"}]}},{"name":"libuuid","version":"2.32.1-22.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libuuid:libuuid:2.32.1-22.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libuuid:2.32.1-22.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libuuid@0:2.32.1-22.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libuuid","version":"2.32.1","epoch":0,"architecture":"x86_64","release":"22.el8","sourceRpm":"util-linux-2.32.1-22.el8.src.rpm","size":34832,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/0e/0e46c3549e4442dcb719ff47db40bf92b7626f","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libuuid.so.1","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libuuid.so.1.3.0","mode":33261,"size":33224,"sha256":"6dfecb825561f6e7fed1dc65fe46b5fb5820c3b109b718ad2aa2e1f4fcfcdbe6"},{"path":"/usr/share/licenses/libuuid/COPYING","mode":33188,"size":217,"sha256":"f051c5b2e7ed25acac4b79d22b9e5df80447c16f9ec543d6ed21c213c576f6aa"},{"path":"/usr/share/licenses/libuuid/COPYING.BSD-3","mode":33188,"size":1391,"sha256":"9b718a9460fed5952466421235bc79eb49d4e9eacc920d7a9dd6285ab8fd6c6d"}]}},{"name":"libverto","version":"0.3.0-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libverto:libverto:0.3.0-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libverto:0.3.0-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libverto@0:0.3.0-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libverto","version":"0.3.0","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"libverto-0.3.0-5.el8.src.rpm","size":28244,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/c1/cd50cbe655e131c6742cc1b459417d20910f5c","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libverto.so.1","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libverto.so.1.0.0","mode":33261,"size":25040,"sha256":"ff518bfc1d08bb9ed31db49f4d8f59f63d301e462e50c54f503198feb6b64ecf"},{"path":"/usr/share/licenses/libverto/COPYING","mode":33188,"size":1054,"sha256":"ee2f49235ed5947ace182dcb3aba92655aeafab4f3a33c98a9c6d75a6a238480"}]}},{"name":"libxcrypt","version":"4.1.1-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libxcrypt:libxcrypt:4.1.1-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libxcrypt:4.1.1-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libxcrypt@0:4.1.1-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libxcrypt","version":"4.1.1","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"libxcrypt-4.1.1-4.el8.src.rpm","size":194420,"license":"LGPLv2+ and BSD and Public Domain","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/a3/baf007ac157d196f2d24cd74f2a0d83456a34d","mode":41471,"size":35,"sha256":""},{"path":"/usr/share/licenses/libxcrypt/AUTHORS","mode":33188,"size":1682,"sha256":"46cfa431806b5fce8e9ea2736b1f4bbaa2a5f2048f18a3515a9e1f3925a83a2d"},{"path":"/usr/share/licenses/libxcrypt/COPYING.LIB","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"},{"path":"/usr/share/licenses/libxcrypt/LICENSING","mode":33188,"size":3015,"sha256":"eaa47c6ebef90e3180e24f1a2c4086a925bdea8159f97998a9ad7c8f6d336d98"}]}},{"name":"libxml2","version":"2.9.7-7.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libxml2:libxml2:2.9.7-7.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libxml2:2.9.7-7.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libxml2@0:2.9.7-7.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libxml2","version":"2.9.7","epoch":0,"architecture":"x86_64","release":"7.el8","sourceRpm":"libxml2-2.9.7-7.el8.src.rpm","size":1752506,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/bin/xmlcatalog","mode":33261,"size":20656,"sha256":"2a944a7b0422ba508a228dc54a93f32adecaf3db9925fa7cd13592d6c492f9c5"},{"path":"/usr/bin/xmllint","mode":33261,"size":75096,"sha256":"12a12be6d5826796b5bcee5b523df2429a4296187241711d4da45399936e5e09"},{"path":"/usr/lib/.build-id/76/7cc6752131b8b445df9b6e67744a9033cf1d61","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/e2/bab7a9bbb404924c9c222b53f9dfad439d272c","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/fd/2eb8de1103bf22afc90278811eb9f4c63e05c6","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib64/libxml2.so.2","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libxml2.so.2.9.7","mode":33261,"size":1503104,"sha256":"487cece4ce4b3e1356d28a7ba958cb2ca42b78ff0745d6d3f48323282261868d"},{"path":"/usr/share/licenses/libxml2/Copyright","mode":33188,"size":1289,"sha256":"c5c63674f8a83c4d2e385d96d1c670a03cb871ba2927755467017317878574bd"}]}},{"name":"libyaml","version":"0.1.7-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libyaml:libyaml:0.1.7-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libyaml:0.1.7-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libyaml@0:0.1.7-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libyaml","version":"0.1.7","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"libyaml-0.1.7-5.el8.src.rpm","size":136478,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/19/086a9628216954b47992cf8a0141847303ce29","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib64/libyaml-0.so.2","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libyaml-0.so.2.0.5","mode":33261,"size":134584,"sha256":"40b3dddf38b4bf7ded16644bd0e37d23aa71205dc4e9dec1509073c10cd6a46b"},{"path":"/usr/share/licenses/libyaml/LICENSE","mode":33188,"size":1058,"sha256":"d0d8b09800a45cd982e9568fc7669d9c1a4c330e275a821bbe24d54366d16fe9"}]}},{"name":"libzstd","version":"1.4.2-2.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:libzstd:libzstd:1.4.2-2.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:libzstd:1.4.2-2.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/libzstd@0:1.4.2-2.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"libzstd","version":"1.4.2","epoch":0,"architecture":"x86_64","release":"2.el8","sourceRpm":"zstd-1.4.2-2.el8.src.rpm","size":703765,"license":"BSD and GPLv2","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/27/284500db25e4d2bcb3f40100e03886649eb4dc","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libzstd.so.1","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libzstd.so.1.4.2","mode":33261,"size":684144,"sha256":"0f47bf33f7eca299d91b12a1783e449fbea8b39c453b31203eff33aef55a9abc"},{"path":"/usr/share/licenses/libzstd/COPYING","mode":33188,"size":18091,"sha256":"f9c375a1be4a41f7b70301dd83c91cb89e41567478859b77eef375a52d782505"},{"path":"/usr/share/licenses/libzstd/LICENSE","mode":33188,"size":1530,"sha256":"2c1a7fa704df8f3a606f6fc010b8b5aaebf403f3aeec339a12048f1ba7331a0b"}]}},{"name":"lua-libs","version":"5.3.4-11.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:lua-libs:lua-libs:5.3.4-11.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:lua-libs:5.3.4-11.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/lua-libs@0:5.3.4-11.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"lua-libs","version":"5.3.4","epoch":0,"architecture":"x86_64","release":"11.el8","sourceRpm":"lua-5.3.4-11.el8.src.rpm","size":351728,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/7e/f1d3025756582831343d5fb7bb38ba0f7beb0b","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib64/liblua-5.3.so","mode":33261,"size":351728,"sha256":"90abdb0d90b21113226289f90ecb33b33559d785d1d10e2a5493d18a9c2d9f02"}]}},{"name":"lz4-libs","version":"1.8.1.2-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:lz4-libs:lz4-libs:1.8.1.2-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:lz4-libs:1.8.1.2-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/lz4-libs@0:1.8.1.2-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"lz4-libs","version":"1.8.1.2","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"lz4-1.8.1.2-4.el8.src.rpm","size":97367,"license":"GPLv2+ and BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/17/b7630f730b89b9a74f587b5f97d1d1033cc473","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/liblz4.so.1","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/liblz4.so.1.8.1","mode":33261,"size":96056,"sha256":"0b7edeb33f7d285159d11b0a3f3d9dc59ef2f05e3bc08a1c486b6fdb91e90d8e"}]}},{"name":"lzo","version":"2.08-14.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:lzo:lzo:2.08-14.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:lzo:2.08-14.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/lzo@0:2.08-14.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"lzo","version":"2.08","epoch":0,"architecture":"x86_64","release":"14.el8","sourceRpm":"lzo-2.08-14.el8.src.rpm","size":198757,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/4d/e08a272aca34817d8bfe88ccd9223415a7a599","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/liblzo2.so.2","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/liblzo2.so.2.0.0","mode":33261,"size":167584,"sha256":"c67ce7e96089af7390f3228c4922adcb88fa7fb5b81899b02126497a46374540"},{"path":"/usr/share/licenses/lzo/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"mpfr","version":"3.1.6-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:mpfr:mpfr:3.1.6-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:mpfr:3.1.6-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/mpfr@0:3.1.6-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"mpfr","version":"3.1.6","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"mpfr-3.1.6-1.el8.src.rpm","size":612625,"license":"LGPLv3+ and GPLv3+ and GFDL","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/86/a54225590697a85c95d7aec38fa8026fda3dc9","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libmpfr.so.4","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libmpfr.so.4.1.6","mode":33261,"size":504672,"sha256":"b7fafdf827a7ffc23e958f461d88f7cf92f198f2e23074e9a790f86458146b7d"},{"path":"/usr/share/licenses/mpfr/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/mpfr/COPYING.LESSER","mode":33188,"size":7639,"sha256":"a853c2ffec17057872340eee242ae4d96cbf2b520ae27d903e1b2fef1a5f9d1c"}]}},{"name":"ncurses-base","version":"6.1-7.20180224.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:ncurses-base:ncurses-base:6.1-7.20180224.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:ncurses-base:6.1-7.20180224.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/ncurses-base@0:6.1-7.20180224.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"ncurses-base","version":"6.1","epoch":0,"architecture":"noarch","release":"7.20180224.el8","sourceRpm":"ncurses-6.1-7.20180224.el8.src.rpm","size":290089,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/share/licenses/ncurses-base/COPYING","mode":33188,"size":1408,"sha256":"86106f0da1cf5ccfa0f0651665dd1b4515e8edad1c7972780155770548b317d9"},{"path":"/usr/share/tabset/std","mode":33188,"size":135,"sha256":"fbadb5f608b355fe481c0c7d9c6265b2372bfa35250662f81f68d46540080770"},{"path":"/usr/share/tabset/stdcrt","mode":33188,"size":95,"sha256":"cf6c37b18ceea7c306f7e3a5e604a03b0dfb9c22ec99163e4b52f885ce063145"},{"path":"/usr/share/tabset/vt100","mode":33188,"size":160,"sha256":"075251754239d9973945d82b95c18cd90997acd2017393e70c8832e9297de056"},{"path":"/usr/share/tabset/vt300","mode":33188,"size":64,"sha256":"61f8388cad6a381feb819bc6a8d299d06a853d15e1f4bfdfd6b6f40069ad4956"},{"path":"/usr/share/terminfo/A/Apple_Terminal","mode":33188,"size":2473,"sha256":"6bf12fa8e2596f3c60d54d74f8dcf8f1630baa174654136899b819d908bdbad8"},{"path":"/usr/share/terminfo/E/Eterm","mode":33188,"size":2281,"sha256":"ec895a5f98e5f7f9b6be082689f7d81bc627c71dc826e30ac4f4276d9fd0df47"},{"path":"/usr/share/terminfo/E/Eterm-256color","mode":33188,"size":2521,"sha256":"c5d5b1a94ae7f5dd893f8e7b3aea83e791fbfe0f5032f03ad7da2eceb48c3529"},{"path":"/usr/share/terminfo/E/Eterm-88color","mode":33188,"size":2451,"sha256":"7f5508b34629f9757d8b8f72e19c1f2307c2d3e3c258f08a1ee0dd63d55a856c"},{"path":"/usr/share/terminfo/E/Eterm-color","mode":33188,"size":2281,"sha256":"ec895a5f98e5f7f9b6be082689f7d81bc627c71dc826e30ac4f4276d9fd0df47"},{"path":"/usr/share/terminfo/a/ansi","mode":33188,"size":1481,"sha256":"93ec8cb9beb0c898ebc7dda0f670de31addb605be9005735228680d592cff657"},{"path":"/usr/share/terminfo/a/ansi80x25","mode":33188,"size":1502,"sha256":"acd69b88fbc9045037b562dd67c876e88cc5d2616af20b9ca6c41d33ee335606"},{"path":"/usr/share/terminfo/a/ansis","mode":33188,"size":1502,"sha256":"acd69b88fbc9045037b562dd67c876e88cc5d2616af20b9ca6c41d33ee335606"},{"path":"/usr/share/terminfo/a/aterm","mode":33188,"size":2217,"sha256":"ba3149ceecc4682a8b9b62171939b869c2e8e0601942a642922f4b64cc0b5411"},{"path":"/usr/share/terminfo/b/bterm","mode":33188,"size":1155,"sha256":"b5166019760429c4d6150180f1c2dd81136488e21c36b564e605c9dc7366f1db"},{"path":"/usr/share/terminfo/c/cons25","mode":33188,"size":1502,"sha256":"acd69b88fbc9045037b562dd67c876e88cc5d2616af20b9ca6c41d33ee335606"},{"path":"/usr/share/terminfo/c/cygwin","mode":33188,"size":1518,"sha256":"3e04bfdcc0764f4e28655701864845752cd3f77d0c52390637ebe588f91665cf"},{"path":"/usr/share/terminfo/d/dumb","mode":33188,"size":308,"sha256":"123c85a2812a517d967db5f31660db0e6aded4a0b95ed943c5ab435368e7a25c"},{"path":"/usr/share/terminfo/e/eterm","mode":33188,"size":842,"sha256":"c79a54efd731abe696b0373d814c9a67839eb74229cb0f63ec436b43871b8a2a"},{"path":"/usr/share/terminfo/e/eterm-color","mode":33188,"size":1249,"sha256":"718af703c538849e5b13ca124dc0416a60e05f1eed5208f6d72836c51c108f31"},{"path":"/usr/share/terminfo/g/gnome","mode":33188,"size":3215,"sha256":"e6d9c90d328d11542f2f28c05a33977fb822a5d72b51456d8b7e4091f37676c0"},{"path":"/usr/share/terminfo/g/gnome-256color","mode":33188,"size":3619,"sha256":"8e7026ff5f02e68ea5bf7377a659215a21fbb70ebe3dc2908b4946938746db0c"},{"path":"/usr/share/terminfo/h/hurd","mode":33188,"size":1893,"sha256":"ea3517cda1607f3c65f58a746c524bced0a32aa3840e5751cdde267f15c07748"},{"path":"/usr/share/terminfo/j/jfbterm","mode":33188,"size":1710,"sha256":"c238f6378992e34dc9eef03f52b6efeb6b6d37a5042d4f1a5a1334b40e367735"},{"path":"/usr/share/terminfo/k/kon","mode":33188,"size":1710,"sha256":"c238f6378992e34dc9eef03f52b6efeb6b6d37a5042d4f1a5a1334b40e367735"},{"path":"/usr/share/terminfo/k/kon2","mode":33188,"size":1710,"sha256":"c238f6378992e34dc9eef03f52b6efeb6b6d37a5042d4f1a5a1334b40e367735"},{"path":"/usr/share/terminfo/k/konsole","mode":33188,"size":3147,"sha256":"d54737abe9927dd7447b70d33a15a895339e796296fb6eabb53a5cdf95e28511"},{"path":"/usr/share/terminfo/k/konsole-256color","mode":33188,"size":3357,"sha256":"8fb0d289deddb27a2f6e253527798d38a2e952fa4e293188e268aeffd6d271f7"},{"path":"/usr/share/terminfo/l/linux","mode":33188,"size":1822,"sha256":"4beebb2d5615856487c4a46d826c70c27b590ffc849744c1a06056ba2ba757a7"},{"path":"/usr/share/terminfo/m/mach","mode":33188,"size":617,"sha256":"ecd31c58040e5908eb434514e67620b2e4be538655126f427155760b273c7e9b"},{"path":"/usr/share/terminfo/m/mach-bold","mode":33188,"size":652,"sha256":"4e4400e3ad4df2dbbf90920860c540cd72552ca71a24b556a0b6ba62fa091b84"},{"path":"/usr/share/terminfo/m/mach-color","mode":33188,"size":1095,"sha256":"5caa825bd606e26c8b6c55a3206eccfea525e788f74da5e7cb48cc713db52239"},{"path":"/usr/share/terminfo/m/mach-gnu","mode":33188,"size":1056,"sha256":"99372cd399478be723230692595362004df345dee6c4145e4d109113a2357717"},{"path":"/usr/share/terminfo/m/mach-gnu-color","mode":33188,"size":1318,"sha256":"e1c62541670d0e10fe46daabce8ce95d9fd77115a68106e5eb2c2a7647e40a13"},{"path":"/usr/share/terminfo/m/mlterm","mode":33188,"size":3110,"sha256":"84a72b515c64b2594914b7b90b082300467b3c815f4223b2dcaef789e4e46ed2"},{"path":"/usr/share/terminfo/m/mrxvt","mode":33188,"size":3144,"sha256":"d9ccb1774f5631d96af45db221fc6efb370d8ddc49baecd7bb217bab20573a32"},{"path":"/usr/share/terminfo/n/nsterm","mode":33188,"size":2473,"sha256":"6bf12fa8e2596f3c60d54d74f8dcf8f1630baa174654136899b819d908bdbad8"},{"path":"/usr/share/terminfo/n/nxterm","mode":33188,"size":1551,"sha256":"f74fe619914bfe650f6071bbbaf242c439de8a2f0ecefe9e80870216dfb844b4"},{"path":"/usr/share/terminfo/p/pcansi","mode":33188,"size":1198,"sha256":"ecda9662049c96ee0a574f40cfb8950b0198b508b5b72a3de05774eb3cb3f34e"},{"path":"/usr/share/terminfo/p/putty","mode":33188,"size":2460,"sha256":"9ae6e78233c431b1420f2decb2366bbd7aeca8a2114fe8fc8039cb5a0ab0d866"},{"path":"/usr/share/terminfo/p/putty-256color","mode":33188,"size":2686,"sha256":"c4cac29cfa971a3ec4fabc789acb49d6abe64de8ba5c27e756d6d63c1dc84bf4"},{"path":"/usr/share/terminfo/r/rxvt","mode":33188,"size":2307,"sha256":"f33c1aa275fe5817678b61898573754d6b855607c291afe2f6795441097a6a3f"},{"path":"/usr/share/terminfo/r/rxvt-16color","mode":33188,"size":2519,"sha256":"ab1a4668a6ffd1b4b01d4ef3a38e2f3cace3d40c1f1b60bdb7e1c2287d20c596"},{"path":"/usr/share/terminfo/r/rxvt-256color","mode":33188,"size":2485,"sha256":"bca06510856fe184904c21410b0c63c16972de9bdeb99c3e3c9299191878230e"},{"path":"/usr/share/terminfo/r/rxvt-88color","mode":33188,"size":2453,"sha256":"091b08cab321b22dcee7aa80362e541122164716b9830874950b6b8c8ba6a7c4"},{"path":"/usr/share/terminfo/r/rxvt-basic","mode":33188,"size":2167,"sha256":"f62895c1844a812f25561b9d02cdf125ade487bf92a60bcc00e2c66cfc08b794"},{"path":"/usr/share/terminfo/r/rxvt-color","mode":33188,"size":2251,"sha256":"2a4642610d94fb16e2d0ba2d04b72e395814bc25744b5f269ff3f28893e64df0"},{"path":"/usr/share/terminfo/r/rxvt-cygwin","mode":33188,"size":2273,"sha256":"7a6f37c37d18a8dcddaf2d1ff64d42423ae6177272d8e64e201e216c240c449c"},{"path":"/usr/share/terminfo/r/rxvt-cygwin-native","mode":33188,"size":2291,"sha256":"0660c542f166cae23a7218f75123180e6ad8d5acbd342068314c91964cd4390e"},{"path":"/usr/share/terminfo/r/rxvt-unicode","mode":33188,"size":2208,"sha256":"063264a85fd735a13028390c8d43cf38b5214417c6e48908eabb85bcdb9b7495"},{"path":"/usr/share/terminfo/r/rxvt-xpm","mode":33188,"size":2249,"sha256":"e0d7ec933ce140fb9548664083bbab6604593b6fa1ba1dd6eb0a91dd795c9396"},{"path":"/usr/share/terminfo/s/screen","mode":33188,"size":1653,"sha256":"60df1fc3f6346efdd64e6971b36e98bc35e2a175c0d4420e7fd22c5d0853c112"},{"path":"/usr/share/terminfo/s/screen-16color","mode":33188,"size":2071,"sha256":"953590d73e211177f772e560bc41484de24a72459a741b3581db3c742e4d71f1"},{"path":"/usr/share/terminfo/s/screen-256color","mode":33188,"size":1995,"sha256":"868cdd7aeeb7201aa33883296d596d149f55002625a671876da65ce2f6a3b290"},{"path":"/usr/share/terminfo/s/screen.Eterm","mode":33188,"size":2323,"sha256":"0b940c1dbb17acdf27e5acb65f99e680da847619eb902e0a225b14b120971ed1"},{"path":"/usr/share/terminfo/s/screen.gnome","mode":33188,"size":3287,"sha256":"4f7a5ad8721bd29977845ecc018cccd81ea6916842977509e1dfb370cd468c41"},{"path":"/usr/share/terminfo/s/screen.konsole","mode":33188,"size":3271,"sha256":"7294a74cee3704e30d342c4208a863df0cf7efe83f0141ba1c5fd3768760155a"},{"path":"/usr/share/terminfo/s/screen.konsole-256color","mode":33188,"size":3454,"sha256":"a5ac0409c4cd8c518f267a5a48bcdc82f3b7f137dc97f448837a63153d330236"},{"path":"/usr/share/terminfo/s/screen.linux","mode":33188,"size":1867,"sha256":"0da28a0c084ef373054cf43aa4d4899636ff40b812bb8d66e325f2d0c30ceef5"},{"path":"/usr/share/terminfo/s/screen.mlterm","mode":33188,"size":3104,"sha256":"b5c44865b01a0ef5375430bff581ced25e0c39bd8babbbafbbe16fa6ae396c89"},{"path":"/usr/share/terminfo/s/screen.mlterm-256color","mode":33188,"size":3297,"sha256":"4d948d3366566dd82ddbf1db563f22e987c44b6add1536723b97691a39b57e27"},{"path":"/usr/share/terminfo/s/screen.mrxvt","mode":33188,"size":3222,"sha256":"1055b1ae17f86dc7e658fb34613d8f9a4e845e49365c35d3a6053f8951c0d9b1"},{"path":"/usr/share/terminfo/s/screen.putty","mode":33188,"size":2750,"sha256":"d1d4e5abe3e72dcb4239a18763dd5e55b98c95b4fe2a21c0edee963e3297184b"},{"path":"/usr/share/terminfo/s/screen.putty-256color","mode":33188,"size":2860,"sha256":"32ea43f836ec63b2bd11f86d7a42f3ce858beba03f1b28eb6581618dadb52f79"},{"path":"/usr/share/terminfo/s/screen.rxvt","mode":33188,"size":2247,"sha256":"56c9d69c6d47692e303fe4d96181076162910cf74cefe89437ead6f26c408c3d"},{"path":"/usr/share/terminfo/s/screen.teraterm","mode":33188,"size":1727,"sha256":"725d4c2a9c80bed343cb48aadc13aabc855b5aa1a573c9a54bae2dc529a9c5e2"},{"path":"/usr/share/terminfo/s/screen.vte","mode":33188,"size":3360,"sha256":"0e339b3d65c23a066ac9d8d7d3afaf266feb11dab2d042406a3ec45873eebba2"},{"path":"/usr/share/terminfo/s/screen.vte-256color","mode":33188,"size":3514,"sha256":"e69bfa913b17f9fff3ead0289fbed657a21c21e4de4a4d9eb8edaf70754db8ed"},{"path":"/usr/share/terminfo/s/screen.xterm-256color","mode":33188,"size":3459,"sha256":"63e5331cd64a5211a4ed476452a2654d77825c2449d989cf2e6e8a7889fc8aa8"},{"path":"/usr/share/terminfo/s/screen.xterm-new","mode":33188,"size":3575,"sha256":"0215182a3f8a0ec27209799f21befa88a3f588fdb5663edcd9148e065ceb7ae3"},{"path":"/usr/share/terminfo/s/screen.xterm-r6","mode":33188,"size":1668,"sha256":"ecd3c79d5dc9301f0472af6a58ff9319275091556bbcaaa7d4b79833ac2f9dd1"},{"path":"/usr/share/terminfo/s/screen.xterm-xfree86","mode":33188,"size":3575,"sha256":"0215182a3f8a0ec27209799f21befa88a3f588fdb5663edcd9148e065ceb7ae3"},{"path":"/usr/share/terminfo/s/st","mode":33188,"size":2949,"sha256":"6c9514d660232ea443e619ab3ab6dfb9fea10b19bdd168a3da112db01001136c"},{"path":"/usr/share/terminfo/s/st-16color","mode":33188,"size":3343,"sha256":"f029dc0aa4a8e755ae1673dd1cb11ae4af30789c0d27f5015fe7d008b22d8159"},{"path":"/usr/share/terminfo/s/st-256color","mode":33188,"size":3111,"sha256":"7ae4cbb8a2784c2e95cd166b635878dfb4e53471afa32723d4186cb5343702c1"},{"path":"/usr/share/terminfo/s/stterm","mode":33188,"size":2949,"sha256":"6c9514d660232ea443e619ab3ab6dfb9fea10b19bdd168a3da112db01001136c"},{"path":"/usr/share/terminfo/s/stterm-16color","mode":33188,"size":3343,"sha256":"f029dc0aa4a8e755ae1673dd1cb11ae4af30789c0d27f5015fe7d008b22d8159"},{"path":"/usr/share/terminfo/s/stterm-256color","mode":33188,"size":3111,"sha256":"7ae4cbb8a2784c2e95cd166b635878dfb4e53471afa32723d4186cb5343702c1"},{"path":"/usr/share/terminfo/s/sun","mode":33188,"size":1004,"sha256":"02e392161cb23f49a8fb1ba2f1a6583e013c0c26672f58c5eaca828db3b19914"},{"path":"/usr/share/terminfo/s/sun1","mode":33188,"size":1004,"sha256":"02e392161cb23f49a8fb1ba2f1a6583e013c0c26672f58c5eaca828db3b19914"},{"path":"/usr/share/terminfo/s/sun2","mode":33188,"size":1004,"sha256":"02e392161cb23f49a8fb1ba2f1a6583e013c0c26672f58c5eaca828db3b19914"},{"path":"/usr/share/terminfo/t/teraterm","mode":33188,"size":1701,"sha256":"75be3c4134fb55cb4b90e82eb97a7cc1cf346015a1afd723f48171862250e748"},{"path":"/usr/share/terminfo/t/teraterm2.3","mode":33188,"size":1592,"sha256":"6598b360cd87b5c3e3f99a5b0b4d462c59e754bad79968febc84c77b7acc3bdc"},{"path":"/usr/share/terminfo/t/tmux","mode":33188,"size":3153,"sha256":"fe430822d0555eaadfd3748d7a56e78d60b42cd51a0cc492b8b918d55212ed12"},{"path":"/usr/share/terminfo/t/tmux-256color","mode":33188,"size":3295,"sha256":"3e23bb2e0eda229c32ffe3b9ea54c11919a01d539ca4d94650349c3da2e2ac48"},{"path":"/usr/share/terminfo/v/vs100","mode":33188,"size":1525,"sha256":"2b1249158a7053eee58242625f79b29f35da721cbcf695a327521cfed3bec117"},{"path":"/usr/share/terminfo/v/vt100","mode":33188,"size":1190,"sha256":"44fe1bfcc36f3a7669a387b623a44c360f9e150868f9924920182b44bcbbdba6"},{"path":"/usr/share/terminfo/v/vt100-am","mode":33188,"size":1190,"sha256":"44fe1bfcc36f3a7669a387b623a44c360f9e150868f9924920182b44bcbbdba6"},{"path":"/usr/share/terminfo/v/vt100-nav","mode":33188,"size":1055,"sha256":"e509a4ee7373ff884ef9b5b293fdffa88182711d6b0448fe99d2cbeb1939114a"},{"path":"/usr/share/terminfo/v/vt102","mode":33188,"size":1184,"sha256":"60e451f57c0308b79004ebc6189b49417b4ac11d783154072cae803a11af7d3f"},{"path":"/usr/share/terminfo/v/vt200","mode":33188,"size":1377,"sha256":"75a4723bfcdcd22756366838f1d65233f386d7592b019740c8ca5b578e9a5857"},{"path":"/usr/share/terminfo/v/vt220","mode":33188,"size":1377,"sha256":"75a4723bfcdcd22756366838f1d65233f386d7592b019740c8ca5b578e9a5857"},{"path":"/usr/share/terminfo/v/vt52","mode":33188,"size":470,"sha256":"1d8e7d40be89fe71e5d2582caa5168fe53ed85d9063e0ccf42e5c53f4d17b069"},{"path":"/usr/share/terminfo/v/vte","mode":33188,"size":3355,"sha256":"8cb5a672dedd365d4831f11fbafedf0f803e70e7bb4dea69d9aa371027b6cd72"},{"path":"/usr/share/terminfo/v/vte-256color","mode":33188,"size":3607,"sha256":"0462f44fd6f4e5ac720e9e315bad30d6236716dbf31bd083fb619444ce56e3aa"},{"path":"/usr/share/terminfo/v/vwmterm","mode":33188,"size":1302,"sha256":"eae3fe39004992478d09bdb5063c6609f8c6f5119053de8fca645002b993b535"},{"path":"/usr/share/terminfo/w/wsvt25","mode":33188,"size":1597,"sha256":"28d3410e6b83a3b78a41f108098ac8772a3af3ee2b627b9f9bb4b19b363a5be3"},{"path":"/usr/share/terminfo/w/wsvt25m","mode":33188,"size":1607,"sha256":"18c85db3b0ef0ab15b7eb8dc4ac6ea14a37d851628220c8bb61e2edfa4f81683"},{"path":"/usr/share/terminfo/x/xfce","mode":33188,"size":3128,"sha256":"3dd1f7ed31697af67aaeb0c5efc724298d1a92e76bbc406fa17f98c927533da3"},{"path":"/usr/share/terminfo/x/xterm","mode":33188,"size":3617,"sha256":"1e56cd2b185047fd1fda6eacf067d1d85191463f1da4b1bf2128e17fe609815f"},{"path":"/usr/share/terminfo/x/xterm-1002","mode":33188,"size":3598,"sha256":"3f8873764e44acb8d47cb743ad4203584698f3dfc71cbbeb70da2dbff5d5c4be"},{"path":"/usr/share/terminfo/x/xterm-1003","mode":33188,"size":3596,"sha256":"2ae6ccb1c3c7af51aa8a24924bb87974e90b6559dd0ed057c42ae7cffd2ff840"},{"path":"/usr/share/terminfo/x/xterm-1005","mode":33188,"size":3613,"sha256":"db3f585af9406e3f119d2708ebe8381c465b17e827d668825901e65335613543"},{"path":"/usr/share/terminfo/x/xterm-1006","mode":33188,"size":3597,"sha256":"977ff286ea5a88afbd8998a74d04146288e3011d901314260fd54bff3497b2fa"},{"path":"/usr/share/terminfo/x/xterm-16color","mode":33188,"size":3857,"sha256":"b6b95048b459156682b6a3212ce0d4f099c87a54882e8c876530004d3ca69819"},{"path":"/usr/share/terminfo/x/xterm-24","mode":33188,"size":1525,"sha256":"2b1249158a7053eee58242625f79b29f35da721cbcf695a327521cfed3bec117"},{"path":"/usr/share/terminfo/x/xterm-256color","mode":33188,"size":3713,"sha256":"7620aabd7be3a33a75e4817db17f6714bcf2a5336c6c6c51b12c2ee43e74c100"},{"path":"/usr/share/terminfo/x/xterm-88color","mode":33188,"size":3679,"sha256":"6d0a051181c07ddf0442f542375ac67d86eb7c0aaa0fe919361a1bce09974123"},{"path":"/usr/share/terminfo/x/xterm-8bit","mode":33188,"size":1991,"sha256":"5956361073c012c553c68a0089065a44d0c7e950df02114e6520f815f419aa82"},{"path":"/usr/share/terminfo/x/xterm-basic","mode":33188,"size":2205,"sha256":"a9a35b70ee5a50c27637598f84d206ed9bfe4e66550ff863e0115e548ae0b3fb"},{"path":"/usr/share/terminfo/x/xterm-bold","mode":33188,"size":1592,"sha256":"4296a878469b6bc5bab5acbce875e43bc501ab57a62d8d29cd34a424ba1e9de4"},{"path":"/usr/share/terminfo/x/xterm-color","mode":33188,"size":1551,"sha256":"f74fe619914bfe650f6071bbbaf242c439de8a2f0ecefe9e80870216dfb844b4"},{"path":"/usr/share/terminfo/x/xterm-direct","mode":33188,"size":3661,"sha256":"3519edd987899e953931c7907e0342d2392a3383ffddd6eef7b632ff59516cca"},{"path":"/usr/share/terminfo/x/xterm-direct2","mode":33188,"size":3651,"sha256":"9316fced488ee2277fbb281a302362b3c82a6c414954037cbe6c2d2ff3e65aa8"},{"path":"/usr/share/terminfo/x/xterm-hp","mode":33188,"size":2251,"sha256":"c1fb479583d422e6046b35302f944962b98e409161f4d13806aed6c79b9b5da7"},{"path":"/usr/share/terminfo/x/xterm-new","mode":33188,"size":3611,"sha256":"9044f070e173876a4914cc4fb965a2832fcdb18abee1d82bae5df29f4d6745f0"},{"path":"/usr/share/terminfo/x/xterm-nic","mode":33188,"size":3627,"sha256":"18e365928ffb140aae9e86bc4f758a9bd603237a74e41185d5147579a65fd601"},{"path":"/usr/share/terminfo/x/xterm-noapp","mode":33188,"size":3573,"sha256":"43673e62c97d99d9ba1ae13e2742eee3cd1f94c1447a98f6daefc14b4d2dfb2f"},{"path":"/usr/share/terminfo/x/xterm-old","mode":33188,"size":1493,"sha256":"927b8821c947b96b020ca7341dffb57bdfa2986fcaecd5fdbf2ca2369eacc285"},{"path":"/usr/share/terminfo/x/xterm-pcolor","mode":33188,"size":1736,"sha256":"8e26c29e1e306f010b464dacc578ca179943ff3717e43af3d566bad24d74dc10"},{"path":"/usr/share/terminfo/x/xterm-r5","mode":33188,"size":1301,"sha256":"82098ec067be6189e91e8264278bb85fe3b7bfdeaa3754be301313be140522ca"},{"path":"/usr/share/terminfo/x/xterm-r6","mode":33188,"size":1491,"sha256":"ee12fe6d2d8e1d0b83d1042fe8a38f1aed6fd73e2c7316e6db5ec5b061b09ef8"},{"path":"/usr/share/terminfo/x/xterm-sco","mode":33188,"size":2427,"sha256":"7b263571d8faea2decc93c9544d318bad2575287c0435172d4d7b427da97fb0b"},{"path":"/usr/share/terminfo/x/xterm-sun","mode":33188,"size":2511,"sha256":"59ff2e4c54bdd7c06e8f14fcd5c7dd2687560f6a251e00af47f90cd3a25f69b6"},{"path":"/usr/share/terminfo/x/xterm-utf8","mode":33188,"size":3627,"sha256":"1dbcda3b0020deb52bdbbc2103499422c7a25e1527cf17445ccf7b08b1eb2241"},{"path":"/usr/share/terminfo/x/xterm-vt220","mode":33188,"size":2389,"sha256":"99afd4451a07b57527fa44c0e08a4543d151464a26fc4d9326116373f33c8e3b"},{"path":"/usr/share/terminfo/x/xterm-vt52","mode":33188,"size":484,"sha256":"ec2164504f16ace2ce5d17b1f07a655029767148dc5f58d388853454aeb47a6d"},{"path":"/usr/share/terminfo/x/xterm-x10mouse","mode":33188,"size":3595,"sha256":"528494945a2e0934b9ce68e94e95853ba0d1a83f0b48f53139da212dfabcda68"},{"path":"/usr/share/terminfo/x/xterm-x11hilite","mode":33188,"size":3620,"sha256":"b7af246ba47b100afcabb3dee7cc52c1686ee2127becd73d952823e410fe58e7"},{"path":"/usr/share/terminfo/x/xterm-x11mouse","mode":33188,"size":3604,"sha256":"dbda39a53519d0aea9524d658e6bfd6a7337a83b30d2539c6f31d2667a8a3e17"},{"path":"/usr/share/terminfo/x/xterm-xf86-v32","mode":33188,"size":2040,"sha256":"815040ec1c43c48641c930d6efd596dd3ffedb858c092d204db7d679dedca047"},{"path":"/usr/share/terminfo/x/xterm-xf86-v33","mode":33188,"size":2030,"sha256":"3cd4e00bb8394ae485e6e19d3f79fda189ad180d6c30f67ea9f854dd220c39b9"},{"path":"/usr/share/terminfo/x/xterm-xf86-v333","mode":33188,"size":2040,"sha256":"d76ac338322b93169c4f1be085e0a28ac2de5c70bc2e7acf3967fb0ff2d05094"},{"path":"/usr/share/terminfo/x/xterm-xf86-v40","mode":33188,"size":2246,"sha256":"52a70e4af3efcd6d57156501c56f99de86374792fd9ed85b8e6f97e04fd674a1"},{"path":"/usr/share/terminfo/x/xterm-xf86-v43","mode":33188,"size":2260,"sha256":"bef75e99c6d11623dc551d28b3e755bbdd611c3bc2eacfe7adb3dc3996cc9a9a"},{"path":"/usr/share/terminfo/x/xterm-xf86-v44","mode":33188,"size":2294,"sha256":"e8d2495110bbfebabdb8d89dad2d39a70bb806704bb379d8d0a9ad61869a8781"},{"path":"/usr/share/terminfo/x/xterm-xfree86","mode":33188,"size":2274,"sha256":"2cfabe28ee20533848426f6c04c134603dd121a3d6831d0ec8a12f200e5a863b"},{"path":"/usr/share/terminfo/x/xterm-xi","mode":33188,"size":2020,"sha256":"59b2ad72d3752c4e3875502821fc90857f3b4d7e3ded5ff975b6c557e3944076"},{"path":"/usr/share/terminfo/x/xterms","mode":33188,"size":1525,"sha256":"2b1249158a7053eee58242625f79b29f35da721cbcf695a327521cfed3bec117"}]}},{"name":"ncurses-libs","version":"6.1-7.20180224.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:ncurses-libs:ncurses-libs:6.1-7.20180224.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:ncurses-libs:6.1-7.20180224.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/ncurses-libs@0:6.1-7.20180224.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"ncurses-libs","version":"6.1","epoch":0,"architecture":"x86_64","release":"7.20180224.el8","sourceRpm":"ncurses-6.1-7.20180224.el8.src.rpm","size":1120040,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/0f/a4257065e15ec5447b36eec86bdf4ad6b6ad3d","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/2b/5886411e342c52d649245d46acd346d9870bb1","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/46/936366ebfed6d3828e23ce2a848023b6bd01d7","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/5e/b7135acda6824ce98894c52c45cda27a866c4a","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/63/d42395e2ac6dd60332da36d26486f8a669b2cb","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/a4/925636ecde9fb630563d73b62fe1589498db0a","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/ad/836bbea1beebbd1df8bfab324bfec157320013","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/bf/86c2ac74bfa0db05a88ad5f2b636720d0c2604","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/d0/90a2a9f97976d8b604bcec67c09dbb44a7dc4f","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/e6/0c3bf2c757d54e7e7958fa7f9f3e9f7af20647","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/e7/4bd7b5c64379e0337c21cac016ab752ccacd57","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/ef/4d909db95c328002dca46789bb58dc01b4bce0","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libform.so.6","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib64/libform.so.6.1","mode":33261,"size":88848,"sha256":"575325aed3db6b7c34b174dd0da3f52f0663a1546a44afb78e2bab5751d6ad9d"},{"path":"/usr/lib64/libformw.so.6","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libformw.so.6.1","mode":33261,"size":97152,"sha256":"92d7fcf93e8d409af23d181f99d8d84706ae89fe0b31c4aae3710e013fcba723"},{"path":"/usr/lib64/libmenu.so.6","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib64/libmenu.so.6.1","mode":33261,"size":48040,"sha256":"cd21371deba4ea1f3641ad4b5434932cf4418cf9ab068fade27303fe7b0212b2"},{"path":"/usr/lib64/libmenuw.so.6","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libmenuw.so.6.1","mode":33261,"size":48040,"sha256":"6734fa55b9a333f9ff53e25fa84937c8310ef257c732261e3ea77152ab172e7d"},{"path":"/usr/lib64/libncurses.so.6","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libncurses.so.6.1","mode":33261,"size":216912,"sha256":"37e54f939ea95345b87cd6aacb4b933889708a851f5d4030dc33718edb42be16"},{"path":"/usr/lib64/libncursesw.so.6","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libncursesw.so.6.1","mode":33261,"size":300104,"sha256":"6917186341a5e6ea36eea5488909ab0b254c1d25d00507f919be453d71753a03"},{"path":"/usr/lib64/libpanel.so.6","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libpanel.so.6.1","mode":33261,"size":21952,"sha256":"8832fe392e9cae2ea5ef543ed85db363390b7df2488413d193254ad47fed9d65"},{"path":"/usr/lib64/libpanelw.so.6","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libpanelw.so.6.1","mode":33261,"size":21952,"sha256":"9dc1ca629379124479d1ae271e50c00ef3673e570321000e36a80006e52d5739"},{"path":"/usr/lib64/libtic.so.6","mode":41471,"size":13,"sha256":""},{"path":"/usr/lib64/libtic.so.6.1","mode":33261,"size":68424,"sha256":"9bef84ab9530dcf32ee44395912e7bc4417f70c69fd43d878b0d7d2de7894560"},{"path":"/usr/lib64/libtinfo.so.6","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/libtinfo.so.6.1","mode":33261,"size":208616,"sha256":"4d3bfa809d1ed5c6efd9e6b4f04658cc3bc967492ee9b09ebc80a77110f9bfc2"}]}},{"name":"nettle","version":"3.4.1-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:nettle:nettle:3.4.1-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:nettle:3.4.1-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/nettle@0:3.4.1-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"nettle","version":"3.4.1","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"nettle-3.4.1-1.el8.src.rpm","size":683185,"license":"LGPLv3+ or GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/07/12af30140400a99a0bd18bde0012e2519f3067","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/7b/55309cb00960367d164941eb8ad779ac75d0df","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/.libhogweed.so.4.5.hmac","mode":33188,"size":65,"sha256":"451b29b2271e5137c66acf11edc15a64fb97cfaa59491a85dfc8f0e4a626d15b"},{"path":"/usr/lib64/.libhogweed.so.4.hmac","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib64/.libnettle.so.6.5.hmac","mode":33188,"size":65,"sha256":"3a34d2460ff8cf5eb279265c7fbb8a69ef7ecdac9cdba9f1e9cd5bdcdc41784d"},{"path":"/usr/lib64/.libnettle.so.6.hmac","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib64/libhogweed.so.4","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libhogweed.so.4.5","mode":33261,"size":248080,"sha256":"c074e9515c76da932a1cb63fcf698bbddf617a2ca73b39f94cc5686f05cb0724"},{"path":"/usr/lib64/libnettle.so.6","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libnettle.so.6.5","mode":33261,"size":299920,"sha256":"71de20c3894bfe28159365a4411305994daa01222baee6c8888cbd60eb58543d"},{"path":"/usr/share/licenses/nettle/COPYING.LESSERv3","mode":33188,"size":7639,"sha256":"a853c2ffec17057872340eee242ae4d96cbf2b520ae27d903e1b2fef1a5f9d1c"},{"path":"/usr/share/licenses/nettle/COPYINGv2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"npth","version":"1.5-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:npth:npth:1.5-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:npth:1.5-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/npth@0:1.5-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"npth","version":"1.5","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"npth-1.5-4.el8.src.rpm","size":47909,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/a4/1fdf4ad239c5c2439a39d7be3174f77858d4e7","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libnpth.so.0","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libnpth.so.0.1.1","mode":33261,"size":21384,"sha256":"dd524880183221b8b8f5bbe08d58af24405a8b0104436c7e14f17b61319f877e"},{"path":"/usr/share/licenses/npth/COPYING.LIB","mode":33188,"size":26525,"sha256":"ce64d5f7b49ea6d80fdb6d4cdee6839d1a94274f7493dc797c3b55b65ec8e9ed"}]}},{"name":"openldap","version":"2.4.46-11.el8_1","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:openldap:openldap:2.4.46-11.el8_1:*:*:*:*:*:*:*","cpe:2.3:a:*:openldap:2.4.46-11.el8_1:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/openldap@0:2.4.46-11.el8_1?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"openldap","version":"2.4.46","epoch":0,"architecture":"x86_64","release":"11.el8_1","sourceRpm":"openldap-2.4.46-11.el8_1.src.rpm","size":1388793,"license":"OpenLDAP","vendor":"CentOS","files":[{"path":"/etc/openldap/ldap.conf","mode":33188,"size":900,"sha256":"3bea281bbd267ed31c02249d9ce4c7659d764c6c36b0f0c81a39e4c810236eb2"},{"path":"/usr/lib/.build-id/12/034441ec0d6b61520d61f5846895582b53292e","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/39/7d45fb760a09fbb17872979cae6d50a93efe96","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/ae/aaaa315ed18dc999af2e4305c025384ef512d9","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/d0/c8abc32e2f342bc700b6173b300e541c0ce8df","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib64/liblber-2.4.so.2","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/liblber-2.4.so.2.10.9","mode":33261,"size":97048,"sha256":"38531c51f0b9f3fc6cb3753cf4729c59fc375a4a3ac871e015b5149cc29d3af1"},{"path":"/usr/lib64/libldap-2.4.so.2","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libldap-2.4.so.2.10.9","mode":33261,"size":473376,"sha256":"0a5f170859496fc4a7073fbe1816091f4930470f2da183a606ad42c6ff099eb2"},{"path":"/usr/lib64/libldap_r-2.4.so.2","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib64/libldap_r-2.4.so.2.10.9","mode":33261,"size":529912,"sha256":"68e93c520a31e2c74bf2d66757ca127407023b2ddd8f57331ed325145603238f"},{"path":"/usr/lib64/libslapi-2.4.so.2","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib64/libslapi-2.4.so.2.10.9","mode":33261,"size":173760,"sha256":"bb97c93e3fda0f738423935c2ddae62fe872bac24542162e9523e23bb9cce1fa"},{"path":"/usr/share/licenses/openldap/COPYRIGHT","mode":33188,"size":2345,"sha256":"a207b1dd64d275e3cbe0bed9ae5e8b05f410318984c4c84ca07c992808da4379"},{"path":"/usr/share/licenses/openldap/LICENSE","mode":33188,"size":2214,"sha256":"310fe25c858a9515fc8c8d7d1f24a67c9496f84a91e0a0e41ea9975b1371e569"}]}},{"name":"openssl-libs","version":"1.1.1c-15.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:openssl-libs:openssl-libs:1.1.1c-15.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:openssl-libs:1.1.1c-15.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/openssl-libs@1:1.1.1c-15.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"openssl-libs","version":"1.1.1c","epoch":1,"architecture":"x86_64","release":"15.el8","sourceRpm":"openssl-1.1.1c-15.el8.src.rpm","size":3744176,"license":"OpenSSL","vendor":"CentOS","files":[{"path":"/etc/pki/tls/ct_log_list.cnf","mode":33188,"size":412,"sha256":"f1c1803d13d1d0b755b13b23c28bd4e20e07baf9f2b744c9337ba5866aa0ec3b"},{"path":"/etc/pki/tls/openssl.cnf","mode":33188,"size":11225,"sha256":"af49f6cc959e96df354a9a9442814fcccc6d3e1ed6fa2d4af123d2e2987b66f1"},{"path":"/usr/lib/.build-id/00/2a6b0c4063f20cd80099a3b4d9e3732e0bbc73","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/32/e275760859214d906dab89c9ab008bc40f6e6f","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/39/da39ce3c907073d0e69f48906646b3e288ca78","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/54/eb62cc41d23c3de00b5d5745322de1383acf26","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/fc/a69d9f4bc067ffa2f880051d3979ce96070ac5","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/.libcrypto.so.1.1.1c.hmac","mode":33188,"size":65,"sha256":"e9de44a982946949d78b267ac03d085851bf18ad14efcb493bfd8d47d58f1222"},{"path":"/usr/lib64/.libcrypto.so.1.1.hmac","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib64/.libssl.so.1.1.1c.hmac","mode":33188,"size":65,"sha256":"0e2871a8c6fcc65fb6ce1b90bc4df64b8438378c7cd9a6f699b2cfaa95530456"},{"path":"/usr/lib64/.libssl.so.1.1.hmac","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib64/engines-1.1/afalg.so","mode":33261,"size":20464,"sha256":"d81f39a80822de1e9a63a1dfe7c2778fd75bde0c58a4e95a4164aac46e6c6121"},{"path":"/usr/lib64/engines-1.1/capi.so","mode":33261,"size":7416,"sha256":"723b91cedc5ce98e2959fde3e1f7b9ad24531aa1416ef53541254413a8932f70"},{"path":"/usr/lib64/engines-1.1/padlock.so","mode":33261,"size":24168,"sha256":"7e38818fafd2bb7681e6d92aa273e1055132647d4a686152778117e0fe5020c4"},{"path":"/usr/lib64/libcrypto.so.1.1","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libcrypto.so.1.1.1c","mode":33261,"size":3058736,"sha256":"b29662bd5d05c53e6ce913e0ac0f04ce5a5c55bbfb680dc1e9eea3a1630a22be"},{"path":"/usr/lib64/libssl.so.1.1","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libssl.so.1.1.1c","mode":33261,"size":615504,"sha256":"7e758cc5b69a84ac3116abc89ea8963bc57b3dfe5b05cf35d759c74d6c1a3c6f"},{"path":"/usr/share/licenses/openssl-libs/LICENSE","mode":33188,"size":6121,"sha256":"c32913b33252e71190af2066f08115c69bc9fddadf3bf29296e20c835389841c"}]}},{"name":"p11-kit","version":"0.23.14-5.el8_0","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:p11-kit:p11-kit:0.23.14-5.el8_0:*:*:*:*:*:*:*","cpe:2.3:a:*:p11-kit:0.23.14-5.el8_0:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/p11-kit@0:0.23.14-5.el8_0?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"p11-kit","version":"0.23.14","epoch":0,"architecture":"x86_64","release":"5.el8_0","sourceRpm":"p11-kit-0.23.14-5.el8_0.src.rpm","size":1394732,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/bin/p11-kit","mode":33261,"size":41984,"sha256":"f3c511801f565a90e8c49e6b0d877fe67f24268e07643136bca144470e6e0428"},{"path":"/usr/lib/.build-id/08/5cdfd57ab06e3134a2c00e71475574cee850df","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/4b/b97f2c714af5f1460036865989d75810850c07","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/b6/f024857f04d8afee61f0bcc0632f73e1b35202","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib64/libp11-kit.so.0","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libp11-kit.so.0.3.0","mode":33261,"size":1295528,"sha256":"ed97293116426180852e63d6eeb216e9487ef3ac1c3d81cb59c6fe55ca25563d"},{"path":"/usr/lib64/p11-kit-proxy.so","mode":41471,"size":19,"sha256":""},{"path":"/usr/libexec/p11-kit/p11-kit-remote","mode":33261,"size":32344,"sha256":"748f34340a2b990ae3c00f93c8fc133d2e77cc20f48cce06fcb5b0305d7576c0"},{"path":"/usr/share/licenses/p11-kit/COPYING","mode":33188,"size":1447,"sha256":"2e1ba993904df807a10c3eda1e5c272338edc35674b679773a8b3ad460731054"}]}},{"name":"p11-kit-trust","version":"0.23.14-5.el8_0","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:p11-kit-trust:p11-kit-trust:0.23.14-5.el8_0:*:*:*:*:*:*:*","cpe:2.3:a:*:p11-kit-trust:0.23.14-5.el8_0:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/p11-kit-trust@0:0.23.14-5.el8_0?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"p11-kit-trust","version":"0.23.14","epoch":0,"architecture":"x86_64","release":"5.el8_0","sourceRpm":"p11-kit-0.23.14-5.el8_0.src.rpm","size":508547,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/bin/trust","mode":33261,"size":239200,"sha256":"4a4a3aecdda8127b4d447a9a379c275613296811d9d15fcf16b98272a81e038c"},{"path":"/usr/lib/.build-id/3a/0bef58a33134c3e894b5d143454afdb0825262","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/52/a32cadf1779253d61f57b74abb40757075bd63","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib64/libnssckbi.so","mode":32768,"size":0,"sha256":""},{"path":"/usr/lib64/pkcs11/p11-kit-trust.so","mode":33261,"size":268296,"sha256":"17b194507b9603f3cc4237ca844e1de167ab7980f5f025baa2bb14187f4373d6"},{"path":"/usr/libexec/p11-kit/trust-extract-compat","mode":33261,"size":275,"sha256":"e3b9b63689b120e461687c7febc6ab0c3d33d6acd6f943c46113c9ed284b49ac"},{"path":"/usr/share/p11-kit/modules/p11-kit-trust.module","mode":33188,"size":776,"sha256":"4a451086326b39dcefbee7d38f2b19886bb25c1eb6f64b06d1e0dd00c8c4b4e4"}]}},{"name":"pam","version":"1.3.1-8.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:pam:pam:1.3.1-8.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:pam:1.3.1-8.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/pam@0:1.3.1-8.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"pam","version":"1.3.1","epoch":0,"architecture":"x86_64","release":"8.el8","sourceRpm":"pam-1.3.1-8.el8.src.rpm","size":2857052,"license":"BSD and GPLv2+","vendor":"CentOS","files":[{"path":"/etc/pam.d/config-util","mode":33188,"size":232,"sha256":"4f10f27a970924ba9f636f2d5fdb4267c3ada93f7b4eee1bc3ad05c33406e76c"},{"path":"/etc/pam.d/fingerprint-auth","mode":33188,"size":701,"sha256":"ef504b9d80c9db13ebd0d4aca651de31784938caa4e059d13964e48032057219"},{"path":"/etc/pam.d/other","mode":33188,"size":154,"sha256":"c5c2a7c1f8dfbefa5df66cd32a7b754266d6375471d43cea06b8bea937d24b40"},{"path":"/etc/pam.d/password-auth","mode":33188,"size":760,"sha256":"515f0848df9db305c4c1505220bd4292f1036245dced25a62baffd1321eb2804"},{"path":"/etc/pam.d/postlogin","mode":33188,"size":398,"sha256":"3b565d5426d2dbb52dd605d009c151b0b35c4411d37241049b26cb60f4b36add"},{"path":"/etc/pam.d/smartcard-auth","mode":33188,"size":743,"sha256":"7c7bde5453e7f5de23fec09bc7a8639e2985725d4e225ad6b4009b4a66b04096"},{"path":"/etc/pam.d/system-auth","mode":33188,"size":760,"sha256":"515f0848df9db305c4c1505220bd4292f1036245dced25a62baffd1321eb2804"},{"path":"/etc/security/access.conf","mode":33188,"size":4564,"sha256":"f68915c4eb637aacbfa01cf26dc469a73f70acb0495efc4b074ecbc626bcb345"},{"path":"/etc/security/chroot.conf","mode":33188,"size":82,"sha256":"7fb959ba2053842c5e0d60605a5ed7528fca2727414700cf3783c3f1309d2f30"},{"path":"/etc/security/console.handlers","mode":33188,"size":624,"sha256":"51d0a7ff736763340d192e07c3ff423f0de85347ab849c3065d18212590e1119"},{"path":"/etc/security/console.perms","mode":33188,"size":939,"sha256":"d1fd01ea23a67467ef8196a118752d1ee5a6f31982af9f5cc810a708a37d0472"},{"path":"/etc/security/faillock.conf","mode":33188,"size":2232,"sha256":"6209097352db267635e00812bf419e9d1b010850280b4d7a064e106ee70ac4bb"},{"path":"/etc/security/group.conf","mode":33188,"size":3635,"sha256":"41df4bc646811997d0390c6d37d839d2aef4a9a1a940c44ee1a798a9dc1ac864"},{"path":"/etc/security/limits.conf","mode":33188,"size":2422,"sha256":"185b151a665848d8ee518342b9a88a2d64898b0b1a2d01b12be731f75d48943b"},{"path":"/etc/security/namespace.conf","mode":33188,"size":1440,"sha256":"d0c3045ba5071b8375fde6165d4e4db9b69f49af5d2525cecd2bca1cb7538552"},{"path":"/etc/security/namespace.init","mode":33261,"size":1016,"sha256":"2d76094c06f10839c566ef64bde5624c325aeab7991e7f5d776c5310e8f41932"},{"path":"/etc/security/opasswd","mode":33152,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/etc/security/pam_env.conf","mode":33188,"size":2972,"sha256":"ff4956721a3f53e56e25ffffde62fe4fa0267e5dd94c3411def12de50322fb8f"},{"path":"/etc/security/sepermit.conf","mode":33188,"size":419,"sha256":"885ec2a43042ad88d7f849e5e1cbef4e34e58229764a84a927c0e09cd7d47d70"},{"path":"/etc/security/time.conf","mode":33188,"size":2179,"sha256":"6802adfc8efc6168f87e98e960fa7d15e516a295fef7a6472ef5359527e886ff"},{"path":"/usr/lib/.build-id/02/51f6622efb43dd45c88a995d77166962d69ba9","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/03/d995ed9f50fde8fefe530f4dda82f60c33689a","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/06/937dd05de3fbba28adccfefb4a7d00b81642ae","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/07/d5a91d383e1c5c32e53eb1d3bb5ae18e78bd3f","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/0f/ff8147702da595ed23dd3ae6076eaa1e949afd","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/12/7dc9d59d5c820b4e1b6900cc33799090b098c8","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/25/34b313ce342ddeec4a5be5902f18f04d3605f4","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/25/6cc757b0354b555f66bc0bf3d52b073adfbc71","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/3f/6bf574ee7c52195c3751a62bd5e9c37c8b05e3","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/42/f9b803594153201428c472514dffcdffb907c2","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/45/192ce177ed22beaecca8dfbfb7ac5c7d811928","mode":41471,"size":48,"sha256":""},{"path":"/usr/lib/.build-id/47/a9a2d6a3ff3983e2794e7e34012f395b18fa4d","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/53/2a0b536aa676ae361b31444829bbf08feaa38b","mode":41471,"size":48,"sha256":""},{"path":"/usr/lib/.build-id/58/effdb70bd8e72afa878a651a6ff479fa17b029","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/5d/e597c3b9fef35b2917e14111568be97d8fd026","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/62/43a238598ef60be15d769c927dca61d7613445","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/63/40462efa30a55265d6463d8e2d7a6ed68ebd3e","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/64/82c7e934ce2ed338b2c84b002aa1bc13f56bed","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/67/67846132282cfd4d1f3939a4616450f21caad2","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/68/7c7e7462a63122f669c29f9ff310bf634f0cdd","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/6b/22a491dedb60ff54f44db5d4f74d59371d4199","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/6e/1978a35fdfb3b5e2d577ae1e774314500473d3","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/72/b28ea8caf184577570f0e3654f9108e3d31567","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/76/f7473a7494e4bc52cb236f7f22002243d0cf5d","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/78/9dadbe2c7296b74af5379176a07d70dfdaeba4","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/79/3c1cadd4070d4cc30dde94b0a582e1d07e4511","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/7c/230aa8281bdd39174ec14fe1a62fb40a16e2f4","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/7e/502d1183e82905b1ac8e311041497624c25173","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/82/94405cc71d21ff52da24a68bbd58cbc55e0cff","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/82/99a9a26ebb8f952332ff5b89ad8aedcc0d26e4","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/8a/b92a4d1f03f423b15672353259b8a2f8773fbb","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/8e/8c255c0272d798f2beb9e9980b0927f3b3e00b","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/91/cc5209b937d09319632df2c546db5236cb28c2","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/93/4078d89daf67c09b3f481f84c7693121a85c24","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/99/9a24b2a704b0b055201beb4407520d762b795a","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/a2/0e2951ff14bd853ebb6cfd5f04370430be2a66","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/ab/0325bf361aa4552a27fcade35e9ec591206056","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/ad/1e93c6776bdd4fd13a0ee72077ce42059bb3d0","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/b0/7a8cd5cd98a2e68f81855e03c51c9db17c8239","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/b1/baee265d4e97989fde751e8979a33be86f6713","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/b4/922395a3e6c6beacacf1c8beb7ec41e09d2dc9","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/c7/efab877bc271230b72a43441a543ab4986a642","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/c9/cc366e55162d568fb98e946ba2f734eb64405a","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/d5/54b2071328155b73faf189cd5ef8eeb638f24f","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/db/c85e13a7520a78ce5e8cc4f5b84befa413de6c","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/e0/aaa45233b43ab85dfc39eabb98c1d0f9622f84","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/e0/e9e8b905edbcd6987f598bd330c99f7d204d80","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/e3/adaa2d4338dfdf5c0ffdd33974c861fa95721c","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/ea/71bdec017daecef880dbec01ff4b21946f3251","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/ed/6b81acd2208f2280d13add3ff9ed6176075d8f","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/f0/45ee462d826d18f096c583f1a5a992d0a138d8","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/f2/f23f87ead0f721f4cc7dc6d97a6ed5def2bfea","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/f5/e0c727c8b63404d1d9d71c080cc30c25a9013b","mode":41471,"size":52,"sha256":""},{"path":"/usr/lib/.build-id/f8/4a4697e8289016429ae525d0cf9ef3b5b23c63","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/f8/5ef2e543ba5b1f5f769ccc82919aabcc1a05be","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/fa/862fc38a64f0de2022b8824dc88450c5b12ca9","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib/.build-id/fe/0548533cccf64e2f0e85a2bb33f70f777129a9","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/tmpfiles.d/pam.conf","mode":33188,"size":98,"sha256":"4d4c2cdce5e69cc9427a7a96d35cfb1d1cf4bb72d540a87fc93a2345839f78ae"},{"path":"/usr/lib64/libpam.so.0","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libpam.so.0.84.2","mode":33261,"size":128992,"sha256":"c6c40d4d00b1f58ee35d90176710393ae7ed000ce6debb750bc71aef62025ae1"},{"path":"/usr/lib64/libpam_misc.so.0","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libpam_misc.so.0.82.1","mode":33261,"size":20136,"sha256":"e730fe65812b7fccd78f043593afd20b0aab047ccb57e5218b715fb764910985"},{"path":"/usr/lib64/libpamc.so.0","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libpamc.so.0.82.1","mode":33261,"size":22136,"sha256":"66508c1487b95e4a1205e7f13500463514125cc69d3e72838485eb802a63c0a6"},{"path":"/usr/lib64/security/pam_access.so","mode":33261,"size":22656,"sha256":"2bf618be989ac4110b83b70d916438ab9ba5fdcc7251e80ddf1765bc02ce9d57"},{"path":"/usr/lib64/security/pam_chroot.so","mode":33261,"size":13456,"sha256":"38076076568135b90e987ec0bafd8491bc7dc1f6ea6ebb4c923eb4ee531ca244"},{"path":"/usr/lib64/security/pam_console.so","mode":33261,"size":34984,"sha256":"d0139d3db177e4e2f7c4530bf6b58bd6f694f881ee58a852e2cb2ac709fae72e"},{"path":"/usr/lib64/security/pam_cracklib.so","mode":33261,"size":21840,"sha256":"b2e53f5da8d673bfac55014864452a36286e5c6844f6bf667bc70d9df74a06a0"},{"path":"/usr/lib64/security/pam_debug.so","mode":33261,"size":13864,"sha256":"c2d6109ee9048861e93bb8697a537b532ea53473c75e927b0878a2bdae57df68"},{"path":"/usr/lib64/security/pam_deny.so","mode":33261,"size":9552,"sha256":"be1b8deb94380dbbc64255be6e1f50ad5333948eede62660f9d69726652d18b2"},{"path":"/usr/lib64/security/pam_echo.so","mode":33261,"size":13944,"sha256":"a55f5a3d6b525d3d15bcd741634d90631ff767f9497527f011b32769ae9e9b2c"},{"path":"/usr/lib64/security/pam_env.so","mode":33261,"size":22536,"sha256":"644b67ee0ec00a1951c0e645e73f4c6221c4bca790be6a2c2bd511f01d63d5eb"},{"path":"/usr/lib64/security/pam_exec.so","mode":33261,"size":18008,"sha256":"960df2fd2af8ecbd061d06e7cb2879ba764beb7449f27e35b8d5482edda02f39"},{"path":"/usr/lib64/security/pam_faildelay.so","mode":33261,"size":13472,"sha256":"038ceef2a345d5e4b1103cfbe2bbc6b388af13ba1af19edcbe2e0d152eddf803"},{"path":"/usr/lib64/security/pam_faillock.so","mode":33261,"size":24408,"sha256":"7e2c22a8590abfdacc1ca053e6f0bbbed630478ad1f9f9606f97c92b20fa73f8"},{"path":"/usr/lib64/security/pam_filter.so","mode":33261,"size":18040,"sha256":"42fa13a48c20bce2024855ba627db8103553a263a22e1e9a5c9092f137bfb929"},{"path":"/usr/lib64/security/pam_filter/upperLOWER","mode":33261,"size":14912,"sha256":"ba6b0b73ba59452d48cc6d60e3ac6c0349d5afb2d84791e02188ca3d2af89a8e"},{"path":"/usr/lib64/security/pam_ftp.so","mode":33261,"size":13456,"sha256":"56d1651333d3a575a601501f3db9b58edd1f05f2df68874d9a6378466baa9da3"},{"path":"/usr/lib64/security/pam_group.so","mode":33261,"size":17880,"sha256":"b494682d28da59d4830daa6dd2da541a23f72c5cb0df26c44a39c3e8bf3aa3bb"},{"path":"/usr/lib64/security/pam_issue.so","mode":33261,"size":13560,"sha256":"53d5e30b1de96f7d3f3323bd88bf1a92c25a44141a1c8394b41e7ba74181cc0a"},{"path":"/usr/lib64/security/pam_keyinit.so","mode":33261,"size":13600,"sha256":"cbd4561fbf8a40ba97d6c6a54f24bfb273c5e99fa92087e419871df9a98fc9dc"},{"path":"/usr/lib64/security/pam_lastlog.so","mode":33261,"size":22456,"sha256":"0765cd75d593c0a0914709cff2751be3bbed3cc219a49847d04b8bf3978f56d1"},{"path":"/usr/lib64/security/pam_limits.so","mode":33261,"size":26056,"sha256":"371aa6baa185353f0465fbc2b7863728ea71c7f9303583be524bc52a6d2e9107"},{"path":"/usr/lib64/security/pam_listfile.so","mode":33261,"size":13768,"sha256":"1d867100132c22638df82ccb7d93ab6c6515d6a0c005957205dd2bdd79456a89"},{"path":"/usr/lib64/security/pam_localuser.so","mode":33261,"size":13760,"sha256":"abc6fdb36d4c9e14135eb378cca89085bb3b9c14c714081a2c6b800b1c378a4a"},{"path":"/usr/lib64/security/pam_loginuid.so","mode":33261,"size":13704,"sha256":"a88c477b389115505f8114093a06115f33bb8b22477c35f87c128908e0898944"},{"path":"/usr/lib64/security/pam_mail.so","mode":33261,"size":17792,"sha256":"2117d41e082c264e8d241cf8c7ce5a91a8887085cc6588713a7ed76bec9fd581"},{"path":"/usr/lib64/security/pam_mkhomedir.so","mode":33261,"size":13464,"sha256":"e3f3816ecf25f9cc88742540a3f4cde7440a3c0975050cb7d1e8bf27aaf0cb8f"},{"path":"/usr/lib64/security/pam_motd.so","mode":33261,"size":13648,"sha256":"14e8fa4f84281838d06081f8259994f66f5db3895c506c3497122d55ec03db02"},{"path":"/usr/lib64/security/pam_namespace.so","mode":33261,"size":51672,"sha256":"150330dc66fcea232e20a6f9a3017941ab8fd75fe485001136d24ad2f502cea8"},{"path":"/usr/lib64/security/pam_nologin.so","mode":33261,"size":13640,"sha256":"fde7250470126b29e668d1a8f338d1f2c4bc0e107f0e47d6cab7aaa0d91a4f3b"},{"path":"/usr/lib64/security/pam_permit.so","mode":33261,"size":9648,"sha256":"c221a6ff6c9686fc83ab57a646a3179d9d68a744c20749f22d997e3dd6148047"},{"path":"/usr/lib64/security/pam_postgresok.so","mode":33261,"size":9360,"sha256":"1664809297bbd7605f102aac819d3d6a8cc38b117c47b0d605921073bb80e1d0"},{"path":"/usr/lib64/security/pam_pwhistory.so","mode":33261,"size":23952,"sha256":"baf7a2e3ae8c4895512e977b27cc62c29445409afa0ff6c693e52de057b493c1"},{"path":"/usr/lib64/security/pam_rhosts.so","mode":33261,"size":13464,"sha256":"a324d603ac076c8bfbcaed1704d295fba4929274034114f0ffa41c0ec2551cf4"},{"path":"/usr/lib64/security/pam_rootok.so","mode":33261,"size":13720,"sha256":"d7ff5afeb8e85fb9f9d1096034e0040a61f5539c3070dd97b9679257d26d8e3b"},{"path":"/usr/lib64/security/pam_securetty.so","mode":33261,"size":13712,"sha256":"5fd1a3a3d198565fc3be4e08c12d7568ea4869193b332564db7c8c8988b07209"},{"path":"/usr/lib64/security/pam_selinux.so","mode":33261,"size":26616,"sha256":"1b732a96949bcf3fa7cffd3d92e5de50031382cd5f4babfc6ef3d8c52d0e68fe"},{"path":"/usr/lib64/security/pam_selinux_permit.so","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/security/pam_sepermit.so","mode":33261,"size":17888,"sha256":"23317d3e4b8d222e2ec69011aa099c9199b2aec263071426458b010eccf1422b"},{"path":"/usr/lib64/security/pam_shells.so","mode":33261,"size":13624,"sha256":"64093f66d00593f705731298e2873d7163734e15607f4caa312fe19dd56ce95d"},{"path":"/usr/lib64/security/pam_stress.so","mode":33261,"size":18272,"sha256":"9e25fcbd8316de12e3fc5fbbe282f99707a628f17118f113ebdcb0ae3057221b"},{"path":"/usr/lib64/security/pam_succeed_if.so","mode":33261,"size":18504,"sha256":"78bf90f2959577c52564bd68dbd2f42ff232cc20e6a6422a0e1c29280ae18440"},{"path":"/usr/lib64/security/pam_time.so","mode":33261,"size":17808,"sha256":"179ed72bfbeed78f9df5d325e498a360ca7df69c095f7db8cc4e12b0b5794be2"},{"path":"/usr/lib64/security/pam_timestamp.so","mode":33261,"size":30528,"sha256":"6d00117ce9cd49f1bcf35516d2d12aadcb709343c76e4dd1cc512eb536735e26"},{"path":"/usr/lib64/security/pam_tty_audit.so","mode":33261,"size":13776,"sha256":"04f8ac604c27a8f2e2e20e12815d434c24f1c183774fb20ba9e6c632e98c383d"},{"path":"/usr/lib64/security/pam_umask.so","mode":33261,"size":13536,"sha256":"e189ffea0a090a4c7b21aa2342d1bc6dea26ac2f9e8d2839e9d0f49d9d34db30"},{"path":"/usr/lib64/security/pam_unix.so","mode":33261,"size":79056,"sha256":"9f63b453e6bdbd44a3edf2d38968098e5e8c107e40b3ea7f4716fec73bccc58d"},{"path":"/usr/lib64/security/pam_unix_acct.so","mode":41471,"size":11,"sha256":""},{"path":"/usr/lib64/security/pam_unix_auth.so","mode":41471,"size":11,"sha256":""},{"path":"/usr/lib64/security/pam_unix_passwd.so","mode":41471,"size":11,"sha256":""},{"path":"/usr/lib64/security/pam_unix_session.so","mode":41471,"size":11,"sha256":""},{"path":"/usr/lib64/security/pam_userdb.so","mode":33261,"size":17888,"sha256":"26adb4f67e588bc15aca603b6b92458b1bf559222c79080ac29db3bd9cd6f1f9"},{"path":"/usr/lib64/security/pam_warn.so","mode":33261,"size":9720,"sha256":"592f8788b706a4dd30ea5d872f2c1495a6e884bceca0b2c02533602def3443bf"},{"path":"/usr/lib64/security/pam_wheel.so","mode":33261,"size":13560,"sha256":"e4ad1af6fd7d8674d4239e65950254239bc7641113a79dc418d6fca74411a630"},{"path":"/usr/lib64/security/pam_xauth.so","mode":33261,"size":25984,"sha256":"6f32206c3120d1fec3b73cbe7d2bee7708c4f624c9aeed7821ca83b6e1e9c375"},{"path":"/usr/sbin/faillock","mode":33261,"size":21152,"sha256":"b9299e0bb91da1ae0b94f5e3a1f5ad843ef5c36800ec2de073a1db1eb5b511ab"},{"path":"/usr/sbin/mkhomedir_helper","mode":33261,"size":27360,"sha256":"a257172b4831edac2c891d5368a99f019baaf0054f62be1764412fea1761c3be"},{"path":"/usr/sbin/pam_console_apply","mode":33261,"size":61656,"sha256":"7e9d63758e3f0d5a396a8369d9661f3bf3165363d231b792871d9de67639224a"},{"path":"/usr/sbin/pam_timestamp_check","mode":35309,"size":14872,"sha256":"48ec339f41bd50dd177b344371a3037b2833c54080fbe9841bfc9bd598b8f46f"},{"path":"/usr/sbin/pwhistory_helper","mode":33261,"size":21320,"sha256":"e562c55c8ea1bad12cbb12b040391a4a089dec72a4c091ed01f302f42c03a895"},{"path":"/usr/sbin/unix_chkpwd","mode":35309,"size":49464,"sha256":"30a8793d32987706e98fae126a4f8d46bbb8f2aa43c73e021c955faaac9fc8dd"},{"path":"/usr/sbin/unix_update","mode":33216,"size":49456,"sha256":"8c350e931622f3841c7c3880a95192ad62b75da681bb5d3bc459d4a69c8a0b71"},{"path":"/usr/share/licenses/pam/Copyright","mode":33188,"size":2045,"sha256":"133d98e7a2ab3ffd330b4debb0bfc10fea21e4b2b5a5b09de2e924293be5ff08"},{"path":"/usr/share/licenses/pam/gpl-2.0.txt","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/locale/en_GB/LC_MESSAGES/Linux-PAM.mo","mode":33188,"size":546,"sha256":"706c9bc7b2fcd06356228352e2fa807a87e019bf4e16532352c3eb7e718f0b3b"}]}},{"name":"pcre","version":"8.42-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:pcre:pcre:8.42-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:pcre:8.42-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/pcre@0:8.42-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"pcre","version":"8.42","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"pcre-8.42-4.el8.src.rpm","size":518067,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/22/03234c40ccfd77ea2bbee7ba4772e7db89c565","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/c0/ea2c9d06cb57414b681dec7d0b8ae8a89c6589","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib64/libpcre.so.1","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libpcre.so.1.2.10","mode":33261,"size":472912,"sha256":"f20925959f95d595193fdd0c1a627e61ff86a29f1774be588ea75ce369414608"},{"path":"/usr/lib64/libpcreposix.so.0","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib64/libpcreposix.so.0.0.6","mode":33261,"size":11888,"sha256":"6952ae73488eb10cf5a765255142be9c89dcf977a85136a447a03205eee93818"},{"path":"/usr/share/licenses/pcre/COPYING","mode":33188,"size":95,"sha256":"17abe1dbb92b21ab173cf9757dd57b0b15cd8d863b2ccdef635fdbef03077fb0"},{"path":"/usr/share/licenses/pcre/LICENCE","mode":33188,"size":3182,"sha256":"f998c0f52eb704eff28f503580cfca3f2547280aa212994f6cf2d8e317587c1c"}]}},{"name":"pcre2","version":"10.32-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:pcre2:pcre2:10.32-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:pcre2:10.32-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/pcre2@0:10.32-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"pcre2","version":"10.32","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"pcre2-10.32-1.el8.src.rpm","size":667046,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/07/2f420c5cd119ff169ae7d73e698eded50925dc","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/cb/3c9986ed17121c3da6e74890023d727c5af289","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib64/libpcre2-8.so.0","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libpcre2-8.so.0.7.1","mode":33261,"size":553480,"sha256":"799d254188ff14306d19fe891df385fda7707d97f72fa8daedc5ab0c58cbb219"},{"path":"/usr/lib64/libpcre2-posix.so.2","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib64/libpcre2-posix.so.2.0.1","mode":33261,"size":11896,"sha256":"15dd8fc092680ee6bbcb10b58e5cee612a1e402729afe5838246715a29bc2c8c"},{"path":"/usr/share/licenses/pcre2/COPYING","mode":33188,"size":97,"sha256":"99272c55f3dcfa07a8a7e15a5c1a33096e4727de74241d65fa049fccfdd59507"},{"path":"/usr/share/licenses/pcre2/LICENCE","mode":33188,"size":3456,"sha256":"c4a8b89cd38d6a7501d5b11a472fa15e71a051b66d6331c6cda364101389d6ee"}]}},{"name":"platform-python","version":"3.6.8-23.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:platform-python:platform-python:3.6.8-23.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:platform-python:3.6.8-23.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/platform-python@0:3.6.8-23.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"platform-python","version":"3.6.8","epoch":0,"architecture":"x86_64","release":"23.el8","sourceRpm":"python3-3.6.8-23.el8.src.rpm","size":41790,"license":"Python","vendor":"CentOS","files":[{"path":"/usr/bin/pydoc3.6","mode":33261,"size":89,"sha256":"cae2571c9656ca78109f8d561405625f4fa9a2d531cb725c161d19f5db187eac"},{"path":"/usr/bin/pyvenv-3.6","mode":33261,"size":446,"sha256":"c3131184975ef2015c4a19aaab679e9e884dfdd768e14fd9af0503f151396584"},{"path":"/usr/bin/unversioned-python","mode":33188,"size":0,"sha256":""},{"path":"/usr/lib/.build-id/64/50f089ced0bc3bd83173ad73ba97d9b74b89e2","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/64/50f089ced0bc3bd83173ad73ba97d9b74b89e2.1","mode":41471,"size":43,"sha256":""},{"path":"/usr/libexec/no-python","mode":33261,"size":157,"sha256":"81f6ba91a7968c981a35d6f072b6ffebf86be5396c0cf5aad8179c6e45c7fdad"},{"path":"/usr/libexec/platform-python","mode":41471,"size":20,"sha256":""},{"path":"/usr/libexec/platform-python3.6","mode":33261,"size":12440,"sha256":"4c9c82ea6de8831aa928e5b172065983802d175a4ed06dcf09d03d3d21622ea8"},{"path":"/usr/libexec/platform-python3.6m","mode":33261,"size":12440,"sha256":"4c9c82ea6de8831aa928e5b172065983802d175a4ed06dcf09d03d3d21622ea8"},{"path":"/usr/share/licenses/platform-python/LICENSE","mode":33188,"size":12763,"sha256":"b9a6d9320b8f2693e8d41e496ce56caadacaddcca9be2a64a61749278f425cf2"},{"path":"/usr/share/man/man1/python.1.gz","mode":33188,"size":0,"sha256":""}]}},{"name":"platform-python-setuptools","version":"39.2.0-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:platform-python-setuptools:platform-python-setuptools:39.2.0-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:platform-python-setuptools:39.2.0-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/platform-python-setuptools@0:39.2.0-5.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"platform-python-setuptools","version":"39.2.0","epoch":0,"architecture":"noarch","release":"5.el8","sourceRpm":"python-setuptools-39.2.0-5.el8.src.rpm","size":2930163,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/python3.6/site-packages/__pycache__/easy_install.cpython-36.opt-1.pyc","mode":33188,"size":259,"sha256":"e899399c4dda98a7fe94f6b536ec1a5265f3ad39a1c76dc0100f8bbf22968e8d"},{"path":"/usr/lib/python3.6/site-packages/__pycache__/easy_install.cpython-36.pyc","mode":33188,"size":259,"sha256":"e899399c4dda98a7fe94f6b536ec1a5265f3ad39a1c76dc0100f8bbf22968e8d"},{"path":"/usr/lib/python3.6/site-packages/easy_install.py","mode":33188,"size":126,"sha256":"3030bdbede40c43b175f9a9c2a5073d939d6e93a6ebff0286e77e1089f57dcf3"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/__init__.py","mode":33188,"size":103822,"sha256":"0fa0c61472335671be0725258aa66ec3776407771c13acf98dd8432456a9d766"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":95680,"sha256":"4f355f4a3f08b558d4b890549353660578e147a02f44215db00a9df544805a49"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":95680,"sha256":"4f355f4a3f08b558d4b890549353660578e147a02f44215db00a9df544805a49"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/__pycache__/py31compat.cpython-36.opt-1.pyc","mode":33188,"size":624,"sha256":"abbcdfaabe0dc394557feba08accb267b4e4ad1f50bd273c252578cada90c4a7"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/__pycache__/py31compat.cpython-36.pyc","mode":33188,"size":624,"sha256":"abbcdfaabe0dc394557feba08accb267b4e4ad1f50bd273c252578cada90c4a7"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__init__.py","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":113,"sha256":"d56754de562d9bd3d3f0ff80cac164add19e93a745a2ab37554bea2f4e6d776f"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":113,"sha256":"d56754de562d9bd3d3f0ff80cac164add19e93a745a2ab37554bea2f4e6d776f"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__pycache__/appdirs.cpython-36.opt-1.pyc","mode":33188,"size":18539,"sha256":"800ec56958fb35625d855541f5ab2f560f987d573f994170f1ad5ccfd17c5186"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__pycache__/appdirs.cpython-36.pyc","mode":33188,"size":18539,"sha256":"800ec56958fb35625d855541f5ab2f560f987d573f994170f1ad5ccfd17c5186"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__pycache__/pyparsing.cpython-36.opt-1.pyc","mode":33188,"size":201035,"sha256":"64ebb24cfe8034f5c3182a01afc46c4a15c1634b340bb94500071c2bad91f2e2"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__pycache__/pyparsing.cpython-36.pyc","mode":33188,"size":201035,"sha256":"64ebb24cfe8034f5c3182a01afc46c4a15c1634b340bb94500071c2bad91f2e2"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__pycache__/six.cpython-36.opt-1.pyc","mode":33188,"size":24410,"sha256":"6fb30c6e2705fb969ceff9eab10c18748068fef263ef518b9d1fe2501209f9d8"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/__pycache__/six.cpython-36.pyc","mode":33188,"size":24410,"sha256":"6fb30c6e2705fb969ceff9eab10c18748068fef263ef518b9d1fe2501209f9d8"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/appdirs.py","mode":33188,"size":22374,"sha256":"b6019a2f49b8268d957ae19fa0e3a27cbbfb6bba14109bb69f5bd192aa0fc3ed"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__about__.py","mode":33188,"size":720,"sha256":"ce47023d337fe9370b5b436b960d35efaf91d5043f5953d39bcb33d51e3e1e33"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__init__.py","mode":33188,"size":513,"sha256":"fef35a7394ebcf0b2bcdb38521b17ee5c1ea73f63668f4f60fbceb211d3a04ea"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/__about__.cpython-36.opt-1.pyc","mode":33188,"size":639,"sha256":"5d87f9ee0f14e4a17b2e66231424512e34f56f3bb36edd137afc43ac05f0b7fe"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/__about__.cpython-36.pyc","mode":33188,"size":639,"sha256":"5d87f9ee0f14e4a17b2e66231424512e34f56f3bb36edd137afc43ac05f0b7fe"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":477,"sha256":"aeb4a144efafa928ded168646691327511b5c7beb352e961a328c86cd9d62910"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":477,"sha256":"aeb4a144efafa928ded168646691327511b5c7beb352e961a328c86cd9d62910"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/_compat.cpython-36.opt-1.pyc","mode":33188,"size":924,"sha256":"77bb5bfee7e585f9504f3fa1efffe642ee857cc79f8b7dd680ac728006e973e8"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/_compat.cpython-36.pyc","mode":33188,"size":924,"sha256":"77bb5bfee7e585f9504f3fa1efffe642ee857cc79f8b7dd680ac728006e973e8"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/_structures.cpython-36.opt-1.pyc","mode":33188,"size":2781,"sha256":"6e18462d4d0ae8aa003875739f5670caac399d1d206308fc4062a392a8505ba2"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/_structures.cpython-36.pyc","mode":33188,"size":2781,"sha256":"6e18462d4d0ae8aa003875739f5670caac399d1d206308fc4062a392a8505ba2"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/markers.cpython-36.opt-1.pyc","mode":33188,"size":8698,"sha256":"df27a559b99c58c9d664a7db7cc6c0b15b3c3d56d04eb1e77247ab1acecaf0a4"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/markers.cpython-36.pyc","mode":33188,"size":8804,"sha256":"3234941e3ea8fb95d66e22bea8c1de0fd518a0094cd392116f967cf2334aac55"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/requirements.cpython-36.opt-1.pyc","mode":33188,"size":3800,"sha256":"6a059c6300bbe3d8e39e51910cbe0bf909a04e4ee7ccebbfd9c0b1287337ee8b"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/requirements.cpython-36.pyc","mode":33188,"size":3800,"sha256":"6a059c6300bbe3d8e39e51910cbe0bf909a04e4ee7ccebbfd9c0b1287337ee8b"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/specifiers.cpython-36.opt-1.pyc","mode":33188,"size":19743,"sha256":"5e77ace481863e5ff1acd208442b80eb3c21c6f3c5dc389ad0acddfb46738bb7"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/specifiers.cpython-36.pyc","mode":33188,"size":19743,"sha256":"5e77ace481863e5ff1acd208442b80eb3c21c6f3c5dc389ad0acddfb46738bb7"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/utils.cpython-36.opt-1.pyc","mode":33188,"size":408,"sha256":"81c51f53301119280092c54513df6d59dcaa23f5ee2d8c003107567f50677c57"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/utils.cpython-36.pyc","mode":33188,"size":408,"sha256":"81c51f53301119280092c54513df6d59dcaa23f5ee2d8c003107567f50677c57"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/version.cpython-36.opt-1.pyc","mode":33188,"size":10518,"sha256":"535dda079048da34043fd35ac2779360938efa04f2112067d010f149d3756fcc"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/__pycache__/version.cpython-36.pyc","mode":33188,"size":10518,"sha256":"535dda079048da34043fd35ac2779360938efa04f2112067d010f149d3756fcc"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/_compat.py","mode":33188,"size":860,"sha256":"562fc0d2b0107876d4f9af57d2db75c909bd46a92041b0d2c73470f16954f640"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/_structures.py","mode":33188,"size":1416,"sha256":"448984089e1cff04e5693618c1960b1c489e6c331a00998ad683c0461c354f9a"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/markers.py","mode":33188,"size":8248,"sha256":"b8470106d1afcea96d82702ba9bf5ce11adc2275decc32e8b35e336c11e1589a"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/requirements.py","mode":33188,"size":4355,"sha256":"4a290bd94ca76ec4f4aad63d96daa78277616bfb1fa34c3a5c6161021a12a1a4"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/specifiers.py","mode":33188,"size":28025,"sha256":"4803117abcceddf2b622415909a664bb065a2ff106a8734ecf8a678b8be19cdd"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/utils.py","mode":33188,"size":421,"sha256":"de6e96bcf9ba34dc44f2b9131a69f4afbe41fc66521a0ee291a7f11ec04dd560"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/packaging/version.py","mode":33188,"size":11556,"sha256":"3b01a7c587ebda084dcd8c79f6a588064acadd29c1ea7f997ddd5768ba679ccd"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/pyparsing.py","mode":33188,"size":229867,"sha256":"3e27de2d8dfe5a121c055ccbb6fd14e13fe9c03b4faee061042920e6f2ea6b6f"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/_vendor/six.py","mode":33188,"size":30098,"sha256":"03a85d259563237b7f81e79b67d07352fc11ac85e8d257f0cd094cd8b70ac9ab"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/extern/__init__.py","mode":33188,"size":2487,"sha256":"254b651c7be5c4748db81e295aa363731ee7ea41be7f05e0eea989db33499486"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/extern/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":2345,"sha256":"773e0f374d72a0ba2ccd7e217caca694b9157cb15bd4f8e8d9dafac3acab16f0"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/extern/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":2345,"sha256":"773e0f374d72a0ba2ccd7e217caca694b9157cb15bd4f8e8d9dafac3acab16f0"},{"path":"/usr/lib/python3.6/site-packages/pkg_resources/py31compat.py","mode":33188,"size":600,"sha256":"fb2b15aa8c4b7ad0272fde2e33490792898a4130b52592cdd99523a9484c78a1"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/DESCRIPTION.rst","mode":33188,"size":1547,"sha256":"98eb24e2e1f899add2ed18c693c9b8904310b2c48067123c0e3d59f046479310"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/INSTALLER","mode":33188,"size":4,"sha256":"ceebae7b8927a3227e5303cf5e0f1f7b34bb542ad7250ac03fbcde36ec2f1508"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/LICENSE.txt","mode":33188,"size":1078,"sha256":"c32a3ac395af6321efd28be73d06a00f0db6ab887d1c21d4fec46128d2056d5a"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/METADATA","mode":33188,"size":3028,"sha256":"807787bb84b7a18c0cae00ae482f3c0a104021a64e933516ccaa60f57a2676ba"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/RECORD","mode":33188,"size":13565,"sha256":"55ad01c2a0bedb38b03f4361a25aceb33b6e7e0a0989df50a56180c1dfd92d2e"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/WHEEL","mode":33188,"size":110,"sha256":"91db0dfb93890192221cdfa23b846197cd8ac92d1b0d67f8b81c0c6e435a7ebf"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/dependency_links.txt","mode":33188,"size":239,"sha256":"1e5902164a0ae536d9e4430b6cb29884b718fc4df5901583f13a96d848266ad4"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/entry_points.txt","mode":33188,"size":2990,"sha256":"8c1a826039558e5fffb23605197a35250188300605244fa9ad8594b6731911ec"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/metadata.json","mode":33188,"size":4969,"sha256":"db4d37e32496110ccdb5bfc2ca0e84633a197e9623c87b0a95e59e947fbe44ea"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/top_level.txt","mode":33188,"size":38,"sha256":"d87517555c00e0f7dfd7181316bdc6b135d729a3da3babe51baa0d27fe2ee138"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/zip-safe","mode":33188,"size":1,"sha256":"01ba4719c80b6fe911b091a7c05124b64eeece964e09c058ef8f9805daca546b"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__init__.py","mode":33188,"size":5700,"sha256":"59621d09b1499d9f5f6686960cdff1d6f0c0fd1926f92735e622af3ed218285b"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":6219,"sha256":"7d671b0124725d2486b83a7d18bb30a8ff0ea4b841f08fa0fabc858528866c21"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":6219,"sha256":"7d671b0124725d2486b83a7d18bb30a8ff0ea4b841f08fa0fabc858528866c21"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/archive_util.cpython-36.opt-1.pyc","mode":33188,"size":5067,"sha256":"34d23813c9b1ef2eaf24db0f25f053ff687b858b75e730ce7333a6f36d954c78"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/archive_util.cpython-36.pyc","mode":33188,"size":5067,"sha256":"34d23813c9b1ef2eaf24db0f25f053ff687b858b75e730ce7333a6f36d954c78"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/build_meta.cpython-36.opt-1.pyc","mode":33188,"size":5750,"sha256":"d3c6ae623d5ce3b4d4986062b60acfe2edc61a9558a0c39807ee5ecac3f5e512"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/build_meta.cpython-36.pyc","mode":33188,"size":5840,"sha256":"d3e85a754a3256cb1e7a58245d601986d09a3044d2a78cd2bbe52162e79a17f5"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/config.cpython-36.opt-1.pyc","mode":33188,"size":14991,"sha256":"49845e2255066c869f7733bd1ca9a75488c5cde4cd720104893daf27702cd3fa"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/config.cpython-36.pyc","mode":33188,"size":14991,"sha256":"49845e2255066c869f7733bd1ca9a75488c5cde4cd720104893daf27702cd3fa"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/dep_util.cpython-36.opt-1.pyc","mode":33188,"size":786,"sha256":"5e144ea88d7667b32be114c7fde8fb29a2b2eaa636ab59a3db4bdab6b1dcab74"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/dep_util.cpython-36.pyc","mode":33188,"size":786,"sha256":"5e144ea88d7667b32be114c7fde8fb29a2b2eaa636ab59a3db4bdab6b1dcab74"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/depends.cpython-36.opt-1.pyc","mode":33188,"size":5212,"sha256":"e481c633fc3ea82b487ffe817ab303ed7f29922b00536cfb71d1dbf5ef20fdad"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/depends.cpython-36.pyc","mode":33188,"size":5212,"sha256":"e481c633fc3ea82b487ffe817ab303ed7f29922b00536cfb71d1dbf5ef20fdad"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/dist.cpython-36.opt-1.pyc","mode":33188,"size":36761,"sha256":"e65a3b4af736f9bb6d01660e22d0faa657ca2170c5b36f00cbc901e1da9d2f88"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/dist.cpython-36.pyc","mode":33188,"size":36806,"sha256":"5b5dc961833dd73db98ceb02fe896e7a81dbb22e9fcd2989498de80c1951a31b"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/extension.cpython-36.opt-1.pyc","mode":33188,"size":1906,"sha256":"5bcc6cf5bdd6c2253e843be9c8c1668d16c17348181d41df7df5b3c039952f89"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/extension.cpython-36.pyc","mode":33188,"size":1906,"sha256":"5bcc6cf5bdd6c2253e843be9c8c1668d16c17348181d41df7df5b3c039952f89"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/glibc.cpython-36.opt-1.pyc","mode":33188,"size":1476,"sha256":"39ac990ab1be2fc333e93ddf9d60656f379ce1c24b1f1c4261fefd39d74eea6d"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/glibc.cpython-36.pyc","mode":33188,"size":1476,"sha256":"39ac990ab1be2fc333e93ddf9d60656f379ce1c24b1f1c4261fefd39d74eea6d"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/glob.cpython-36.opt-1.pyc","mode":33188,"size":3722,"sha256":"8d850438b68c80ecd8c004dbdfc887f693e90eaa9781bf602840d8961c5a9923"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/glob.cpython-36.pyc","mode":33188,"size":3774,"sha256":"52cbb68debd96f28a3330d7edb942fd7aac8dbd294b36c2f838cb4c4a4c452cd"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/launch.cpython-36.opt-1.pyc","mode":33188,"size":785,"sha256":"b66c42e6a44edf7367e8c9abf6a3ce66b7581ffbf7838c4dbec6c951338bb450"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/launch.cpython-36.pyc","mode":33188,"size":785,"sha256":"b66c42e6a44edf7367e8c9abf6a3ce66b7581ffbf7838c4dbec6c951338bb450"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/lib2to3_ex.cpython-36.opt-1.pyc","mode":33188,"size":2364,"sha256":"db8bd27cde66f07b2a88007f02ee2b5cfbd3508c45d98af0fe3af98a6853af70"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/lib2to3_ex.cpython-36.pyc","mode":33188,"size":2364,"sha256":"db8bd27cde66f07b2a88007f02ee2b5cfbd3508c45d98af0fe3af98a6853af70"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/monkey.cpython-36.opt-1.pyc","mode":33188,"size":4603,"sha256":"e83a7ebb28915bc574c549ecf8c6520d419c0c701121c112e954dc0ce4300639"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/monkey.cpython-36.pyc","mode":33188,"size":4603,"sha256":"e83a7ebb28915bc574c549ecf8c6520d419c0c701121c112e954dc0ce4300639"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/msvc.cpython-36.opt-1.pyc","mode":33188,"size":34471,"sha256":"7b250a93d5fc2c09ea0702654cf6b504f9bf677b9c5b44c4962206b43be6c8c3"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/msvc.cpython-36.pyc","mode":33188,"size":34471,"sha256":"7b250a93d5fc2c09ea0702654cf6b504f9bf677b9c5b44c4962206b43be6c8c3"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/namespaces.cpython-36.opt-1.pyc","mode":33188,"size":3609,"sha256":"cadde9685f1103730d5538ae54fd6b0fb15dc217cf23501e3b2eb22d71d5dbf3"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/namespaces.cpython-36.pyc","mode":33188,"size":3609,"sha256":"cadde9685f1103730d5538ae54fd6b0fb15dc217cf23501e3b2eb22d71d5dbf3"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/package_index.cpython-36.opt-1.pyc","mode":33188,"size":32185,"sha256":"bda8ca7e423781edb5dba5c81928ad4fb1349c9b29fca62ccf6e4b2682befe9b"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/package_index.cpython-36.pyc","mode":33188,"size":32185,"sha256":"bda8ca7e423781edb5dba5c81928ad4fb1349c9b29fca62ccf6e4b2682befe9b"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/pep425tags.cpython-36.opt-1.pyc","mode":33188,"size":7273,"sha256":"b66771bddaea61cc4e4b94ca1c1be488d942b59dd8c9807c4d4928f98ccbd822"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/pep425tags.cpython-36.pyc","mode":33188,"size":7273,"sha256":"847186f2521fbb956473fbc6252258bead6ad045b4f32e82be0d25fd510b381c"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/py27compat.cpython-36.opt-1.pyc","mode":33188,"size":742,"sha256":"50c41dea4b8e8696e774b594bbf2c898120e5cd7eb0ab72c760894be1ef30ff6"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/py27compat.cpython-36.pyc","mode":33188,"size":742,"sha256":"50c41dea4b8e8696e774b594bbf2c898120e5cd7eb0ab72c760894be1ef30ff6"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/py31compat.cpython-36.opt-1.pyc","mode":33188,"size":1481,"sha256":"115cc9bb095711d4406f8f06f8af8eda9cdfd77997d2b0112c28e275de960762"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/py31compat.cpython-36.pyc","mode":33188,"size":1481,"sha256":"115cc9bb095711d4406f8f06f8af8eda9cdfd77997d2b0112c28e275de960762"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/py33compat.cpython-36.opt-1.pyc","mode":33188,"size":1334,"sha256":"b0dc7b89958eb99a6c04581800d41050d2cf0fd6a70440ccc6068403389b5595"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/py33compat.cpython-36.pyc","mode":33188,"size":1334,"sha256":"b0dc7b89958eb99a6c04581800d41050d2cf0fd6a70440ccc6068403389b5595"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/py36compat.cpython-36.opt-1.pyc","mode":33188,"size":2138,"sha256":"41205350ca1cfbf21c82b0209553c5e9cd901bf077cbe6ce3ebc6dd560876e80"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/py36compat.cpython-36.pyc","mode":33188,"size":2138,"sha256":"41205350ca1cfbf21c82b0209553c5e9cd901bf077cbe6ce3ebc6dd560876e80"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/sandbox.cpython-36.opt-1.pyc","mode":33188,"size":15654,"sha256":"d86d65cddbc75e6b2b33cd98b169b38ef9452ea080750305ed123b693605c241"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/sandbox.cpython-36.pyc","mode":33188,"size":15654,"sha256":"d86d65cddbc75e6b2b33cd98b169b38ef9452ea080750305ed123b693605c241"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/site-patch.cpython-36.opt-1.pyc","mode":33188,"size":1437,"sha256":"9cead081ea6b2674606ad4b73e359258add48b9cfcd01e55c2621eef5e968fd8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/site-patch.cpython-36.pyc","mode":33188,"size":1437,"sha256":"9cead081ea6b2674606ad4b73e359258add48b9cfcd01e55c2621eef5e968fd8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/ssl_support.cpython-36.opt-1.pyc","mode":33188,"size":6717,"sha256":"b8ed93569f1cf78d16e96be2e92fb6f221ebd17d3b55f6fe0a070a31bb488b81"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/ssl_support.cpython-36.pyc","mode":33188,"size":6717,"sha256":"b8ed93569f1cf78d16e96be2e92fb6f221ebd17d3b55f6fe0a070a31bb488b81"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/unicode_utils.cpython-36.opt-1.pyc","mode":33188,"size":1100,"sha256":"667cb1e874475cb2199d723bb1a9033cad5f6752012c58d39b9c6b20031787f2"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/unicode_utils.cpython-36.pyc","mode":33188,"size":1100,"sha256":"667cb1e874475cb2199d723bb1a9033cad5f6752012c58d39b9c6b20031787f2"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/version.cpython-36.opt-1.pyc","mode":33188,"size":259,"sha256":"d0762d631b95d7b33120cbf6beee4fc3a54386edf0d4b529c4486ccc65bd92e0"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/version.cpython-36.pyc","mode":33188,"size":259,"sha256":"d0762d631b95d7b33120cbf6beee4fc3a54386edf0d4b529c4486ccc65bd92e0"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/wheel.cpython-36.opt-1.pyc","mode":33188,"size":6153,"sha256":"7f2c2ce0e4b1122073ecac1f5ad800a83bebc809d625a2fa8b2deb26ffc222c8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/wheel.cpython-36.pyc","mode":33188,"size":6181,"sha256":"6701af95ae00d985abb8d455aa3970803a1923c9938fbe1247b4c72d2abb4915"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/windows_support.cpython-36.opt-1.pyc","mode":33188,"size":942,"sha256":"473c609247f1eb3087d7052e8d87eb6e951602743838c78bab4e4f2568e0754e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/__pycache__/windows_support.cpython-36.pyc","mode":33188,"size":942,"sha256":"473c609247f1eb3087d7052e8d87eb6e951602743838c78bab4e4f2568e0754e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/__init__.py","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":113,"sha256":"d56754de562d9bd3d3f0ff80cac164add19e93a745a2ab37554bea2f4e6d776f"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":113,"sha256":"d56754de562d9bd3d3f0ff80cac164add19e93a745a2ab37554bea2f4e6d776f"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/__pycache__/pyparsing.cpython-36.opt-1.pyc","mode":33188,"size":201035,"sha256":"64ebb24cfe8034f5c3182a01afc46c4a15c1634b340bb94500071c2bad91f2e2"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/__pycache__/pyparsing.cpython-36.pyc","mode":33188,"size":201035,"sha256":"64ebb24cfe8034f5c3182a01afc46c4a15c1634b340bb94500071c2bad91f2e2"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/__pycache__/six.cpython-36.opt-1.pyc","mode":33188,"size":24410,"sha256":"6fb30c6e2705fb969ceff9eab10c18748068fef263ef518b9d1fe2501209f9d8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/__pycache__/six.cpython-36.pyc","mode":33188,"size":24410,"sha256":"6fb30c6e2705fb969ceff9eab10c18748068fef263ef518b9d1fe2501209f9d8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__about__.py","mode":33188,"size":720,"sha256":"ce47023d337fe9370b5b436b960d35efaf91d5043f5953d39bcb33d51e3e1e33"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__init__.py","mode":33188,"size":513,"sha256":"fef35a7394ebcf0b2bcdb38521b17ee5c1ea73f63668f4f60fbceb211d3a04ea"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/__about__.cpython-36.opt-1.pyc","mode":33188,"size":639,"sha256":"5d87f9ee0f14e4a17b2e66231424512e34f56f3bb36edd137afc43ac05f0b7fe"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/__about__.cpython-36.pyc","mode":33188,"size":639,"sha256":"5d87f9ee0f14e4a17b2e66231424512e34f56f3bb36edd137afc43ac05f0b7fe"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":477,"sha256":"aeb4a144efafa928ded168646691327511b5c7beb352e961a328c86cd9d62910"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":477,"sha256":"aeb4a144efafa928ded168646691327511b5c7beb352e961a328c86cd9d62910"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/_compat.cpython-36.opt-1.pyc","mode":33188,"size":924,"sha256":"77bb5bfee7e585f9504f3fa1efffe642ee857cc79f8b7dd680ac728006e973e8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/_compat.cpython-36.pyc","mode":33188,"size":924,"sha256":"77bb5bfee7e585f9504f3fa1efffe642ee857cc79f8b7dd680ac728006e973e8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/_structures.cpython-36.opt-1.pyc","mode":33188,"size":2781,"sha256":"6e18462d4d0ae8aa003875739f5670caac399d1d206308fc4062a392a8505ba2"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/_structures.cpython-36.pyc","mode":33188,"size":2781,"sha256":"6e18462d4d0ae8aa003875739f5670caac399d1d206308fc4062a392a8505ba2"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/markers.cpython-36.opt-1.pyc","mode":33188,"size":8695,"sha256":"5ad505f5df542d6272de9dab40cd8a7ddd63bcd7edf14ce84dc420c5a8a482aa"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/markers.cpython-36.pyc","mode":33188,"size":8801,"sha256":"898e77a4e4c393f3908f4c8f12549a52f06cda5426c22f77e984a812bab99b34"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/requirements.cpython-36.opt-1.pyc","mode":33188,"size":3794,"sha256":"7f70af38900424ca21d9d943e5a4b061da86f9342dad0dc6232a976804bade2c"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/requirements.cpython-36.pyc","mode":33188,"size":3794,"sha256":"7f70af38900424ca21d9d943e5a4b061da86f9342dad0dc6232a976804bade2c"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/specifiers.cpython-36.opt-1.pyc","mode":33188,"size":19743,"sha256":"5e77ace481863e5ff1acd208442b80eb3c21c6f3c5dc389ad0acddfb46738bb7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/specifiers.cpython-36.pyc","mode":33188,"size":19743,"sha256":"5e77ace481863e5ff1acd208442b80eb3c21c6f3c5dc389ad0acddfb46738bb7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/utils.cpython-36.opt-1.pyc","mode":33188,"size":408,"sha256":"81c51f53301119280092c54513df6d59dcaa23f5ee2d8c003107567f50677c57"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/utils.cpython-36.pyc","mode":33188,"size":408,"sha256":"81c51f53301119280092c54513df6d59dcaa23f5ee2d8c003107567f50677c57"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/version.cpython-36.opt-1.pyc","mode":33188,"size":10518,"sha256":"535dda079048da34043fd35ac2779360938efa04f2112067d010f149d3756fcc"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/__pycache__/version.cpython-36.pyc","mode":33188,"size":10518,"sha256":"535dda079048da34043fd35ac2779360938efa04f2112067d010f149d3756fcc"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/_compat.py","mode":33188,"size":860,"sha256":"562fc0d2b0107876d4f9af57d2db75c909bd46a92041b0d2c73470f16954f640"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/_structures.py","mode":33188,"size":1416,"sha256":"448984089e1cff04e5693618c1960b1c489e6c331a00998ad683c0461c354f9a"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/markers.py","mode":33188,"size":8239,"sha256":"1afa64f44636d3229a31388a81067cc85104a6876a560558b5f7a4a2273562db"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/requirements.py","mode":33188,"size":4343,"sha256":"b78e0cd87556b6bf29848cf63a19c82f3b864f7ad30136a8bdcb55d5da675488"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/specifiers.py","mode":33188,"size":28025,"sha256":"4803117abcceddf2b622415909a664bb065a2ff106a8734ecf8a678b8be19cdd"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/utils.py","mode":33188,"size":421,"sha256":"de6e96bcf9ba34dc44f2b9131a69f4afbe41fc66521a0ee291a7f11ec04dd560"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/packaging/version.py","mode":33188,"size":11556,"sha256":"3b01a7c587ebda084dcd8c79f6a588064acadd29c1ea7f997ddd5768ba679ccd"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/pyparsing.py","mode":33188,"size":229867,"sha256":"3e27de2d8dfe5a121c055ccbb6fd14e13fe9c03b4faee061042920e6f2ea6b6f"},{"path":"/usr/lib/python3.6/site-packages/setuptools/_vendor/six.py","mode":33188,"size":30098,"sha256":"03a85d259563237b7f81e79b67d07352fc11ac85e8d257f0cd094cd8b70ac9ab"},{"path":"/usr/lib/python3.6/site-packages/setuptools/archive_util.py","mode":33188,"size":6592,"sha256":"930f086ff94a8c27273ca35b4bb87c1f3b5154ad1de5169c537aff2917559e63"},{"path":"/usr/lib/python3.6/site-packages/setuptools/build_meta.py","mode":33188,"size":5671,"sha256":"16595a293af5bd22728947918d5244666784691ce162e78d9629ad7306896daf"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__init__.py","mode":33188,"size":594,"sha256":"356cc9d00d4111e9e066955ea94c962cd9b66e4e0fdc5e222f941412b1f2ee40"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":664,"sha256":"3024b8fe1afa016a0257f52000ff22b30c45fa9f94d1354a2c00eb955f9eec31"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":664,"sha256":"3024b8fe1afa016a0257f52000ff22b30c45fa9f94d1354a2c00eb955f9eec31"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/alias.cpython-36.opt-1.pyc","mode":33188,"size":2357,"sha256":"6307b644e7fa51ebebe2b51825b2b41bf719faffd7b58ce3743b90a378966d20"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/alias.cpython-36.pyc","mode":33188,"size":2357,"sha256":"6307b644e7fa51ebebe2b51825b2b41bf719faffd7b58ce3743b90a378966d20"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/bdist_egg.cpython-36.opt-1.pyc","mode":33188,"size":14338,"sha256":"045ee6113a8b5d0c7c085af5eabf9add0306e05c973b4e9c323b223d91631670"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/bdist_egg.cpython-36.pyc","mode":33188,"size":14338,"sha256":"045ee6113a8b5d0c7c085af5eabf9add0306e05c973b4e9c323b223d91631670"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/bdist_rpm.cpython-36.opt-1.pyc","mode":33188,"size":1700,"sha256":"a0b2b2eebb3ddff437024a56065ac229588bfbf3d5fb0152705c2679bb59c01c"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/bdist_rpm.cpython-36.pyc","mode":33188,"size":1700,"sha256":"a0b2b2eebb3ddff437024a56065ac229588bfbf3d5fb0152705c2679bb59c01c"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/bdist_wininst.cpython-36.opt-1.pyc","mode":33188,"size":901,"sha256":"932d3c78fb72fdab7441dfe8b155ffe59920cf0fa21a41299a7b6708910fae8e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/bdist_wininst.cpython-36.pyc","mode":33188,"size":901,"sha256":"932d3c78fb72fdab7441dfe8b155ffe59920cf0fa21a41299a7b6708910fae8e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/build_clib.cpython-36.opt-1.pyc","mode":33188,"size":2372,"sha256":"e8c5ddc069dce440dd131077b26b4e20e4d16718e41492f6be07b977907504c5"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/build_clib.cpython-36.pyc","mode":33188,"size":2372,"sha256":"e8c5ddc069dce440dd131077b26b4e20e4d16718e41492f6be07b977907504c5"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/build_ext.cpython-36.opt-1.pyc","mode":33188,"size":9941,"sha256":"93be45e06c328fb02311952451c323500c289af76486caefe4c5af4772f9001c"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/build_ext.cpython-36.pyc","mode":33188,"size":9971,"sha256":"4fde437b3ea3e1a07b057be9693ee843019abbe52a2f8d87cca28ae7b364d536"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/build_py.cpython-36.opt-1.pyc","mode":33188,"size":8496,"sha256":"e187df78eb437617ca00e52d4ad7866e48743be1a7bf14a4679a87fa67739f36"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/build_py.cpython-36.pyc","mode":33188,"size":8496,"sha256":"e187df78eb437617ca00e52d4ad7866e48743be1a7bf14a4679a87fa67739f36"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/develop.cpython-36.opt-1.pyc","mode":33188,"size":6350,"sha256":"3744a18940e826554e51e9f1b700d6924eb401b11e6c93929e784628a5628fd4"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/develop.cpython-36.pyc","mode":33188,"size":6350,"sha256":"3744a18940e826554e51e9f1b700d6924eb401b11e6c93929e784628a5628fd4"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/dist_info.cpython-36.opt-1.pyc","mode":33188,"size":1317,"sha256":"8ab7022abceb8bd75c43b7bdbcfc754f051e3bcd59e570a18cc986852210ecad"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/dist_info.cpython-36.pyc","mode":33188,"size":1317,"sha256":"8ab7022abceb8bd75c43b7bdbcfc754f051e3bcd59e570a18cc986852210ecad"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/easy_install.cpython-36.opt-1.pyc","mode":33188,"size":64821,"sha256":"d3764f18debd93dc4f14b4e163780acfae352b4bfbd2c836df1a69769df1f84e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/easy_install.cpython-36.pyc","mode":33188,"size":64866,"sha256":"fad65140c35221e136d4356ffb47279ffcad670a912c1728eb86fd96454bbcc6"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/egg_info.cpython-36.opt-1.pyc","mode":33188,"size":20891,"sha256":"b41fb808f11798d9c1d8bdf07ebe6b770583752695547d12e8d7dd118d254ba1"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/egg_info.cpython-36.pyc","mode":33188,"size":20891,"sha256":"b41fb808f11798d9c1d8bdf07ebe6b770583752695547d12e8d7dd118d254ba1"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/install.cpython-36.opt-1.pyc","mode":33188,"size":3897,"sha256":"91a874d869f6925def4559c620a53290b5eae6d20b14b76dda4657558b6874b8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/install.cpython-36.pyc","mode":33188,"size":3897,"sha256":"91a874d869f6925def4559c620a53290b5eae6d20b14b76dda4657558b6874b8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/install_egg_info.cpython-36.opt-1.pyc","mode":33188,"size":2362,"sha256":"b2261c3b378ef18e93bc493857d6448ed72e4a170a3eb2774b588e8bfbfc2e49"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/install_egg_info.cpython-36.pyc","mode":33188,"size":2362,"sha256":"b2261c3b378ef18e93bc493857d6448ed72e4a170a3eb2774b588e8bfbfc2e49"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/install_lib.cpython-36.opt-1.pyc","mode":33188,"size":3971,"sha256":"c0bd5dc5c01d069b93433b2e5ae79a9eacc87b120c716c4aad5f14ba2056cef8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/install_lib.cpython-36.pyc","mode":33188,"size":4007,"sha256":"746ef37ebfc258efb7a359400716c74bbcbc706fb729db2e9f77c75308f972d1"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/install_scripts.cpython-36.opt-1.pyc","mode":33188,"size":2202,"sha256":"a8d0445b414fa54171feba039ec1af8bef6b78973a3b60446622b2e68f3a6b43"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/install_scripts.cpython-36.pyc","mode":33188,"size":2202,"sha256":"a8d0445b414fa54171feba039ec1af8bef6b78973a3b60446622b2e68f3a6b43"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/py36compat.cpython-36.opt-1.pyc","mode":33188,"size":4547,"sha256":"2b3712ce79c0b092269bf28259c47a738df2cfb93ec9334b1a5a7ff5872e6dc7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/py36compat.cpython-36.pyc","mode":33188,"size":4547,"sha256":"2b3712ce79c0b092269bf28259c47a738df2cfb93ec9334b1a5a7ff5872e6dc7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/register.cpython-36.opt-1.pyc","mode":33188,"size":517,"sha256":"c7d06a1d200c1c15c3a3ee62016a3f40c95c4c0bc81bce658c21d6a2639cb502"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/register.cpython-36.pyc","mode":33188,"size":517,"sha256":"c7d06a1d200c1c15c3a3ee62016a3f40c95c4c0bc81bce658c21d6a2639cb502"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/rotate.cpython-36.opt-1.pyc","mode":33188,"size":2503,"sha256":"52976e5786459623b0b4ffa54551c369bb791d7aef667c6f822e5d0f3b417dc4"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/rotate.cpython-36.pyc","mode":33188,"size":2503,"sha256":"52976e5786459623b0b4ffa54551c369bb791d7aef667c6f822e5d0f3b417dc4"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/saveopts.cpython-36.opt-1.pyc","mode":33188,"size":848,"sha256":"138cf00d8097c9527467bbfef86d29bb2e3996f358bafa4be2832cf78d01eba6"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/saveopts.cpython-36.pyc","mode":33188,"size":848,"sha256":"138cf00d8097c9527467bbfef86d29bb2e3996f358bafa4be2832cf78d01eba6"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/sdist.cpython-36.opt-1.pyc","mode":33188,"size":6312,"sha256":"a19f5ddda19394f6c1a72c52d1b4c9c425b52523ede5138ccd3323659437a01e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/sdist.cpython-36.pyc","mode":33188,"size":6312,"sha256":"a19f5ddda19394f6c1a72c52d1b4c9c425b52523ede5138ccd3323659437a01e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/setopt.cpython-36.opt-1.pyc","mode":33188,"size":4526,"sha256":"8e141f42f14fa0d651ea44252be2a27d73df9f24ca3f62991b1fdd2c26f0a158"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/setopt.cpython-36.pyc","mode":33188,"size":4526,"sha256":"8e141f42f14fa0d651ea44252be2a27d73df9f24ca3f62991b1fdd2c26f0a158"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/test.cpython-36.opt-1.pyc","mode":33188,"size":8085,"sha256":"e76bf8707d46b4db871c361e59eb1e70d93fa0133aaa7752199ea4f47ae0dedd"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/test.cpython-36.pyc","mode":33188,"size":8085,"sha256":"e76bf8707d46b4db871c361e59eb1e70d93fa0133aaa7752199ea4f47ae0dedd"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/upload.cpython-36.opt-1.pyc","mode":33188,"size":1315,"sha256":"46e28e2ff8f0988571d6f8e577d018d47ec537b88a87f6c00b82fe454c0587f6"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/upload.cpython-36.pyc","mode":33188,"size":1315,"sha256":"46e28e2ff8f0988571d6f8e577d018d47ec537b88a87f6c00b82fe454c0587f6"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/upload_docs.cpython-36.opt-1.pyc","mode":33188,"size":6000,"sha256":"990e98ce0b74148b1df9f6c24b1da63399272aa65afed7dd983793b9fbb7f3a7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/__pycache__/upload_docs.cpython-36.pyc","mode":33188,"size":6024,"sha256":"6fa3014672a5b90c8bec019d8008e047d0fa8fccde0649840588da52ffd63f1f"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/alias.py","mode":33188,"size":2426,"sha256":"2a3a44d2ccff483207bf77e965c2102beb02909cfe4ab0ba1a6ba0e9bf4d91cf"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/bdist_egg.py","mode":33188,"size":18185,"sha256":"450f61f019925695ca250493de2fdbfec9b4f7767e6825db7cc04433622b23e4"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/bdist_rpm.py","mode":33188,"size":1508,"sha256":"07b9744e7cc219bfb49cb966eab4b4d2358b9288c04b05667615b6c39433fc09"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/bdist_wininst.py","mode":33188,"size":637,"sha256":"ffa773de5a41d6d636d342f128f2cceea8304c271e38c81a58517e8d6dbea66d"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/build_clib.py","mode":33188,"size":4484,"sha256":"6d0f5a06bfb96523bef5f1ac1ac0cbcf49a79c5b5e1d46677ed54b921bc70ead"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/build_ext.py","mode":33188,"size":13173,"sha256":"3c2440676c589eac84a1fec414db69298974b19cd3d2a74a50d4c7dec51d3ea9"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/build_py.py","mode":33188,"size":9596,"sha256":"c96c9869a4bd177a3d25b21cce7d3ae00e60d42e7f5222910f119a4ea61bb4b1"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/develop.py","mode":33188,"size":8046,"sha256":"c0a6cec36fea52f703b62da5666b716c39986f9e3200089b131cd722f4e8cfe0"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/dist_info.py","mode":33188,"size":960,"sha256":"e6dea439fadd8002d3f8fde882cb3a3c5f64f8b7b27acb9ec9cba4ddd5326672"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/easy_install.py","mode":33188,"size":87026,"sha256":"13ed52731e127c22cb64cd9eea4f00d93f9ba39703317a8b9e2835da4c60532f"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/egg_info.py","mode":33188,"size":24800,"sha256":"ddbe58dedfdb97fcd94429269468b78a0bd1cdef6839ac5df9d55fdb0d4504e7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/install.py","mode":33188,"size":4683,"sha256":"6b4119a4bfc0f3ae8a11d86271319bbb20ff4d8975b3291fcddaeb8becdacd3e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/install_egg_info.py","mode":33188,"size":2203,"sha256":"6cc81e21e4625f34380c018f575df6f24723c108c78ce594e059e00162d5efc4"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/install_lib.py","mode":33188,"size":3840,"sha256":"d759b17f40a1d7636cb98c12f0f1f05c146fca1ebbd5000ce1c4d187b7a9cc6d"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/install_scripts.py","mode":33188,"size":2439,"sha256":"503d2b119ebceb599362121dcdcb2a2a7525f0fa33a1c5d697d5414355535a77"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/launcher manifest.xml","mode":33188,"size":628,"sha256":"c652db8d6ac1d35b4a0b4fa195590e2a48923dbccc9a5d9e38fb49fee7029db1"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/py36compat.py","mode":33188,"size":4986,"sha256":"4b38d970ec45ef3745513e3b66fda7ec03371fc9280f2b3fd0ea52fa7f6021f7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/register.py","mode":33188,"size":270,"sha256":"6c794c9b5aa605b49d6a14ce4fcc3a52103e120790233ee9e9c0fea8e6ae6a22"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/rotate.py","mode":33188,"size":2164,"sha256":"728e42d44908ecfd06193e93ab3f93d92223d8b0494d95d810ba666a8e9de0a4"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/saveopts.py","mode":33188,"size":658,"sha256":"cdaed00817108a628aae259ca0271b8713e3533df481207be33b932f8ef1a4fe"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/sdist.py","mode":33188,"size":6711,"sha256":"a1b0d37b60665add8f96714f65987b7b42d6bde984b1b0823bd33386b4d98e6f"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/setopt.py","mode":33188,"size":5085,"sha256":"353583cb1fa08c317eb717f874ee7beececb3b31d5a0a47432adf7ac5c5a46bf"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/test.py","mode":33188,"size":9214,"sha256":"31e04071751e3c68cf2aa8f3e33bd3ac76ad2ef36c8e53c571a82ddd79c561d9"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/upload.py","mode":33188,"size":1172,"sha256":"8b581f22d6779d03a7e452976fcb4b0b629dede282f2558ee1b744e8da86a44e"},{"path":"/usr/lib/python3.6/site-packages/setuptools/command/upload_docs.py","mode":33188,"size":7311,"sha256":"a17886a6533f71428bc04e02596c3df11cc2b9f02ef2d061302f7b19e805726b"},{"path":"/usr/lib/python3.6/site-packages/setuptools/config.py","mode":33188,"size":18006,"sha256":"dcbf70c05d7fba9aecc87b141d75ecc8b989500e4721ccc9610d811732d68dcd"},{"path":"/usr/lib/python3.6/site-packages/setuptools/dep_util.py","mode":33188,"size":935,"sha256":"7e08b1bc2d51eec1f7af5de4b727fb3741402e8a845cbd5c05aae6369484a168"},{"path":"/usr/lib/python3.6/site-packages/setuptools/depends.py","mode":33188,"size":5837,"sha256":"842f1020370cdd50e9457bd1540e8e7cbf406907f1be1c4770dff0eac03236af"},{"path":"/usr/lib/python3.6/site-packages/setuptools/dist.py","mode":33188,"size":42613,"sha256":"d63de4b8d10669a0335b3d222d622dc7388dc894d90bc3207137cc67853859eb"},{"path":"/usr/lib/python3.6/site-packages/setuptools/extension.py","mode":33188,"size":1729,"sha256":"b9cea71c8f8cc7098d08d3db522067c9b4b2aa1a49aa36e1bce43e7a676fb7f1"},{"path":"/usr/lib/python3.6/site-packages/setuptools/extern/__init__.py","mode":33188,"size":2499,"sha256":"d9e28cb01330b19aa894871806d2d9537b7deaceb14933f83d368d7cce4ff88d"},{"path":"/usr/lib/python3.6/site-packages/setuptools/extern/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":2353,"sha256":"f1ba04477b1f6bd1a1ff170d779c07ef91ead7cf0878fffbc7f4a0acca442ae7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/extern/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":2353,"sha256":"f1ba04477b1f6bd1a1ff170d779c07ef91ead7cf0878fffbc7f4a0acca442ae7"},{"path":"/usr/lib/python3.6/site-packages/setuptools/glibc.py","mode":33188,"size":3146,"sha256":"5fae15bc63cbd806d444ac1846c5893975c60183a217fbf6aa2c5e4e40142ee5"},{"path":"/usr/lib/python3.6/site-packages/setuptools/glob.py","mode":33188,"size":5207,"sha256":"63e7e9bfcc1d1d9ceff433c2686002a4c481589e9a9aaff57b447f8bcfde978c"},{"path":"/usr/lib/python3.6/site-packages/setuptools/launch.py","mode":33188,"size":787,"sha256":"b1dede8f0841a1c083c7fc06f6b22cd0e699f07b6698553c642e8847f4b42ef8"},{"path":"/usr/lib/python3.6/site-packages/setuptools/lib2to3_ex.py","mode":33188,"size":2013,"sha256":"b797b5da16d1da98bd5787b35834c1e0933e0084949c63a499c9d81de937c638"},{"path":"/usr/lib/python3.6/site-packages/setuptools/monkey.py","mode":33188,"size":5261,"sha256":"1ffc89f7512d0d6bb6d2fe49b0498578372489854c8691379cc704771c5df888"},{"path":"/usr/lib/python3.6/site-packages/setuptools/msvc.py","mode":33188,"size":40877,"sha256":"f04895f72a5bdc440942cb0f707d4765b74db1b46faac16727bc0f1441b0148a"},{"path":"/usr/lib/python3.6/site-packages/setuptools/namespaces.py","mode":33188,"size":3199,"sha256":"17436b6eff0a093d8eaceeebc1ad37a26e0de0664a0259dc7beaebf9c80341af"},{"path":"/usr/lib/python3.6/site-packages/setuptools/package_index.py","mode":33188,"size":40136,"sha256":"c21b18a1006d1ad40c9b96df02261e6c660b325f876840a13e8ac050477acdd4"},{"path":"/usr/lib/python3.6/site-packages/setuptools/pep425tags.py","mode":33188,"size":10873,"sha256":"23b9715a9cbd5ca10b049d02558893ece3d6d2190115ed243696c40705d5fd74"},{"path":"/usr/lib/python3.6/site-packages/setuptools/py27compat.py","mode":33188,"size":536,"sha256":"de6c3144c0e4e50e4ed6b49738445b4035e116ac032618548ad7cc5bfaa9502a"},{"path":"/usr/lib/python3.6/site-packages/setuptools/py31compat.py","mode":33188,"size":1192,"sha256":"5ee5351c2b0613fdf31af051221630da207e2210852b8f8fc70fe3322a9d3559"},{"path":"/usr/lib/python3.6/site-packages/setuptools/py33compat.py","mode":33188,"size":1182,"sha256":"34a4bce279782e32c8a1a77a3907e09b28199f898cbeba24fdbd4dd6dcde6dec"},{"path":"/usr/lib/python3.6/site-packages/setuptools/py36compat.py","mode":33188,"size":2891,"sha256":"5540d6c66bb9aede101e519346d005bba5b98ef7cbe960637830337a8072d0e3"},{"path":"/usr/lib/python3.6/site-packages/setuptools/sandbox.py","mode":33188,"size":14276,"sha256":"f546f07c42f9418e37ea8308d4bb455a8861a19f94cf01ef1b2663507fea864c"},{"path":"/usr/lib/python3.6/site-packages/setuptools/script (dev).tmpl","mode":33188,"size":201,"sha256":"7fb311d7b7539336aa90231256c7b2382315acf55231d99342c681f1c6737ee2"},{"path":"/usr/lib/python3.6/site-packages/setuptools/script.tmpl","mode":33188,"size":138,"sha256":"5864ede6989eccedbb73e0dbc7a9794384f715fdb4039cfbf3bda1bf76808586"},{"path":"/usr/lib/python3.6/site-packages/setuptools/site-patch.py","mode":33188,"size":2307,"sha256":"055b7ac88ac33172687e503927a0c921cb0951f5bf5c479584ecde9534c50cfe"},{"path":"/usr/lib/python3.6/site-packages/setuptools/ssl_support.py","mode":33188,"size":8492,"sha256":"6010c9b026634a9eb60968f19929247bd927f6b8471e3db90aeb3ace12515b77"},{"path":"/usr/lib/python3.6/site-packages/setuptools/unicode_utils.py","mode":33188,"size":996,"sha256":"34e899ff9843ef603ac3ee30563f1ac0714cde7e752a6c3521cfefc75e5716ac"},{"path":"/usr/lib/python3.6/site-packages/setuptools/version.py","mode":33188,"size":144,"sha256":"a20fdcb9941bd1023aba429915f6563e5af51e02413cf9f6bceda6fdb23d6531"},{"path":"/usr/lib/python3.6/site-packages/setuptools/wheel.py","mode":33188,"size":7778,"sha256":"d95efe5c60f48d116f10ea376eda65d48ee4530699214166aa701561ea0cc0fb"},{"path":"/usr/lib/python3.6/site-packages/setuptools/windows_support.py","mode":33188,"size":714,"sha256":"e46adfa923f6f9d2c6268653ab683a7422a4c90c716b69f92108979490a86041"},{"path":"/usr/share/licenses/platform-python-setuptools/LICENSE","mode":33188,"size":1078,"sha256":"c32a3ac395af6321efd28be73d06a00f0db6ab887d1c21d4fec46128d2056d5a"}]}},{"name":"popt","version":"1.16-14.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:popt:popt:1.16-14.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:popt:1.16-14.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/popt@0:1.16-14.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"popt","version":"1.16","epoch":0,"architecture":"x86_64","release":"14.el8","sourceRpm":"popt-1.16-14.el8.src.rpm","size":128374,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/84/9c7ba88f28eebc110436dc7683766f044ab4a8","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/libpopt.so.0","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/libpopt.so.0.0.0","mode":33261,"size":56112,"sha256":"d724c14290609379289e9e59973a53368a24fe3be08b071fd93c35cba39ba114"},{"path":"/usr/share/licenses/popt/COPYING","mode":33188,"size":1277,"sha256":"518d4f2a05064cb9a8ec0ea02e86408af4feed6916f78ef42171465db8b383c5"}]}},{"name":"procps-ng","version":"3.3.15-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:procps-ng:procps-ng:3.3.15-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:procps-ng:3.3.15-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/procps-ng@0:3.3.15-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"procps-ng","version":"3.3.15","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"procps-ng-3.3.15-1.el8.src.rpm","size":938380,"license":"GPL+ and GPLv2 and GPLv2+ and GPLv3+ and LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/free","mode":33261,"size":23000,"sha256":"48cbd22aa4402ff9906916956f4708b2ffc04a4e7e1e0dfd43ea1a23ea8828a5"},{"path":"/usr/bin/pgrep","mode":33261,"size":31240,"sha256":"30b03a2a040119fbee00deefe8bf275985e563ff84fca5d010fe4a7a95ae0eea"},{"path":"/usr/bin/pidof","mode":33261,"size":18376,"sha256":"6ca50f631db80f2a0f53298c04bfc2cf1db99a0f42f034e77d60b9fd9dc073e1"},{"path":"/usr/bin/pkill","mode":33261,"size":31240,"sha256":"0603814ebb3cac8ae2867a07bab75e1e89dca20f3dd6ba21ef0d2715c696f120"},{"path":"/usr/bin/pmap","mode":33261,"size":34864,"sha256":"7c01f26201b9ec77b9de7d2c477e0cd5a68ca788bea97f0e2fa767166137d0a8"},{"path":"/usr/bin/ps","mode":33261,"size":142216,"sha256":"4abc5eb310f5c22b1a1dcdaef59a6c5e19e8532bd09c0a2774bb6d40bfec947b"},{"path":"/usr/bin/pwdx","mode":33261,"size":14280,"sha256":"44382195edd3af090bf895134cbb219d14969c7facf06a0845a94fcef5b9c5c1"},{"path":"/usr/bin/skill","mode":33261,"size":31608,"sha256":"fcef04e281415fb8c49488ba4f1954cafe8ff8a412c43631b5e23f520bd6b4f6"},{"path":"/usr/bin/slabtop","mode":33261,"size":23048,"sha256":"e97536356c7220b0d3ef959cbeafd5a7908b048fa60dfd1a6039b0d25b45c901"},{"path":"/usr/bin/snice","mode":33261,"size":31608,"sha256":"73510a284f1f2da397d2e62ef4b77320f50a11ad179eea5568c3c5fbf8657ede"},{"path":"/usr/bin/tload","mode":33261,"size":18856,"sha256":"08b98c8df3ffff0c1ce11c9b656a33ce6c1c2393c6466ef2e994fdc83b268f60"},{"path":"/usr/bin/top","mode":33261,"size":126432,"sha256":"2899bb5acdf22fdf8f483fec168ab7552cf56c253ea03067a5e7c2a77f78c308"},{"path":"/usr/bin/uptime","mode":33261,"size":14264,"sha256":"cdfcd9b34a5e57eb7c765291a8654135fc47e065da1f345732f04ff3fa1edb62"},{"path":"/usr/bin/vmstat","mode":33261,"size":39392,"sha256":"fb4a57b15b2b3a862a027ad28e7b517ec409cc9ca4f2de8c24054a16b69cfa5d"},{"path":"/usr/bin/w","mode":33261,"size":22536,"sha256":"14dd47a208d08857f31fb5adf313debc0c25ced24f3603a58415b49b03caded3"},{"path":"/usr/bin/watch","mode":33261,"size":31592,"sha256":"1b1eea1bcc5dfc8b0959e0611a60b83c67bf052566d09161f1d43913ba5cc74f"},{"path":"/usr/lib/.build-id/23/699a74b2f799b29c18421032436b3c83c042e6","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/52/c3c927e2921a1aa3a5c5c53cd13a73247cb484","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/58/7ce00e5ea1aaa7f1aae19c50e59be930885885","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/5b/cc0e9145619a44fbca70ae968c953a3f337f53","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/63/c0ebd7583057ffd285761acceaf971179a9891","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/6d/b9498c811bfaf6e43d7677863f1d5014848c70","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/71/fd359be723167276c2f805925a8f33d40d8f23","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/71/fd359be723167276c2f805925a8f33d40d8f23.1","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/74/723408d0cd07b5cdb9048c8bd97871b10fbff9","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/a9/7cbd4d880126e40ca82e625c6c48723efdf96f","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/.build-id/b3/9757aab72962a79acdf879005d0fd39613ee9d","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/b9/a7ce5cab6f0cc95e98d8d4aca14b8c6e2defb7","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/b9/a7ce5cab6f0cc95e98d8d4aca14b8c6e2defb7.1","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/c4/daca67b1750dbae2d4f94541f758d9cdcbc601","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/d6/3088f8f375e5ca55ba9c4fc610c5fb3b08f3f2","mode":41471,"size":21,"sha256":""},{"path":"/usr/lib/.build-id/dd/088398e2e7521e92002b0642a13ca6bc05bac7","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/e8/10dd44789675fbee4b32060fd7758b263bc28f","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/f5/756841021c6f1ab6e1656035a86e813637d7f7","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib64/libprocps.so.7","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libprocps.so.7.1.0","mode":33261,"size":87928,"sha256":"a0d7d048711cb8c448f379e723c5081584c6d034a00e3254c99f8f987439d774"},{"path":"/usr/sbin/pidof","mode":41471,"size":14,"sha256":""},{"path":"/usr/sbin/sysctl","mode":33261,"size":31264,"sha256":"1ec99a423377f8028296f9622efc7cfad3c1ed6c5dfb3752b6f3e6f70faddfba"},{"path":"/usr/share/licenses/procps-ng/COPYING","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/procps-ng/COPYING.LIB","mode":33188,"size":25381,"sha256":"681e386e44a19d7d0674b4320272c90e66b6610b741e7e6305f8219c42e85366"}]}},{"name":"python3-dnf","version":"4.2.17-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-dnf:python3-dnf:4.2.17-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-dnf:4.2.17-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-dnf@0:4.2.17-6.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"python3-dnf","version":"4.2.17","epoch":0,"architecture":"noarch","release":"6.el8","sourceRpm":"dnf-4.2.17-6.el8.src.rpm","size":1829453,"license":"GPLv2+ and GPLv2 and GPL","vendor":"CentOS","files":[{"path":"/usr/bin/dnf-3","mode":33261,"size":1954,"sha256":"096c1d230ab33c0a4766d6e1b6b3e181cf45cdad9b68953012bcdf1298eb4e01"},{"path":"/usr/lib/python3.6/site-packages/dnf/__init__.py","mode":33188,"size":1389,"sha256":"33f2dd0ffdbd197ee95c114bb1b86c0e458c3babc5acb417ddd368176b2127d6"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":518,"sha256":"c73440580363600d95fa63b7b75f2dd694d275f475692fb0bd8b78b9d4ef4c39"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":518,"sha256":"c73440580363600d95fa63b7b75f2dd694d275f475692fb0bd8b78b9d4ef4c39"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/base.cpython-36.opt-1.pyc","mode":33188,"size":72687,"sha256":"e4253525805ed4175966da197a799efddea4a7133b0ee57bf6c2085f61614a59"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/base.cpython-36.pyc","mode":33188,"size":72967,"sha256":"9a293a7c4b4d542e6d8953a34e488fc5bb9769703945ceff6b6c5f6fa03b09ae"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/callback.cpython-36.opt-1.pyc","mode":33188,"size":3639,"sha256":"bc552d899112935dee305705b088d647894b25611041e553201e7b6bd11289d7"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/callback.cpython-36.pyc","mode":33188,"size":3639,"sha256":"bc552d899112935dee305705b088d647894b25611041e553201e7b6bd11289d7"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/comps.cpython-36.opt-1.pyc","mode":33188,"size":25421,"sha256":"3d00e071c0b23947b321c2213d2ad9971172149efc965685e6f0b2a48d88ae32"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/comps.cpython-36.pyc","mode":33188,"size":26025,"sha256":"cee3aed5151f6a4cc95dabe2a8cc34a4c1d0e49571b896dd9c76d726df5130ce"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/const.cpython-36.opt-1.pyc","mode":33188,"size":1448,"sha256":"09d7a9a57a2cd7df7d77a729bddcbeeb7732b6ebe9764440a22fd5561f4e3ef0"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/const.cpython-36.pyc","mode":33188,"size":1448,"sha256":"09d7a9a57a2cd7df7d77a729bddcbeeb7732b6ebe9764440a22fd5561f4e3ef0"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/crypto.cpython-36.opt-1.pyc","mode":33188,"size":6169,"sha256":"0b6c12de235636b41da09203c1c16d831089c74ead841abedb12f1d6450a9e2a"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/crypto.cpython-36.pyc","mode":33188,"size":6169,"sha256":"0b6c12de235636b41da09203c1c16d831089c74ead841abedb12f1d6450a9e2a"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/dnssec.cpython-36.opt-1.pyc","mode":33188,"size":8928,"sha256":"c9ee43123f8484cfdb27c61161cede8dfcd92373223e8a34cf59a52fa8e4903d"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/dnssec.cpython-36.pyc","mode":33188,"size":8928,"sha256":"c9ee43123f8484cfdb27c61161cede8dfcd92373223e8a34cf59a52fa8e4903d"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/drpm.cpython-36.opt-1.pyc","mode":33188,"size":5284,"sha256":"3a4cee056fb4c416faebdc44f0e5ce3ad2c226a7e7105468ef5462b53d5aca9c"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/drpm.cpython-36.pyc","mode":33188,"size":5284,"sha256":"3a4cee056fb4c416faebdc44f0e5ce3ad2c226a7e7105468ef5462b53d5aca9c"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/exceptions.cpython-36.opt-1.pyc","mode":33188,"size":6847,"sha256":"4bea2a7d0e7e689f01950c695747f88c70874f9da17edab9a760b69029a5cd9c"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/exceptions.cpython-36.pyc","mode":33188,"size":6847,"sha256":"4bea2a7d0e7e689f01950c695747f88c70874f9da17edab9a760b69029a5cd9c"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/goal.cpython-36.opt-1.pyc","mode":33188,"size":233,"sha256":"134ca0687dff731f197d111ef5e30847dedd5b87bc6aacfc3813c8bcf7d79c59"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/goal.cpython-36.pyc","mode":33188,"size":233,"sha256":"134ca0687dff731f197d111ef5e30847dedd5b87bc6aacfc3813c8bcf7d79c59"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/history.cpython-36.opt-1.pyc","mode":33188,"size":260,"sha256":"a9645e41a1c3f40acf8ebf2eaba513355c99b62829df6362e862739ec7e0910e"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/history.cpython-36.pyc","mode":33188,"size":260,"sha256":"a9645e41a1c3f40acf8ebf2eaba513355c99b62829df6362e862739ec7e0910e"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/i18n.cpython-36.opt-1.pyc","mode":33188,"size":9610,"sha256":"4dbb973ce574d506b1832c879df26dcf5a3f140f4e08b78a9baf57138c18dd90"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/i18n.cpython-36.pyc","mode":33188,"size":9610,"sha256":"4dbb973ce574d506b1832c879df26dcf5a3f140f4e08b78a9baf57138c18dd90"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/lock.cpython-36.opt-1.pyc","mode":33188,"size":4098,"sha256":"4cda6779240f7e808adfa9cd719a0ed7c23d67230d54c649646a985d2e6a9915"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/lock.cpython-36.pyc","mode":33188,"size":4098,"sha256":"4cda6779240f7e808adfa9cd719a0ed7c23d67230d54c649646a985d2e6a9915"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/logging.cpython-36.opt-1.pyc","mode":33188,"size":7306,"sha256":"ebb9faa8ef3fc4e31e61b2f7fe1d138de3e793c34a9113583a994d1cab5b22b7"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/logging.cpython-36.pyc","mode":33188,"size":7407,"sha256":"e43b19b6f9811d936694b91f7589a32b0251c07b72cf4913edba7fd0f4e852e7"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/match_counter.cpython-36.opt-1.pyc","mode":33188,"size":4387,"sha256":"b05d1c6590be34036aea63f2e0849b6f8591057f1d93653a88d5cbc15c0fe338"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/match_counter.cpython-36.pyc","mode":33188,"size":4387,"sha256":"b05d1c6590be34036aea63f2e0849b6f8591057f1d93653a88d5cbc15c0fe338"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/package.cpython-36.opt-1.pyc","mode":33188,"size":8312,"sha256":"95a80cad7b9e8ad77017fe2910d759d6a18004d257242f7f8e870634caaeff93"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/package.cpython-36.pyc","mode":33188,"size":8312,"sha256":"95a80cad7b9e8ad77017fe2910d759d6a18004d257242f7f8e870634caaeff93"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/persistor.cpython-36.opt-1.pyc","mode":33188,"size":3912,"sha256":"4a4a7ca82acb58ecd29d3967a9f28dbb4dd763d5564eaddbd80d07e7033431dd"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/persistor.cpython-36.pyc","mode":33188,"size":3912,"sha256":"4a4a7ca82acb58ecd29d3967a9f28dbb4dd763d5564eaddbd80d07e7033431dd"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/plugin.cpython-36.opt-1.pyc","mode":33188,"size":8320,"sha256":"f5bebfcb8929a1b18e4709fb9d73581ee36d743721e4e2a07c5daadde40bd85f"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/plugin.cpython-36.pyc","mode":33188,"size":8320,"sha256":"f5bebfcb8929a1b18e4709fb9d73581ee36d743721e4e2a07c5daadde40bd85f"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/pycomp.cpython-36.opt-1.pyc","mode":33188,"size":2971,"sha256":"e313b4cf9af9495b3adfa3013dc521a18837d1cc9ffa2d021e015a28504c0399"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/pycomp.cpython-36.pyc","mode":33188,"size":2971,"sha256":"e313b4cf9af9495b3adfa3013dc521a18837d1cc9ffa2d021e015a28504c0399"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/query.cpython-36.opt-1.pyc","mode":33188,"size":913,"sha256":"af679c676a43283214c9e3c1c2bd3162ab250c73ca0331830b74c1b7c6905741"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/query.cpython-36.pyc","mode":33188,"size":913,"sha256":"af679c676a43283214c9e3c1c2bd3162ab250c73ca0331830b74c1b7c6905741"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/repo.cpython-36.opt-1.pyc","mode":33188,"size":22150,"sha256":"f2df7ceef00939cf9eeb2182cfaed9248889fac67531b72df421a6c78d8e4088"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/repo.cpython-36.pyc","mode":33188,"size":22150,"sha256":"f2df7ceef00939cf9eeb2182cfaed9248889fac67531b72df421a6c78d8e4088"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/repodict.cpython-36.opt-1.pyc","mode":33188,"size":5572,"sha256":"d99a124c1347abc30cde0b3fdac7e7c203f4c11c9f0c211262b543015b0540f3"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/repodict.cpython-36.pyc","mode":33188,"size":5572,"sha256":"d99a124c1347abc30cde0b3fdac7e7c203f4c11c9f0c211262b543015b0540f3"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/sack.cpython-36.opt-1.pyc","mode":33188,"size":1949,"sha256":"728152d226e5245e749bdd926daf24b1990ff94f4cb600a940d5e8a0b4d2264c"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/sack.cpython-36.pyc","mode":33188,"size":1949,"sha256":"728152d226e5245e749bdd926daf24b1990ff94f4cb600a940d5e8a0b4d2264c"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/selector.cpython-36.opt-1.pyc","mode":33188,"size":241,"sha256":"f96c0220048f676519338688fdc8e2d8cdba6f0ca62a6bd8e569d0a5f77c420a"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/selector.cpython-36.pyc","mode":33188,"size":241,"sha256":"f96c0220048f676519338688fdc8e2d8cdba6f0ca62a6bd8e569d0a5f77c420a"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/subject.cpython-36.opt-1.pyc","mode":33188,"size":276,"sha256":"5fd17742ae8902526ce072f25ad759530473f8bf8abb89f8b2267edf603fee9c"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/subject.cpython-36.pyc","mode":33188,"size":276,"sha256":"5fd17742ae8902526ce072f25ad759530473f8bf8abb89f8b2267edf603fee9c"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/transaction.cpython-36.opt-1.pyc","mode":33188,"size":1639,"sha256":"80ab6fe419eeb327b483d7a76ef974001e418b4a8cf8e014a158ac04668ec009"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/transaction.cpython-36.pyc","mode":33188,"size":1639,"sha256":"80ab6fe419eeb327b483d7a76ef974001e418b4a8cf8e014a158ac04668ec009"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/util.cpython-36.opt-1.pyc","mode":33188,"size":15997,"sha256":"ad5830bac1e3c4d4e5993562061731d2b48e352b2907a19069dda308b127396d"},{"path":"/usr/lib/python3.6/site-packages/dnf/__pycache__/util.cpython-36.pyc","mode":33188,"size":15997,"sha256":"ad5830bac1e3c4d4e5993562061731d2b48e352b2907a19069dda308b127396d"},{"path":"/usr/lib/python3.6/site-packages/dnf/base.py","mode":33188,"size":104852,"sha256":"7379031d6a5acb3177433492cb87ab070fab4c717b98d6f0752d771b83f626c3"},{"path":"/usr/lib/python3.6/site-packages/dnf/callback.py","mode":33188,"size":3724,"sha256":"06b558609a0ab85c76b8e7d39ec84ad57f51232cb6e04602dde1cda5e6eb2183"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__init__.py","mode":33188,"size":1221,"sha256":"b432f51c28d993a2ec1583ef9580b0ce94c2cb05307fbe22913b7cbeb2b4c1ac"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":493,"sha256":"46ff7be81d91de0d944d4b3719dca1d2307dcac14520ad6829cd3cd7d10a9e7b"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":493,"sha256":"46ff7be81d91de0d944d4b3719dca1d2307dcac14520ad6829cd3cd7d10a9e7b"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/aliases.cpython-36.opt-1.pyc","mode":33188,"size":5423,"sha256":"8180914696bf6a075611e178dc0b8654e2425da5e38cd1ecf07868b351702756"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/aliases.cpython-36.pyc","mode":33188,"size":5423,"sha256":"8180914696bf6a075611e178dc0b8654e2425da5e38cd1ecf07868b351702756"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/cli.cpython-36.opt-1.pyc","mode":33188,"size":34119,"sha256":"c28c3d18ffe1c325f73744a01bed912f450052fcacb1027305f796258d42bf70"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/cli.cpython-36.pyc","mode":33188,"size":34161,"sha256":"1e1c6c625d0743cfa16872ed2da9ec4f18b395662fbdaceb73a5ae9fb507e380"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/completion_helper.cpython-36.opt-1.pyc","mode":33188,"size":8654,"sha256":"dd44fbeaaddd0383bd212faad11c62360417e66ed948793fa9b33fe499589731"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/completion_helper.cpython-36.pyc","mode":33188,"size":8654,"sha256":"dd44fbeaaddd0383bd212faad11c62360417e66ed948793fa9b33fe499589731"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/demand.cpython-36.opt-1.pyc","mode":33188,"size":1547,"sha256":"6ae7d7120d41b02e8b84b531c5c530aa8d4f184f674a19b7ccd64946a8addcea"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/demand.cpython-36.pyc","mode":33188,"size":1547,"sha256":"6ae7d7120d41b02e8b84b531c5c530aa8d4f184f674a19b7ccd64946a8addcea"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/format.cpython-36.opt-1.pyc","mode":33188,"size":2353,"sha256":"b60949909c783f03866e46de12854e16e91820de22523215401643a19bf3ab94"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/format.cpython-36.pyc","mode":33188,"size":2353,"sha256":"b60949909c783f03866e46de12854e16e91820de22523215401643a19bf3ab94"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/main.cpython-36.opt-1.pyc","mode":33188,"size":5033,"sha256":"732137d64c489b5240a8cd1cb998b55a832d898eb3ce76c59399654c35bf9ca3"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/main.cpython-36.pyc","mode":33188,"size":5033,"sha256":"732137d64c489b5240a8cd1cb998b55a832d898eb3ce76c59399654c35bf9ca3"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/option_parser.cpython-36.opt-1.pyc","mode":33188,"size":16448,"sha256":"3544d8645a3b131345d98a59a57b374ea31edaef8148ce4c141a3b937719dac7"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/option_parser.cpython-36.pyc","mode":33188,"size":16448,"sha256":"3544d8645a3b131345d98a59a57b374ea31edaef8148ce4c141a3b937719dac7"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/output.cpython-36.opt-1.pyc","mode":33188,"size":61748,"sha256":"3a2e20efc35b79b7b815bb88a01d235d8e28c1a62da07cd99560115b0cf2210e"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/output.cpython-36.pyc","mode":33188,"size":61841,"sha256":"100972a681be6be8431b5c7383e62ac85724d633a7496d8722122339ae7c9f01"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/progress.cpython-36.opt-1.pyc","mode":33188,"size":4607,"sha256":"a690d5f90165005590849de265e375d63f5bf21289eaaf843f4adeab8de2cc95"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/progress.cpython-36.pyc","mode":33188,"size":4607,"sha256":"a690d5f90165005590849de265e375d63f5bf21289eaaf843f4adeab8de2cc95"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/term.cpython-36.opt-1.pyc","mode":33188,"size":11771,"sha256":"673a8925afb8abdac1511cd02e0bd2551f2e940e3c2df2c0ef55eca9d54ae885"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/term.cpython-36.pyc","mode":33188,"size":11806,"sha256":"b3377addaadc89932f2801a9a012e9f56b35db165a68473512d1169e1205d993"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/utils.cpython-36.opt-1.pyc","mode":33188,"size":3169,"sha256":"0fe8fe92ea4a516be1480d7f187f160efa8c012672ea58e10260ee18b95c5973"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/__pycache__/utils.cpython-36.pyc","mode":33188,"size":3169,"sha256":"0fe8fe92ea4a516be1480d7f187f160efa8c012672ea58e10260ee18b95c5973"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/aliases.py","mode":33188,"size":7096,"sha256":"fc8b1c457eb62baef70d3142a66a054a206cfeeb8bf051c86ae8525680202f90"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/cli.py","mode":33188,"size":48453,"sha256":"ec2eddfd58ca92d0fe85d4985dc81d8c87b20a03269ff37439f1ec245c2ea91e"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__init__.py","mode":33188,"size":42244,"sha256":"11b7ee7972b5cbf72bc56e2b8939b4ccb48fdb0080f612827fb805dbc0e7f715"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":32904,"sha256":"0511610e0011897f5006b7dca0ca84c87e572a7a6f0f2a8485ffa1fad75b61c6"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":33147,"sha256":"c3e894146cbde8282a1d78e21043adba2e6f9280b5bbe4ef7d73afefd6c6e85b"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/alias.cpython-36.opt-1.pyc","mode":33188,"size":5330,"sha256":"fd0fbfd9951afd9b68f7c6581ba60d886625bcd16271af1381b67144bd49828d"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/alias.cpython-36.pyc","mode":33188,"size":5330,"sha256":"fd0fbfd9951afd9b68f7c6581ba60d886625bcd16271af1381b67144bd49828d"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/autoremove.cpython-36.opt-1.pyc","mode":33188,"size":2080,"sha256":"43e662dc949f11ee358af2395880a2490ed1095a1b39658cfc1676ab6c577107"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/autoremove.cpython-36.pyc","mode":33188,"size":2080,"sha256":"43e662dc949f11ee358af2395880a2490ed1095a1b39658cfc1676ab6c577107"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/check.cpython-36.opt-1.pyc","mode":33188,"size":3611,"sha256":"483c911c7c740da5ea5a7c498acc9e18ec017defee8739a303a49efb3d10e043"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/check.cpython-36.pyc","mode":33188,"size":3611,"sha256":"483c911c7c740da5ea5a7c498acc9e18ec017defee8739a303a49efb3d10e043"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/clean.cpython-36.opt-1.pyc","mode":33188,"size":4105,"sha256":"b42a2ddb0a2dece18bef20d929ebe846394ca198300a78d21e259925c652d848"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/clean.cpython-36.pyc","mode":33188,"size":4105,"sha256":"b42a2ddb0a2dece18bef20d929ebe846394ca198300a78d21e259925c652d848"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/deplist.cpython-36.opt-1.pyc","mode":33188,"size":851,"sha256":"5fa2a072fc79b01b89f877dd7498df8a287491b6d3395092cf3507bafb1c3b96"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/deplist.cpython-36.pyc","mode":33188,"size":851,"sha256":"5fa2a072fc79b01b89f877dd7498df8a287491b6d3395092cf3507bafb1c3b96"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/distrosync.cpython-36.opt-1.pyc","mode":33188,"size":1440,"sha256":"1cf29ab3502e48c0150fe61cd7b4093cae1ff6509f9c9e33572b3943b5f62d5f"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/distrosync.cpython-36.pyc","mode":33188,"size":1440,"sha256":"1cf29ab3502e48c0150fe61cd7b4093cae1ff6509f9c9e33572b3943b5f62d5f"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/downgrade.cpython-36.opt-1.pyc","mode":33188,"size":1803,"sha256":"f9762f083b921916964217834e2f3846c517fc093114696e95cdbc15543f6639"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/downgrade.cpython-36.pyc","mode":33188,"size":1803,"sha256":"f9762f083b921916964217834e2f3846c517fc093114696e95cdbc15543f6639"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/group.cpython-36.opt-1.pyc","mode":33188,"size":10461,"sha256":"118ac1afa4e8a2d6496091f2c182783585acd5a8a2236150c51999165c19be9e"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/group.cpython-36.pyc","mode":33188,"size":10558,"sha256":"3e4592fbe2fe5fc53e37c34364c65aca11f60d875f346f34d589de07e76ac87d"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/install.cpython-36.opt-1.pyc","mode":33188,"size":6338,"sha256":"c4d0b324aee16011a66d7feb116436619b7fed053a15a4edc9bf85e23b8eb174"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/install.cpython-36.pyc","mode":33188,"size":6338,"sha256":"c4d0b324aee16011a66d7feb116436619b7fed053a15a4edc9bf85e23b8eb174"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/makecache.cpython-36.opt-1.pyc","mode":33188,"size":1263,"sha256":"0109a51a34a2bfd549b3be7f0ae2871a946b49de84bfb70e06100738cc800aa5"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/makecache.cpython-36.pyc","mode":33188,"size":1263,"sha256":"0109a51a34a2bfd549b3be7f0ae2871a946b49de84bfb70e06100738cc800aa5"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/mark.cpython-36.opt-1.pyc","mode":33188,"size":2917,"sha256":"9cf533ea6a610d0aaccddac7f576d6b76c0561e028397cf9a6ebe19d12c7d5d2"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/mark.cpython-36.pyc","mode":33188,"size":2917,"sha256":"9cf533ea6a610d0aaccddac7f576d6b76c0561e028397cf9a6ebe19d12c7d5d2"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/module.cpython-36.opt-1.pyc","mode":33188,"size":14070,"sha256":"b488becab47cee0951b443e83389b2604f6051e2de79bf97884bbd26371b818c"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/module.cpython-36.pyc","mode":33188,"size":14070,"sha256":"b488becab47cee0951b443e83389b2604f6051e2de79bf97884bbd26371b818c"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/reinstall.cpython-36.opt-1.pyc","mode":33188,"size":2965,"sha256":"39c7dc1fcd802417e06a5bb2223ad539d66e43c808f1bd4ad8faba5eb251627a"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/reinstall.cpython-36.pyc","mode":33188,"size":3040,"sha256":"c4f7434e40ccc6e2fba31b24668fb29d0fd47bce36542c7d4aa41e074911aef0"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/remove.cpython-36.opt-1.pyc","mode":33188,"size":4126,"sha256":"702584542300aae80dfb97c2f35fbb32a08e289abb8bdc2d365557626668b02b"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/remove.cpython-36.pyc","mode":33188,"size":4126,"sha256":"702584542300aae80dfb97c2f35fbb32a08e289abb8bdc2d365557626668b02b"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/repolist.cpython-36.opt-1.pyc","mode":33188,"size":7408,"sha256":"0ce89be53f7aaaa68a8c7049583c94170dd8314a77430fbd46f4261b4934b2e5"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/repolist.cpython-36.pyc","mode":33188,"size":7408,"sha256":"0ce89be53f7aaaa68a8c7049583c94170dd8314a77430fbd46f4261b4934b2e5"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/repoquery.cpython-36.opt-1.pyc","mode":33188,"size":22311,"sha256":"35cb1a971b2084751627342b3adc227c19bbdd8cf4c4efa7a7fb2414fcc83ecd"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/repoquery.cpython-36.pyc","mode":33188,"size":22311,"sha256":"35cb1a971b2084751627342b3adc227c19bbdd8cf4c4efa7a7fb2414fcc83ecd"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/search.cpython-36.opt-1.pyc","mode":33188,"size":4432,"sha256":"d4ed4ff910bf381d83c9eb3a667ef6a90838d1e324d3936af04446dd798ca0df"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/search.cpython-36.pyc","mode":33188,"size":4432,"sha256":"d4ed4ff910bf381d83c9eb3a667ef6a90838d1e324d3936af04446dd798ca0df"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/shell.cpython-36.opt-1.pyc","mode":33188,"size":7853,"sha256":"c9c7da8e6592b0a1c5917906076c4b5ffdb12a75542591308bfc859273d94212"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/shell.cpython-36.pyc","mode":33188,"size":7853,"sha256":"c9c7da8e6592b0a1c5917906076c4b5ffdb12a75542591308bfc859273d94212"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/swap.cpython-36.opt-1.pyc","mode":33188,"size":1887,"sha256":"a3f79eea4415f41e0f3c10c7e903ae32a044c69155511d8a7940eec47b54d7cb"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/swap.cpython-36.pyc","mode":33188,"size":1887,"sha256":"a3f79eea4415f41e0f3c10c7e903ae32a044c69155511d8a7940eec47b54d7cb"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/updateinfo.cpython-36.opt-1.pyc","mode":33188,"size":13776,"sha256":"94f25ff1a3765673ba01e1d5fc9654849db44d4b49e02dc6edbf94a193b29764"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/updateinfo.cpython-36.pyc","mode":33188,"size":13776,"sha256":"94f25ff1a3765673ba01e1d5fc9654849db44d4b49e02dc6edbf94a193b29764"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/upgrade.cpython-36.opt-1.pyc","mode":33188,"size":3908,"sha256":"34e4748a41a2ea18d6f96d660f3876abaa77193ebfd6cb783d17f2524ca25d65"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/upgrade.cpython-36.pyc","mode":33188,"size":3908,"sha256":"34e4748a41a2ea18d6f96d660f3876abaa77193ebfd6cb783d17f2524ca25d65"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/upgrademinimal.cpython-36.opt-1.pyc","mode":33188,"size":1103,"sha256":"426918009b745ba6255d32709971e2024a8cc8f08c9f4c29730208a3165cc7f1"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/__pycache__/upgrademinimal.cpython-36.pyc","mode":33188,"size":1103,"sha256":"426918009b745ba6255d32709971e2024a8cc8f08c9f4c29730208a3165cc7f1"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/alias.py","mode":33188,"size":7088,"sha256":"38630568c1b5bddf72767cf6f18864fdf49411fef4cfc9fcb550cef9300eaa5a"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/autoremove.py","mode":33188,"size":3053,"sha256":"5d7b723f4ec7d024113aa241de8d687d302529e8e6c5352a7bbaa308c83f72ef"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/check.py","mode":33188,"size":7064,"sha256":"8d4f159579d16e50d1cc33d9d77cbbcce8edf01bdd48c8076f5e98961d8ab053"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/clean.py","mode":33188,"size":4468,"sha256":"29bd5c6750d06836d1e23bc398731ba378ab6e5bd91a80a9e488157f160bbaf9"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/deplist.py","mode":33188,"size":1472,"sha256":"4dac4a508115a155209ec28f55d94849fdbcb56cfea18f93aa628837226c4546"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/distrosync.py","mode":33188,"size":1951,"sha256":"a0b31085c4179dac53c66cea59a176b3083064721c164358e2293a62ee84554c"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/downgrade.py","mode":33188,"size":2325,"sha256":"b21a57b3c8f7d56e78f9538c9ead3346681329ef316a8829b277ea9a9e762947"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/group.py","mode":33188,"size":14986,"sha256":"a40e0c693484c1c9b50144fc165b6db41f2d545648a112e2bfbf6e0437c91a86"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/install.py","mode":33188,"size":7868,"sha256":"b046128bd2e8f82146c4c664f19cd10acc6a880d6783af4ce000e694a8f8fd7d"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/makecache.py","mode":33188,"size":1901,"sha256":"b9d78dafc00162d61f0ed68e2a7964bfa7a430082a6bf406a24f388e616f7d31"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/mark.py","mode":33188,"size":3536,"sha256":"388f9ac126b206f348accf639b3d2295192b6757d4e273639a952ce35baaabbb"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/module.py","mode":33188,"size":15852,"sha256":"970a47a454359fefeb73dfe4d89adc6d9dfd5a0d14ef7531319522e8d0ec5ad6"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/reinstall.py","mode":33188,"size":4189,"sha256":"0d125addd3d434a5e52c3843bc8b180ccffa2ada0f3e2c5caae741ed0adb2da4"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/remove.py","mode":33188,"size":6700,"sha256":"57d5a2d867ce2a849e417cd5c55a87cd3e18dc2535d683bed15016f384bfed97"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/repolist.py","mode":33188,"size":12880,"sha256":"d8ab34562fda90b5af99c68748a8cd3bf26717641fcb83f66449df5836badc13"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/repoquery.py","mode":33188,"size":34226,"sha256":"7e5cff980b116b4dddc563b86fe275be07bf1d61d5b6c9ee330d6380c9fcb092"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/search.py","mode":33188,"size":6358,"sha256":"322a143558ef3b77614b454b7c2cd208c0e2f7eb18f168801c67dfa088076c0b"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/shell.py","mode":33188,"size":9722,"sha256":"4fed88375f7e9c055915f9e877b5753b66185696485f96bc042e88893f3414eb"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/swap.py","mode":33188,"size":2419,"sha256":"073ddcdfacd42bea5a9b7bd46874387a9c45f8b0fed8ef77776130c3ae9108d5"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/updateinfo.py","mode":33188,"size":18725,"sha256":"597693089e5c3635a6aa0c67b734a12b05ecb2640a2ef7e41dd532d1d0897e8a"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/upgrade.py","mode":33188,"size":5069,"sha256":"b927777b4745041e9a33994480a0d4fd0f8b0015a872cddf9a7887e76a47c2d1"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/commands/upgrademinimal.py","mode":33188,"size":1799,"sha256":"c8bd92bcc843028bc4ad0647d1322254009585befad24e4afdc8f368dba10828"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/completion_helper.py","mode":33188,"size":7460,"sha256":"e2343780e0d35183a7b6787d557252e97ef9325c117e33aab80ef60a5223f27e"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/demand.py","mode":33188,"size":2535,"sha256":"d22e929fb22fc39ca0c3e839a1b3affdabc44c2fd385000bb5b8ce9a92d6f3d3"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/format.py","mode":33188,"size":3846,"sha256":"12ee41aad4d8ca62a8a707bd1a7a0f1345609ad73262fe53433f4247a79126f5"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/main.py","mode":33188,"size":6236,"sha256":"01286520fb2621c275275c85a41478324808f4a12e7de14127e5c31e04f294be"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/option_parser.py","mode":33188,"size":23253,"sha256":"a4e88ab2f14ad4f398fce9166ffc4ada808ce3047560e9327e70622fcfcc1507"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/output.py","mode":33188,"size":96950,"sha256":"d8c166f570e29db91463c9d02b81861e5355d828e895b42bacfbb8312c33c5e0"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/progress.py","mode":33188,"size":7609,"sha256":"fefcbe5e3fe2fbf9599d87215c0c8ca88562a78868e01fb6abb47f8db543f677"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/term.py","mode":33188,"size":14694,"sha256":"ff6a32c420d6b47019fda0395da82dfc93eb7eb8b76cb5ea7f62f37a6445e822"},{"path":"/usr/lib/python3.6/site-packages/dnf/cli/utils.py","mode":33188,"size":4520,"sha256":"ec03a7d6185c360de5cd28953013333d3266535e93b4dcf4d92c240484d658a0"},{"path":"/usr/lib/python3.6/site-packages/dnf/comps.py","mode":33188,"size":24164,"sha256":"5c9bfaa78935bf0e968276583eb2a9707d151e9f0169c006967cee9d36b8aa8e"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__init__.py","mode":33188,"size":1977,"sha256":"34dc106bfa82fb7a992ffd93b97033caec94ef1606181a95ff9d9041122b7c23"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":1159,"sha256":"0dc4c31844b250fa3af870e9fbe686074d7ad4132b47646c0e7022da540189a5"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":1159,"sha256":"0dc4c31844b250fa3af870e9fbe686074d7ad4132b47646c0e7022da540189a5"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__pycache__/config.cpython-36.opt-1.pyc","mode":33188,"size":14884,"sha256":"4f54571719e14747037b69f5637f0368621f13b45351ae77d6812db09ed29615"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__pycache__/config.cpython-36.pyc","mode":33188,"size":14884,"sha256":"4f54571719e14747037b69f5637f0368621f13b45351ae77d6812db09ed29615"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__pycache__/read.cpython-36.opt-1.pyc","mode":33188,"size":3211,"sha256":"06563cce0d01541b4ff7191b408363c433125c2020f0f6ab55207e4ff4f5a13c"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__pycache__/read.cpython-36.pyc","mode":33188,"size":3211,"sha256":"06563cce0d01541b4ff7191b408363c433125c2020f0f6ab55207e4ff4f5a13c"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__pycache__/substitutions.cpython-36.opt-1.pyc","mode":33188,"size":1688,"sha256":"511332c96c14deabd517ebee3caf61354574d91ee9221fec3ea3bacb16ef3d5f"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/__pycache__/substitutions.cpython-36.pyc","mode":33188,"size":1688,"sha256":"511332c96c14deabd517ebee3caf61354574d91ee9221fec3ea3bacb16ef3d5f"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/config.py","mode":33188,"size":20457,"sha256":"d9c43e2a4f4da65fe60ec7b7e6bac2b9af63655ad95ca9e0021274857f1860f1"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/read.py","mode":33188,"size":4963,"sha256":"6f38bf8e92977f5d4cdc8930c5886c248fcf578516a2a7897e8d744398fd7cfe"},{"path":"/usr/lib/python3.6/site-packages/dnf/conf/substitutions.py","mode":33188,"size":2418,"sha256":"c3f68f42244f181e443e4e91d615a007bf6b235ecbddf4a686c944559ec56c30"},{"path":"/usr/lib/python3.6/site-packages/dnf/const.py","mode":33188,"size":2434,"sha256":"0816e68e959d1f198a1971ee373a674e557c29de5227404eb00b2f1f441d04e0"},{"path":"/usr/lib/python3.6/site-packages/dnf/crypto.py","mode":33188,"size":5723,"sha256":"1dc97c798a4d7c5654dfa466c824f6fd76b83f54f15656f639e957789e7d910a"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/__init__.py","mode":33188,"size":778,"sha256":"54dacac1df24c29af7bc8848cd8d285594d45a072396afc0a069f64d80521dc4"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":113,"sha256":"5fd8d8df4e704544c688488f2a0127271a72e0f86c2872413dd0e3912e7b1145"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":113,"sha256":"5fd8d8df4e704544c688488f2a0127271a72e0f86c2872413dd0e3912e7b1145"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/__pycache__/group.cpython-36.opt-1.pyc","mode":33188,"size":13526,"sha256":"67dff9d1f4cb008838e27fef91285b8fe238dcf61c9f616c0008e36fbd4bbc00"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/__pycache__/group.cpython-36.pyc","mode":33188,"size":13624,"sha256":"4d6ce594ef07d91cbd3b2549905396f390b650c7da9ece0a38971a7f936f9d50"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/__pycache__/history.cpython-36.opt-1.pyc","mode":33188,"size":17306,"sha256":"f16f852ccfe36d965809fa5687002473d357eb5bc33fcc51f75e10c21b39d200"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/__pycache__/history.cpython-36.pyc","mode":33188,"size":17336,"sha256":"a23b5d399fad6ffad51e9775b8f9a002e5f3b4dfa789af42bb94e0bde08e0499"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/group.py","mode":33188,"size":14303,"sha256":"7ddfadf5c029b1c2f5ee99ab5aa06116d8361555ce5a396e3e4b01fa673dbcd1"},{"path":"/usr/lib/python3.6/site-packages/dnf/db/history.py","mode":33188,"size":16821,"sha256":"78f53e200be29dac0c4884b49242eb73c96d1dd709198715ec027adad6e12d25"},{"path":"/usr/lib/python3.6/site-packages/dnf/dnssec.py","mode":33188,"size":11375,"sha256":"d3390195ad9c93af3887b830202b9a642a6ae92c060fd2ecb7b84dd7bbd8600d"},{"path":"/usr/lib/python3.6/site-packages/dnf/drpm.py","mode":33188,"size":6352,"sha256":"3aec2a0e8944c55568e87609b6c1d01d70fc9a299c243ea575f6717a7a118b31"},{"path":"/usr/lib/python3.6/site-packages/dnf/exceptions.py","mode":33188,"size":5810,"sha256":"89f5cbbf41b4df375b96d427593fb342260ce90e402e9dfea803ee0485858263"},{"path":"/usr/lib/python3.6/site-packages/dnf/goal.py","mode":33188,"size":1101,"sha256":"fb838a3c7eea1f7117a2c932039143b8b968587156cec670bbc54755af039041"},{"path":"/usr/lib/python3.6/site-packages/dnf/history.py","mode":33188,"size":1150,"sha256":"2e2efd9a17712a44319bd864c829870fba1092fd9ef38b9d851e342b1d7c71eb"},{"path":"/usr/lib/python3.6/site-packages/dnf/i18n.py","mode":33188,"size":12321,"sha256":"442c56b9eddcf95e78dd73a278c11d11b531103f07a9448b28e56f60fefe507a"},{"path":"/usr/lib/python3.6/site-packages/dnf/lock.py","mode":33188,"size":5322,"sha256":"53518bb18d056de58a5315b1f84e683ddb5d978d9cd7eafa1354e6c8bfdeddd5"},{"path":"/usr/lib/python3.6/site-packages/dnf/logging.py","mode":33188,"size":8902,"sha256":"0ec67fc9a0ffd2bafee8708b263fc949c8f6231d371112b09a710f6621e5cfbc"},{"path":"/usr/lib/python3.6/site-packages/dnf/match_counter.py","mode":33188,"size":4030,"sha256":"a410f749d7fd825cbf2ff9e0b8b993160d9b1acf33d72453ddc3081d243c0cde"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/__init__.py","mode":33188,"size":1262,"sha256":"2d8bdc77204a38bcd6ea31764cf9aef77a40da140d54852b5fb9ac758084a98f"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":572,"sha256":"835d685904055282297d3ea597a19e0561ce743f20ec810d91a331baf46f588c"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":572,"sha256":"835d685904055282297d3ea597a19e0561ce743f20ec810d91a331baf46f588c"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/__pycache__/exceptions.cpython-36.opt-1.pyc","mode":33188,"size":4520,"sha256":"1a8f219da1995dcd7c7113226a2688794104fd2e8e237f37dc2b874412e7389c"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/__pycache__/exceptions.cpython-36.pyc","mode":33188,"size":4520,"sha256":"1a8f219da1995dcd7c7113226a2688794104fd2e8e237f37dc2b874412e7389c"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/__pycache__/module_base.cpython-36.opt-1.pyc","mode":33188,"size":19970,"sha256":"3f5f5698751ec90f3383d69b4b7f4426b23936e5ca744fcf2a874cedac3d2a57"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/__pycache__/module_base.cpython-36.pyc","mode":33188,"size":20006,"sha256":"71f71a701aed93c5d5880e2b9028de0c18d57b2dacc4369b5897462251c16652"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/exceptions.py","mode":33188,"size":3582,"sha256":"ee75d12dc393ad6e537b5a694a55b3e368117876726738b5bd0ee003530e3f59"},{"path":"/usr/lib/python3.6/site-packages/dnf/module/module_base.py","mode":33188,"size":32815,"sha256":"4fa5763ed514bf75644dc82eae8ad8f2cdfedf6f7beec01af48f160b182f3550"},{"path":"/usr/lib/python3.6/site-packages/dnf/package.py","mode":33188,"size":9438,"sha256":"789e304f0075657a63637dd93041b17a26be2045a07f3630326e0087d7d7a799"},{"path":"/usr/lib/python3.6/site-packages/dnf/persistor.py","mode":33188,"size":4413,"sha256":"2ba53ded43be0176f1bc4f3381fff3cf7c1e250e4b3cb921a355dd0a59a2ba17"},{"path":"/usr/lib/python3.6/site-packages/dnf/plugin.py","mode":33188,"size":8526,"sha256":"0d9f945749991f1391bb2a9a9eb7baf7bf49c17311664446b1edd5fc3d9d1fc6"},{"path":"/usr/lib/python3.6/site-packages/dnf/pycomp.py","mode":33188,"size":3604,"sha256":"cc128a2671dcffdfb6c6c48891a1b5138df65c2467bb1f162450a618f242b577"},{"path":"/usr/lib/python3.6/site-packages/dnf/query.py","mode":33188,"size":1587,"sha256":"276f5d60567dd1394c9c7dd934f52d38678374e2df113947348f2fc4969781d8"},{"path":"/usr/lib/python3.6/site-packages/dnf/repo.py","mode":33188,"size":20714,"sha256":"6fe3647e5f96a01dac2c7affad10ed408230702e1261339d880708dec51c59a6"},{"path":"/usr/lib/python3.6/site-packages/dnf/repodict.py","mode":33188,"size":5166,"sha256":"c61b71482d92e7ed3236e9f57699e9f71c1e2396a611553236dbc3c1739ea240"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__init__.py","mode":33188,"size":4800,"sha256":"12e5808f7c3185fb1bb7b23d61eba294fbf6e50d1da187c51f27d70093815dfd"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3606,"sha256":"4b3caa2eb8fff623b48b28c0b73c986328c97b77d1357631a4f710d028814c58"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3606,"sha256":"4b3caa2eb8fff623b48b28c0b73c986328c97b77d1357631a4f710d028814c58"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/connection.cpython-36.opt-1.pyc","mode":33188,"size":794,"sha256":"5f1fd710e2650f0d7c17fff4db77b4b84d6f635f65dbd2f7299d44a5071b0fed"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/connection.cpython-36.pyc","mode":33188,"size":794,"sha256":"5f1fd710e2650f0d7c17fff4db77b4b84d6f635f65dbd2f7299d44a5071b0fed"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/error.cpython-36.opt-1.pyc","mode":33188,"size":274,"sha256":"8341d51b9e3fa5b1a319d3a613957245e3b3f0bffcc0b13b5f2a17581988599f"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/error.cpython-36.pyc","mode":33188,"size":274,"sha256":"8341d51b9e3fa5b1a319d3a613957245e3b3f0bffcc0b13b5f2a17581988599f"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/miscutils.cpython-36.opt-1.pyc","mode":33188,"size":1397,"sha256":"bd5ceb40fd0d43fd17345d17814089af3add9755f5d951dc6d799ff8836b4332"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/miscutils.cpython-36.pyc","mode":33188,"size":1397,"sha256":"bd5ceb40fd0d43fd17345d17814089af3add9755f5d951dc6d799ff8836b4332"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/transaction.cpython-36.opt-1.pyc","mode":33188,"size":3688,"sha256":"821ab69a005346acfee90e63c2aacc1be342387206eac4b3b99d9038f5cfefb6"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/__pycache__/transaction.cpython-36.pyc","mode":33188,"size":3688,"sha256":"821ab69a005346acfee90e63c2aacc1be342387206eac4b3b99d9038f5cfefb6"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/connection.py","mode":33188,"size":1369,"sha256":"26228b3ffc3879bd7bf5dca4a705f0e46a4f5a496a3edfcf66c49ea0bf8ed4bd"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/error.py","mode":33188,"size":1030,"sha256":"6c3d96dc347791af5c3725c722823ae5fc15b27899e6670ec156d43472f3941b"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/miscutils.py","mode":33188,"size":2238,"sha256":"28704e8636309520fde5066730075bd6cdc43c2ed080da9c8b6fab0c1f19afdf"},{"path":"/usr/lib/python3.6/site-packages/dnf/rpm/transaction.py","mode":33188,"size":3819,"sha256":"093104f907145f4a8beeabff3320beb73fc4e3141a452e66b6a671efacb97305"},{"path":"/usr/lib/python3.6/site-packages/dnf/sack.py","mode":33188,"size":2647,"sha256":"15e677fb4e42578ce593f2a50c4762061754dc9bf5d62fccc799d086c277ac10"},{"path":"/usr/lib/python3.6/site-packages/dnf/selector.py","mode":33188,"size":1125,"sha256":"e38e8340f97a4e1d5d7a9b9dab20645609dff1ffc342ae79fe9c644e7a45ace8"},{"path":"/usr/lib/python3.6/site-packages/dnf/subject.py","mode":33188,"size":1150,"sha256":"c9db675229698f8c0191cca4628e51da4b1ec01e58923200803c0bd65c7406c6"},{"path":"/usr/lib/python3.6/site-packages/dnf/transaction.py","mode":33188,"size":4397,"sha256":"8258c37e12ba5202bb4d9d7ca388c926894dc24219bb4a79e7d349853aa6714f"},{"path":"/usr/lib/python3.6/site-packages/dnf/util.py","mode":33188,"size":15512,"sha256":"277001b237314f7c179c789bef2cb9c346c50b0929102a894e21d8adb3ebe7d5"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/__init__.py","mode":33188,"size":1000,"sha256":"aca948bb2d589edee3dc1f913fafd2a6849132399d1d29c0685eb904080e2560"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":113,"sha256":"35753bcf87496c7e43c2a794f338cbf1105088e51f394c4fdd2bc5b2a3040b99"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":113,"sha256":"35753bcf87496c7e43c2a794f338cbf1105088e51f394c4fdd2bc5b2a3040b99"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/__pycache__/misc.cpython-36.opt-1.pyc","mode":33188,"size":12955,"sha256":"497484eafcb8d414833a6963cfe4520aacf49e68ef7e96209c222375a01d4b27"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/__pycache__/misc.cpython-36.pyc","mode":33188,"size":12955,"sha256":"497484eafcb8d414833a6963cfe4520aacf49e68ef7e96209c222375a01d4b27"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/__pycache__/rpmtrans.cpython-36.opt-1.pyc","mode":33188,"size":13384,"sha256":"20eb5456b3e69714f6974087db75668c5e3557fa38f90911b4ce7a22e3ee8214"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/__pycache__/rpmtrans.cpython-36.pyc","mode":33188,"size":13384,"sha256":"20eb5456b3e69714f6974087db75668c5e3557fa38f90911b4ce7a22e3ee8214"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/misc.py","mode":33188,"size":15461,"sha256":"3c4d4249ca3af8ad0072172658c1b54f814b074dded7da692d64e85f5844f2d4"},{"path":"/usr/lib/python3.6/site-packages/dnf/yum/rpmtrans.py","mode":33188,"size":15238,"sha256":"69083ec5f6ee288e00bdbbbf48eb812367cb186a2e9865006aa7d8d331bb0d7f"}]}},{"name":"python3-gpg","version":"1.10.0-6.el8.0.1","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-gpg:python3-gpg:1.10.0-6.el8.0.1:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-gpg:1.10.0-6.el8.0.1:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-gpg@0:1.10.0-6.el8.0.1?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"python3-gpg","version":"1.10.0","epoch":0,"architecture":"x86_64","release":"6.el8.0.1","sourceRpm":"gpgme-1.10.0-6.el8.0.1.src.rpm","size":1295107,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/28/4bd57866e457106494e9a47ec38823d8ea5e5c","mode":41471,"size":88,"sha256":""},{"path":"/usr/lib64/python3.6/site-packages/gpg-1.10.0-py3.6.egg-info","mode":33188,"size":964,"sha256":"7621d51362e469bb05d1b3d8ad6bb09654b39ec9f7c8b10592b088f82f3b91f3"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__init__.py","mode":33188,"size":4125,"sha256":"0407a8e01d61f59c7f0592bd24c6b3efb40b672949e214a5ef1090b0931086b8"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3181,"sha256":"4e0fc6bced2f0b486d97ebac32f0a235fb6c9db8afd4d072d6314927b5129a05"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3181,"sha256":"4e0fc6bced2f0b486d97ebac32f0a235fb6c9db8afd4d072d6314927b5129a05"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/callbacks.cpython-36.opt-1.pyc","mode":33188,"size":1166,"sha256":"16417b8e8e2160ec0012e9100dbd543a904fd04f20dce7f2f10d58081e7b6967"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/callbacks.cpython-36.pyc","mode":33188,"size":1166,"sha256":"16417b8e8e2160ec0012e9100dbd543a904fd04f20dce7f2f10d58081e7b6967"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/core.cpython-36.opt-1.pyc","mode":33188,"size":47690,"sha256":"026fc9a7951b3566beee9957f27806bb0225080ad24ad24a2149e7fba96f45c2"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/core.cpython-36.pyc","mode":33188,"size":47813,"sha256":"1f15f6d3c4eb32d4578a8b681bdecb4618a741a0e5b51a4b7976caaa38f49cb4"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/errors.cpython-36.opt-1.pyc","mode":33188,"size":8111,"sha256":"f9dc8838538e2a2c2169b64199ee1265c56083f7a70910ee5c72cb0635bc7e61"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/errors.cpython-36.pyc","mode":33188,"size":8111,"sha256":"f9dc8838538e2a2c2169b64199ee1265c56083f7a70910ee5c72cb0635bc7e61"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/gpgme.cpython-36.opt-1.pyc","mode":33188,"size":142211,"sha256":"e3e279a879d74178be0309b79f5325f787b53dc3ace5b380fc023b695c5ee068"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/gpgme.cpython-36.pyc","mode":33188,"size":142211,"sha256":"e3e279a879d74178be0309b79f5325f787b53dc3ace5b380fc023b695c5ee068"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/results.cpython-36.opt-1.pyc","mode":33188,"size":3847,"sha256":"6ae384baab80266cfd669dc3c3357694eb55c6304748216f415f1451625a3ff0"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/results.cpython-36.pyc","mode":33188,"size":3847,"sha256":"6ae384baab80266cfd669dc3c3357694eb55c6304748216f415f1451625a3ff0"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/util.cpython-36.opt-1.pyc","mode":33188,"size":1563,"sha256":"1ce7a90235271d61eafb78ce7ca2b952f540827a10a6d647125935a837056ce1"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/util.cpython-36.pyc","mode":33188,"size":1563,"sha256":"1ce7a90235271d61eafb78ce7ca2b952f540827a10a6d647125935a837056ce1"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/version.cpython-36.opt-1.pyc","mode":33188,"size":1848,"sha256":"f0b650fc8c642f19e75288f5c1366e93382c3cfa3268005a4268bd21148ce271"},{"path":"/usr/lib64/python3.6/site-packages/gpg/__pycache__/version.cpython-36.pyc","mode":33188,"size":1848,"sha256":"f0b650fc8c642f19e75288f5c1366e93382c3cfa3268005a4268bd21148ce271"},{"path":"/usr/lib64/python3.6/site-packages/gpg/_gpgme.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":733464,"sha256":"cbeb0dbd1171d23dc984c1332534ac79f7e1bee4fc33e586d971f6aa6a469fb3"},{"path":"/usr/lib64/python3.6/site-packages/gpg/callbacks.py","mode":33188,"size":1950,"sha256":"b89fad1f8deecd7eed26c3bf64feadcec4aa5e3b1fd2c51841d2496ce33e97ca"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__init__.py","mode":33188,"size":5159,"sha256":"753eb1f28fb5ae054b2442eeab1b695d2a7fea8072e43a749722140be46fd5ea"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":4536,"sha256":"e5f9a70ddc15110205d70835ca7c89f4144cd5e6a74f83054b00a814590b5a13"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":4536,"sha256":"e5f9a70ddc15110205d70835ca7c89f4144cd5e6a74f83054b00a814590b5a13"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/create.cpython-36.opt-1.pyc","mode":33188,"size":318,"sha256":"04dea2d517086e0d184616783c2e43b1d601f2fff657a746500b711bd23a56c0"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/create.cpython-36.pyc","mode":33188,"size":318,"sha256":"04dea2d517086e0d184616783c2e43b1d601f2fff657a746500b711bd23a56c0"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/event.cpython-36.opt-1.pyc","mode":33188,"size":316,"sha256":"6d5cf9d158c79b0fce67aba021d114f50a59130d6fd9116442f1549de2ab1626"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/event.cpython-36.pyc","mode":33188,"size":316,"sha256":"6d5cf9d158c79b0fce67aba021d114f50a59130d6fd9116442f1549de2ab1626"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/import.cpython-36.opt-1.pyc","mode":33188,"size":318,"sha256":"35ce9df082010c2a247cfb307d160a7f419817c8cd0c7e68cb262b927fa55cae"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/import.cpython-36.pyc","mode":33188,"size":318,"sha256":"35ce9df082010c2a247cfb307d160a7f419817c8cd0c7e68cb262b927fa55cae"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/keysign.cpython-36.opt-1.pyc","mode":33188,"size":320,"sha256":"be1ebda0ddf9c354944cd848fd9f57d3285c318c39aa1df161d7ef48160b052d"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/keysign.cpython-36.pyc","mode":33188,"size":320,"sha256":"be1ebda0ddf9c354944cd848fd9f57d3285c318c39aa1df161d7ef48160b052d"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/md.cpython-36.opt-1.pyc","mode":33188,"size":310,"sha256":"97c6c14c911a392484d396ea3958b7ef07fc56fdba93d22ff8db09a323d7a550"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/md.cpython-36.pyc","mode":33188,"size":310,"sha256":"97c6c14c911a392484d396ea3958b7ef07fc56fdba93d22ff8db09a323d7a550"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/pk.cpython-36.opt-1.pyc","mode":33188,"size":310,"sha256":"a15d28398a46015c11d9232fd6b5a911c4e0405bcbe888e6b9c50fbe26d23610"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/pk.cpython-36.pyc","mode":33188,"size":310,"sha256":"a15d28398a46015c11d9232fd6b5a911c4e0405bcbe888e6b9c50fbe26d23610"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/protocol.cpython-36.opt-1.pyc","mode":33188,"size":322,"sha256":"a38628c9f42c47aa8ec75dde77c0b2b78b785e00565996f7886f331a1c3c7ea3"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/protocol.cpython-36.pyc","mode":33188,"size":322,"sha256":"a38628c9f42c47aa8ec75dde77c0b2b78b785e00565996f7886f331a1c3c7ea3"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/sigsum.cpython-36.opt-1.pyc","mode":33188,"size":318,"sha256":"c44f5151bc3532cdb2dd3f94a802f8edde4c391c90639233e6ac4ddec7a2198c"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/sigsum.cpython-36.pyc","mode":33188,"size":318,"sha256":"c44f5151bc3532cdb2dd3f94a802f8edde4c391c90639233e6ac4ddec7a2198c"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/status.cpython-36.opt-1.pyc","mode":33188,"size":2551,"sha256":"20d3886e05e7828147cc319b57234a9aa4e572e10648c60159067882df3fc08d"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/status.cpython-36.pyc","mode":33188,"size":2551,"sha256":"20d3886e05e7828147cc319b57234a9aa4e572e10648c60159067882df3fc08d"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/validity.cpython-36.opt-1.pyc","mode":33188,"size":322,"sha256":"ff54b5020c93c3abca125c46107dccb0b392c5364d1509fea96d1a30359f2d73"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/__pycache__/validity.cpython-36.pyc","mode":33188,"size":322,"sha256":"ff54b5020c93c3abca125c46107dccb0b392c5364d1509fea96d1a30359f2d73"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/create.py","mode":33188,"size":948,"sha256":"1b1f0b58018ec80c415f06792cfcd4e21c16c0f1e785c24b8b3fdd4aac4bec62"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/data/__init__.py","mode":33188,"size":175,"sha256":"c4e5da66e148a2083089a66eaaf68b0628bfaccbd948039775dcef4c4d73e119"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/data/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":285,"sha256":"217469f11bcfc6e9537b8f4f8d0dccad6197d4a7aad27b8571ffaaf47c6844cf"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/data/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":285,"sha256":"217469f11bcfc6e9537b8f4f8d0dccad6197d4a7aad27b8571ffaaf47c6844cf"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/data/__pycache__/encoding.cpython-36.opt-1.pyc","mode":33188,"size":327,"sha256":"7895d0a7ffde7c6e9bd1de4edfba3eb297f57ce7a8acb72e34ca21872f7f4c12"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/data/__pycache__/encoding.cpython-36.pyc","mode":33188,"size":327,"sha256":"7895d0a7ffde7c6e9bd1de4edfba3eb297f57ce7a8acb72e34ca21872f7f4c12"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/data/encoding.py","mode":33188,"size":1094,"sha256":"0eaf26d11493fcc6bcd029fd7a04277a8c51c8c96f904373fb39368036ffafa5"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/event.py","mode":33188,"size":1086,"sha256":"4e52912b4c195b74f1df97d6d469fcc81ee19d15988a55864f60d836cc4ab96b"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/import.py","mode":33188,"size":1087,"sha256":"7fbe6ad24638e36e4f3901d3ff80b469099cfbee1975bc8fd158c49a19781759"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/keylist/__init__.py","mode":33188,"size":167,"sha256":"d1c2b7abaf007323fc3fa23a1acc95ac38ba5e25080050ca04a435f0b031aadb"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/keylist/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":281,"sha256":"4ba8b7d79d47e2ea86951e4398faaff889f5839e3a13ee6804e5a29d6eec3efd"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/keylist/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":281,"sha256":"4ba8b7d79d47e2ea86951e4398faaff889f5839e3a13ee6804e5a29d6eec3efd"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/keylist/__pycache__/mode.cpython-36.opt-1.pyc","mode":33188,"size":322,"sha256":"2681b19b44ebb78feb817f53feffa12581903363f1c9e83bafe819fe483b3fef"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/keylist/__pycache__/mode.cpython-36.pyc","mode":33188,"size":322,"sha256":"2681b19b44ebb78feb817f53feffa12581903363f1c9e83bafe819fe483b3fef"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/keylist/mode.py","mode":33188,"size":1093,"sha256":"0de2125ef0461691fca36b2744ac9941dedd0fab1e38ab9064d4ed7dfe59e9b1"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/keysign.py","mode":33188,"size":948,"sha256":"050aeb8b98816f03856bf8a1fc2aeb0cc61a4f0ceec33758246e485cb3e7b4af"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/md.py","mode":33188,"size":1083,"sha256":"3d3c14b9d2c125fbd98ac0a15a42c8198f392184c6f6e936ec76762f4e60d21d"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/pk.py","mode":33188,"size":1083,"sha256":"702df480018f9ec545e5d168917da18566766dd67a56c0c08dd6cfa668931ba8"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/protocol.py","mode":33188,"size":1089,"sha256":"96e6ffc9da7bf06d8f917cdedc17e32c16079ba2b523cbf2d5c54757dc21ef78"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/__init__.py","mode":33188,"size":189,"sha256":"bf5f1873890d1c16a378ecbc24413a6b2d4ac9c52f5dc9aeca2f0b63c827ad40"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":307,"sha256":"021186ef14e47c0e1caed96bb6f9e7378b8282e7c1a353dec85cec940d6f05c7"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":307,"sha256":"021186ef14e47c0e1caed96bb6f9e7378b8282e7c1a353dec85cec940d6f05c7"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/__pycache__/mode.cpython-36.opt-1.pyc","mode":33188,"size":318,"sha256":"f7023cf92036e2138fb43d2a6e423fec241daffc2c86a1cc337536f0302afaae"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/__pycache__/mode.cpython-36.pyc","mode":33188,"size":318,"sha256":"f7023cf92036e2138fb43d2a6e423fec241daffc2c86a1cc337536f0302afaae"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/__pycache__/notation.cpython-36.opt-1.pyc","mode":33188,"size":326,"sha256":"d2d773830d786768688df44a81d16eb358ccc1eabfcaaa05c01956b7b9ffa4f8"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/__pycache__/notation.cpython-36.pyc","mode":33188,"size":326,"sha256":"d2d773830d786768688df44a81d16eb358ccc1eabfcaaa05c01956b7b9ffa4f8"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/mode.py","mode":33188,"size":1089,"sha256":"0d375f69f38e0420e895f36ae9c0e7a11db4c6842828ff7ec33f2aa5e9cb9837"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sig/notation.py","mode":33188,"size":970,"sha256":"e68daf8ab20526845c81595c134981ea8e8c763e01454d28c42a60d865de2c43"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/sigsum.py","mode":33188,"size":1087,"sha256":"38200f82498d707b6a276f4c9eca26aa1bcd66d60c9faa3ec63eebdea3f41c0a"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/status.py","mode":33188,"size":3977,"sha256":"7f26ea18e8dcfdf64a5a1258055535c5db7f7ec372bb036bd16ba3508b535935"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/tofu/__init__.py","mode":33188,"size":891,"sha256":"35ac21174b40578431aa904f8f9b2ae7bcb2772327c089e88bd4176443e94e2e"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/tofu/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":283,"sha256":"90cec7a9089cf97ccaf176ac23a49d97a87b1d281c98cb96bee4891864794f0a"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/tofu/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":283,"sha256":"90cec7a9089cf97ccaf176ac23a49d97a87b1d281c98cb96bee4891864794f0a"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/tofu/__pycache__/policy.cpython-36.opt-1.pyc","mode":33188,"size":323,"sha256":"ca2f2e829107fdbe79fc0a5ed3f9c26b177db624ff77acaa5bb2230f9f6e985f"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/tofu/__pycache__/policy.cpython-36.pyc","mode":33188,"size":323,"sha256":"ca2f2e829107fdbe79fc0a5ed3f9c26b177db624ff77acaa5bb2230f9f6e985f"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/tofu/policy.py","mode":33188,"size":944,"sha256":"043f686dc18a182325d5530f085393d52826d17ad589b2de0644a2d2eab366c4"},{"path":"/usr/lib64/python3.6/site-packages/gpg/constants/validity.py","mode":33188,"size":1089,"sha256":"f1aecafa1c4fc41c6ee72d72cf910ca92b6d928f9ccaba276e482a972f550c34"},{"path":"/usr/lib64/python3.6/site-packages/gpg/core.py","mode":33188,"size":55065,"sha256":"87f7ccf4b68e2a2d0e2d6299d6bdcaab88ca893f1522fc0fe4e3365263de8966"},{"path":"/usr/lib64/python3.6/site-packages/gpg/errors.py","mode":33188,"size":6331,"sha256":"10c6ce62be518e20f1e7f5b79e26bb1b4d7fd753072cae2c6f543420509095e4"},{"path":"/usr/lib64/python3.6/site-packages/gpg/gpgme.py","mode":33188,"size":187828,"sha256":"5215438e6419613ca4d25e5f87505cba797ae19fd2fd0c3349786dd381900e2e"},{"path":"/usr/lib64/python3.6/site-packages/gpg/results.py","mode":33188,"size":3240,"sha256":"6f34b937766487d40c8c9935772ced111a9b4bd12962abcf0e070eecb9c86ac3"},{"path":"/usr/lib64/python3.6/site-packages/gpg/util.py","mode":33188,"size":1998,"sha256":"a517850f806cc5950a051d885d911c9ec2d27a0769baedd5e9e59f50629775c6"},{"path":"/usr/lib64/python3.6/site-packages/gpg/version.py","mode":33188,"size":2641,"sha256":"62984076083fba0d5394c0643739ab604867b1655f61451af5add09e5e100486"}]}},{"name":"python3-hawkey","version":"0.39.1-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-hawkey:python3-hawkey:0.39.1-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-hawkey:0.39.1-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-hawkey@0:0.39.1-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"python3-hawkey","version":"0.39.1","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"libdnf-0.39.1-5.el8.src.rpm","size":263176,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/10/de01d04f33357b88f985cfea90ba55da11ad65","mode":41471,"size":73,"sha256":""},{"path":"/usr/lib/.build-id/ab/03b30ae8bc362506f37fbae7e05971b71ef7c0","mode":41471,"size":63,"sha256":""},{"path":"/usr/lib64/python3.6/site-packages/hawkey/__init__.py","mode":33188,"size":12765,"sha256":"4db58f1346ace07a53151fac87ebf2ea47f4cd776aed3b7fca33ac9258788db3"},{"path":"/usr/lib64/python3.6/site-packages/hawkey/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":10252,"sha256":"eec261a4e97ea8504b352b52c042024438d18da6476411e51beb274cdf467732"},{"path":"/usr/lib64/python3.6/site-packages/hawkey/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":10252,"sha256":"eec261a4e97ea8504b352b52c042024438d18da6476411e51beb274cdf467732"},{"path":"/usr/lib64/python3.6/site-packages/hawkey/_hawkey.so","mode":33261,"size":207904,"sha256":"e077447619e1ae21414315c52d67b5a5cb99fb7c4ee46e3e7fe1290abf5504d4"},{"path":"/usr/lib64/python3.6/site-packages/hawkey/test/__init__.py","mode":33188,"size":1801,"sha256":"62001423a5078d8689a5b3ab568444b920ea4ec677f13e3a7b269df34e554130"},{"path":"/usr/lib64/python3.6/site-packages/hawkey/test/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":1254,"sha256":"43e92f8985b9621df00e115a502319c07513c2267667137f8e0a7b330aaf5305"},{"path":"/usr/lib64/python3.6/site-packages/hawkey/test/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":1254,"sha256":"43e92f8985b9621df00e115a502319c07513c2267667137f8e0a7b330aaf5305"},{"path":"/usr/lib64/python3.6/site-packages/hawkey/test/_hawkey_test.so","mode":33261,"size":29200,"sha256":"9fda7c96d8eef78b9d7053d74d5e3fe197203da4d594b7c64113a0eaf03f74c9"}]}},{"name":"python3-libcomps","version":"0.1.11-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-libcomps:python3-libcomps:0.1.11-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-libcomps:0.1.11-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-libcomps@0:0.1.11-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"python3-libcomps","version":"0.1.11","epoch":0,"architecture":"x86_64","release":"4.el8","sourceRpm":"libcomps-0.1.11-4.el8.src.rpm","size":147027,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/fe/6c1f8e908ef65cc501a30491ec7552e856e157","mode":41471,"size":69,"sha256":""},{"path":"/usr/lib64/python3.6/site-packages/libcomps/__init__.py","mode":33188,"size":28,"sha256":"06625bfa06225ca1238bb96a578924130dfb63bc46deb89628e1a3c9dccb9b7e"},{"path":"/usr/lib64/python3.6/site-packages/libcomps/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":143,"sha256":"2974f26f5d0a02a36b77269da73420429aa5fdc5827913f33f81662572f9de83"},{"path":"/usr/lib64/python3.6/site-packages/libcomps/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":143,"sha256":"2974f26f5d0a02a36b77269da73420429aa5fdc5827913f33f81662572f9de83"},{"path":"/usr/lib64/python3.6/site-packages/libcomps/_libpycomps.so","mode":33261,"size":146856,"sha256":"01b80c622dfa200bc4becce7915b1b48ade9cf695cd25fe8528f2318b232675e"}]}},{"name":"python3-libdnf","version":"0.39.1-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-libdnf:python3-libdnf:0.39.1-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-libdnf:0.39.1-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-libdnf@0:0.39.1-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"python3-libdnf","version":"0.39.1","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"libdnf-0.39.1-5.el8.src.rpm","size":3666830,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/8a/3a0b2bf2fd8c60fce913549efe79f805c6e2c1","mode":41471,"size":62,"sha256":""},{"path":"/usr/lib/.build-id/9a/074ef6ca3bd072c3b9e7116d91fbec29d7b73d","mode":41471,"size":61,"sha256":""},{"path":"/usr/lib/.build-id/9d/2e5f96702bb1689500c81d9fddfe9ba88bc338","mode":41471,"size":69,"sha256":""},{"path":"/usr/lib/.build-id/9e/33202c04a8f9b4dd5bf7dbab15ac195df9e84f","mode":41471,"size":68,"sha256":""},{"path":"/usr/lib/.build-id/a0/ef6be07c65ca43fb50f8742f26904deb82d640","mode":41471,"size":61,"sha256":""},{"path":"/usr/lib/.build-id/c9/6d1e46785b27b1ac148893263792a04aab824a","mode":41471,"size":63,"sha256":""},{"path":"/usr/lib/.build-id/cb/8bc00d26ebe4e4d87dc3586f79bb6d81db9efd","mode":41471,"size":66,"sha256":""},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__init__.py","mode":33188,"size":172,"sha256":"9b94dfa045584677fec59b0ee25daa458828922d30ac268a7a6e69c8e1f07f30"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":352,"sha256":"f3e62cda6bf29acb305776c1b49d87a507e892abeed1c593feeb996e5a0e3c5c"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":352,"sha256":"f3e62cda6bf29acb305776c1b49d87a507e892abeed1c593feeb996e5a0e3c5c"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/common_types.cpython-36.opt-1.pyc","mode":33188,"size":49751,"sha256":"bc37c6c6354f06c7d7467df19f29ad587e18e684e6a62bc8518d871deb4028ab"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/common_types.cpython-36.pyc","mode":33188,"size":49751,"sha256":"bc37c6c6354f06c7d7467df19f29ad587e18e684e6a62bc8518d871deb4028ab"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/conf.cpython-36.opt-1.pyc","mode":33188,"size":96536,"sha256":"dea23c2924edd483a0b8feacc043d7a63bc7f3611335be7ac9c3cd3b6fd2e6d0"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/conf.cpython-36.pyc","mode":33188,"size":96536,"sha256":"dea23c2924edd483a0b8feacc043d7a63bc7f3611335be7ac9c3cd3b6fd2e6d0"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/module.cpython-36.opt-1.pyc","mode":33188,"size":70104,"sha256":"e9733919794e4cc80c9e93c3aa7667d39d2d7db8aa993132cdd72ae9caea9caa"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/module.cpython-36.pyc","mode":33188,"size":70104,"sha256":"e9733919794e4cc80c9e93c3aa7667d39d2d7db8aa993132cdd72ae9caea9caa"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/repo.cpython-36.opt-1.pyc","mode":33188,"size":30423,"sha256":"9c72ef567381151374243d87da22681230f0e7b139d70a5b32544e61e254e301"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/repo.cpython-36.pyc","mode":33188,"size":30423,"sha256":"9c72ef567381151374243d87da22681230f0e7b139d70a5b32544e61e254e301"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/smartcols.cpython-36.opt-1.pyc","mode":33188,"size":22066,"sha256":"dccce4df47ccc9f9cdc0f07af81101d01f8850b44ba40a5cfd364a6954136970"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/smartcols.cpython-36.pyc","mode":33188,"size":22066,"sha256":"dccce4df47ccc9f9cdc0f07af81101d01f8850b44ba40a5cfd364a6954136970"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/transaction.cpython-36.opt-1.pyc","mode":33188,"size":52214,"sha256":"b93bcee6a7ae36a3e23aed9e41a01cfa2cdbe46a3c480aa5054329f1072fcb92"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/transaction.cpython-36.pyc","mode":33188,"size":52214,"sha256":"b93bcee6a7ae36a3e23aed9e41a01cfa2cdbe46a3c480aa5054329f1072fcb92"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/utils.cpython-36.opt-1.pyc","mode":33188,"size":8631,"sha256":"2d453ee98b030409c2d5affb839fddbc717759664456056140869f37956cec7d"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/__pycache__/utils.cpython-36.pyc","mode":33188,"size":8631,"sha256":"2d453ee98b030409c2d5affb839fddbc717759664456056140869f37956cec7d"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/_common_types.so","mode":33261,"size":510856,"sha256":"aab8cc1a2d2961ae290142b4930ad7b0e7fe16e6cab029b9e3e7546943219374"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/_conf.so","mode":33261,"size":695728,"sha256":"cba2024fe43eca8c9373c95ad1120df6b6fbb566b2ce9e2d155345b26d009f14"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/_module.so","mode":33261,"size":812152,"sha256":"7586cb82797f5d69e3257dc7fee99165c1e4602d52593916c8a891c4a6a6efc7"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/_repo.so","mode":33261,"size":307416,"sha256":"eb3adec8d2f68f214ecaa17fc8d5dde623edab4ddc72bc7c5041fa46a0935599"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/_smartcols.so","mode":33261,"size":232552,"sha256":"281e3470379df09d224c62059fcae11387ce3e39a5adf9480ee59ec49fa00bf5"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/_transaction.so","mode":33261,"size":452504,"sha256":"b3685f2dae870e39a318c5383c336c1f3d033eb82334814e74f4b14b19c168b0"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/_utils.so","mode":33261,"size":94584,"sha256":"cc652c00e6d73adaa4a5a94333c71fbee31d0bf86f79f2b96ec8caa575f52169"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/common_types.py","mode":33188,"size":34439,"sha256":"577866136196ca5749f175856d1cd61ed1bcea49febb68c2adb831f09ce3cba5"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/conf.py","mode":33188,"size":67448,"sha256":"400eebae329c05c1bab9f6c6a7ff8a89532106a5457ebbd012202dacf575f949"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/module.py","mode":33188,"size":43317,"sha256":"72e1bf39088b4e31e5f051eed0082ed8767acc45652e34b1950261d2b113f848"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/repo.py","mode":33188,"size":22007,"sha256":"f545c9131fe7075b38b370753843c83939e4d281c9ad97455c107ac7b520e15f"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/smartcols.py","mode":33188,"size":15164,"sha256":"d289a8eec2db70afa428cd2d9be286a4092a880446b781b03c44d6f3e3c3d6a8"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/transaction.py","mode":33188,"size":40532,"sha256":"4b79311390681b3f3d2b3d5ab2550a3c4898872c0ec1e8aaf22da1d55c9e8fa7"},{"path":"/usr/lib64/python3.6/site-packages/libdnf/utils.py","mode":33188,"size":7882,"sha256":"6883e559c0b27183e7a6b282b393f26f7fe5b447b0d0e42b286fd9b12e8a75b1"}]}},{"name":"python3-libs","version":"3.6.8-23.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-libs:python3-libs:3.6.8-23.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-libs:3.6.8-23.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-libs@0:3.6.8-23.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"python3-libs","version":"3.6.8","epoch":0,"architecture":"x86_64","release":"23.el8","sourceRpm":"python3-3.6.8-23.el8.src.rpm","size":32187857,"license":"Python","vendor":"CentOS","files":[{"path":"/usr/include/python3.6m/pyconfig-64.h","mode":33188,"size":44508,"sha256":"89d58bf9f0b84d258f9905caed4f89555186c12f6eeba5fc3a9901a46825bc7b"},{"path":"/usr/lib/.build-id/05/593bb87c52cccbbc0c88d53a855a3094b06db2","mode":41471,"size":86,"sha256":""},{"path":"/usr/lib/.build-id/07/8f3df84d03e047d8f6faadfbd5ae74d173760d","mode":41471,"size":84,"sha256":""},{"path":"/usr/lib/.build-id/0a/1e6f99f26d5e43b412479aa6d1d103c8bb3dd4","mode":41471,"size":84,"sha256":""},{"path":"/usr/lib/.build-id/0a/aaada9b04641710a4d7fa7aad16213f9e1e04b","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/0b/61f913cfcf5b0d21ef5543743cea9a053ee93b","mode":41471,"size":87,"sha256":""},{"path":"/usr/lib/.build-id/0c/1e90d63df2bc444a3e7808aed262bc932a879f","mode":41471,"size":82,"sha256":""},{"path":"/usr/lib/.build-id/0d/57ce0570295bd8f417b3e33a9c54018d4c9089","mode":41471,"size":92,"sha256":""},{"path":"/usr/lib/.build-id/0e/0949a653fde6162756e1b16c9b4cedb5200614","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/18/72345dd97b81288423dba285128b1d03f80c77","mode":41471,"size":86,"sha256":""},{"path":"/usr/lib/.build-id/1c/be0ba17a1958a083559464fd73566088a1af70","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/20/4290c74fc6b277625504b3744e7ae81f835a1f","mode":41471,"size":88,"sha256":""},{"path":"/usr/lib/.build-id/22/6539fd7f17cdf0ff4509f6ef38695686c61aea","mode":41471,"size":87,"sha256":""},{"path":"/usr/lib/.build-id/23/872658b6c12cd88b9bdc82e23ed1b9c77ac77d","mode":41471,"size":86,"sha256":""},{"path":"/usr/lib/.build-id/2c/546d042263d7d75dbba1ce9420cf7aa36e5959","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/2f/a2ef8add4c60b8885ab7feaee72f56038b0833","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/30/8afccd9cf301c02428d67ed5e184b32c12be87","mode":41471,"size":81,"sha256":""},{"path":"/usr/lib/.build-id/31/fda667bf35190c0ce6ec6b1d6b753e0c90ce58","mode":41471,"size":86,"sha256":""},{"path":"/usr/lib/.build-id/33/845827a18289aba4c39524b392b5bb19b91396","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/33/f20b91aa9105e90502ec78f27c9f36063f856b","mode":41471,"size":88,"sha256":""},{"path":"/usr/lib/.build-id/37/495a017f105d305fd123aa14513acad687bb63","mode":41471,"size":86,"sha256":""},{"path":"/usr/lib/.build-id/3a/3767e54f7cc289cac88b743b56d02c570d9ade","mode":41471,"size":82,"sha256":""},{"path":"/usr/lib/.build-id/47/001bc8c5802417ed9ac30660c9a9993c2d0bf0","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/4a/1790855638147e5992cf5412549b6be59f0e78","mode":41471,"size":91,"sha256":""},{"path":"/usr/lib/.build-id/4f/17eeea0f9a075b8e7e0612b66a3ebef247a2b6","mode":41471,"size":84,"sha256":""},{"path":"/usr/lib/.build-id/4f/c37ea53adda119c53af3d85c702bc6c86de6b4","mode":41471,"size":81,"sha256":""},{"path":"/usr/lib/.build-id/56/910ccf19a29b69f36b6e8a059e5262111b5b4a","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/5f/f93b68eb3ca9a8c89908ffa19934192e8f66e5","mode":41471,"size":84,"sha256":""},{"path":"/usr/lib/.build-id/64/eb6ba6df915c05676b3e114ac662b0961a3604","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/65/b93280a00a46e2ef90c19145bc2347bafd2541","mode":41471,"size":82,"sha256":""},{"path":"/usr/lib/.build-id/67/8319bbcae6ec074f5e13b1862a8fd3ef240e7d","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/67/b6f1af9136d85c43e8532d7b8f4459ab9c18e7","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/6a/19be439129d70a85c8b3c076999e3da3d10954","mode":41471,"size":81,"sha256":""},{"path":"/usr/lib/.build-id/6a/7c5d81d9ab7e866fbc1b65fd8e8dc54ba22c01","mode":41471,"size":79,"sha256":""},{"path":"/usr/lib/.build-id/6a/fb38e8586f699b71b884f4f1121ab2e381975c","mode":41471,"size":89,"sha256":""},{"path":"/usr/lib/.build-id/73/22dd62f80541864532bf8d8b52526d19180251","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/74/fb10f8c10349efbf50b19e302c393c05fed297","mode":41471,"size":91,"sha256":""},{"path":"/usr/lib/.build-id/78/d05f8375f640f0f7b2bf19edc31c8cf08c0968","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/7b/16e114c80de3969092512f2abca54da4102e28","mode":41471,"size":92,"sha256":""},{"path":"/usr/lib/.build-id/7d/d045cbd8175d0e90e31f4d5e522f040833380f","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/89/411dbd05e5b31ca7006a0f7681fb11c72ff623","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/92/de75e037aa068849c6ac3e302f7f4ec6d846ee","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/97/07c0400fc1114434046ecf410b77d5c75c0d2c","mode":41471,"size":81,"sha256":""},{"path":"/usr/lib/.build-id/9a/24eeb9bcc904dddde15d6ace0ab61a50df51f0","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/9c/ea697dadb3820afde0166a17f9f2620aea7e44","mode":41471,"size":85,"sha256":""},{"path":"/usr/lib/.build-id/9c/f222b4e0b1d378215c7799c576627a4fe05393","mode":41471,"size":82,"sha256":""},{"path":"/usr/lib/.build-id/a3/55e390f04a68fe9760cb8055141abec7633513","mode":41471,"size":84,"sha256":""},{"path":"/usr/lib/.build-id/bf/971b70c5f2975343e5cd51149081ef689e0a4a","mode":41471,"size":84,"sha256":""},{"path":"/usr/lib/.build-id/c2/34aca6ed39b90f755b647bb74c383bea4c5530","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/c9/f99120d1d9fee141dfd996fa7fd95883812dce","mode":41471,"size":91,"sha256":""},{"path":"/usr/lib/.build-id/d9/1402836bb02929e58ba29648272414d3e5f5fe","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/da/8a9fa689464af9771c9654fcc3767d78f46c0a","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/da/fde8fac2ba2a83ab3c1f357dd812bf94d5a272","mode":41471,"size":81,"sha256":""},{"path":"/usr/lib/.build-id/dd/20f1a0d28624c648e968ca3b736f56966b1289","mode":41471,"size":81,"sha256":""},{"path":"/usr/lib/.build-id/de/a3afdc74419f227c9869ac6fba7c4eb94148e3","mode":41471,"size":79,"sha256":""},{"path":"/usr/lib/.build-id/e1/730f80464f723ca396281b80cedf69f22eb389","mode":41471,"size":85,"sha256":""},{"path":"/usr/lib/.build-id/e2/48d246084c469cb59b58bbb3c4a9ec6f864741","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib/.build-id/e4/9e1cbfedf94edde96863f6a4798ae37110b11f","mode":41471,"size":84,"sha256":""},{"path":"/usr/lib/.build-id/ee/cd0235abaed36fb49309da47ac013d16340a23","mode":41471,"size":81,"sha256":""},{"path":"/usr/lib/.build-id/f3/5de08f7cf078c6d89c5d0d513c55bf814957a3","mode":41471,"size":82,"sha256":""},{"path":"/usr/lib/.build-id/f3/6dca9680f78a1185288b73f0021e34c02491dc","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/fd/7bc15d09d4209c9b125f10f9e93a81b28d5805","mode":41471,"size":83,"sha256":""},{"path":"/usr/lib64/libpython3.6m.so.1.0","mode":33261,"size":3312920,"sha256":"1e228552fef83e6c14b0b911ad96ac4538e68702d05116ac7ca58261edc1d13f"},{"path":"/usr/lib64/libpython3.so","mode":33261,"size":7104,"sha256":"10c6d035b2fa462e761cdf69f914501d7ebab06b98d3644d10a9c9ccd76a4747"},{"path":"/usr/lib64/python3.6/__future__.py","mode":33188,"size":4841,"sha256":"f360476748d35ebb1c55fc3644e46db265449a15cdf388121e826c2baf81382d"},{"path":"/usr/lib64/python3.6/__phello__.foo.py","mode":33188,"size":64,"sha256":"586d9bf9b42fadd32feb1fba80613bcbfb4180dbcd6f03af678b5a6deb9d6a7b"},{"path":"/usr/lib64/python3.6/__pycache__/__future__.cpython-36.opt-1.pyc","mode":33188,"size":4169,"sha256":"7e4277456639d269994400cfce6d0238f63c8262d0777e2cdcb2f6b85f5ce9f5"},{"path":"/usr/lib64/python3.6/__pycache__/__future__.cpython-36.opt-2.pyc","mode":33188,"size":2193,"sha256":"07b9c7680cb40ce8d949f53bd2548717103224ea9083a074c246072ea4242644"},{"path":"/usr/lib64/python3.6/__pycache__/__future__.cpython-36.pyc","mode":33188,"size":4169,"sha256":"7e4277456639d269994400cfce6d0238f63c8262d0777e2cdcb2f6b85f5ce9f5"},{"path":"/usr/lib64/python3.6/__pycache__/__phello__.foo.cpython-36.opt-1.pyc","mode":33188,"size":121,"sha256":"e9ac132d85327f11e0ca541acba3b6cfee662718c8de6bed670a225b483252f7"},{"path":"/usr/lib64/python3.6/__pycache__/__phello__.foo.cpython-36.opt-2.pyc","mode":33188,"size":121,"sha256":"e9ac132d85327f11e0ca541acba3b6cfee662718c8de6bed670a225b483252f7"},{"path":"/usr/lib64/python3.6/__pycache__/__phello__.foo.cpython-36.pyc","mode":33188,"size":121,"sha256":"e9ac132d85327f11e0ca541acba3b6cfee662718c8de6bed670a225b483252f7"},{"path":"/usr/lib64/python3.6/__pycache__/_bootlocale.cpython-36.opt-1.pyc","mode":33188,"size":954,"sha256":"f9c09e362631106cf11a4b4d980fa5ca329499fac5bb9ef310c0bc6ccdb197ee"},{"path":"/usr/lib64/python3.6/__pycache__/_bootlocale.cpython-36.opt-2.pyc","mode":33188,"size":729,"sha256":"3d44faf2bf394ae62bea86d461baab67227f977008aa3cac647f6b9c7daadf97"},{"path":"/usr/lib64/python3.6/__pycache__/_bootlocale.cpython-36.pyc","mode":33188,"size":982,"sha256":"715111eb620d42ee84f33e038fc04d9534af5795328757ce44fb7c626750b4da"},{"path":"/usr/lib64/python3.6/__pycache__/_collections_abc.cpython-36.opt-1.pyc","mode":33188,"size":28799,"sha256":"905cfba01f65a54e66322f08090c160c2f24027c8d3fb2319b8f788298de6d1a"},{"path":"/usr/lib64/python3.6/__pycache__/_collections_abc.cpython-36.opt-2.pyc","mode":33188,"size":23647,"sha256":"05577f1664763106ec5a4c92dc0564855ee30f54d129869b2f3c074b5d45e67a"},{"path":"/usr/lib64/python3.6/__pycache__/_collections_abc.cpython-36.pyc","mode":33188,"size":28799,"sha256":"905cfba01f65a54e66322f08090c160c2f24027c8d3fb2319b8f788298de6d1a"},{"path":"/usr/lib64/python3.6/__pycache__/_compat_pickle.cpython-36.opt-1.pyc","mode":33188,"size":6510,"sha256":"6f3b1b859770257fc9175370438f2e1eb73c0b071929da6f8129bfb897623c10"},{"path":"/usr/lib64/python3.6/__pycache__/_compat_pickle.cpython-36.opt-2.pyc","mode":33188,"size":6510,"sha256":"6f3b1b859770257fc9175370438f2e1eb73c0b071929da6f8129bfb897623c10"},{"path":"/usr/lib64/python3.6/__pycache__/_compat_pickle.cpython-36.pyc","mode":33188,"size":6568,"sha256":"9d71c987f7b82e64fbf3ea6b65590490eb21eaa151f34004f9e38249ac500c61"},{"path":"/usr/lib64/python3.6/__pycache__/_compression.cpython-36.opt-1.pyc","mode":33188,"size":4106,"sha256":"4490261a7026887202dd4bae54b9c7f57954b58fb175211c39d91760b8f230ea"},{"path":"/usr/lib64/python3.6/__pycache__/_compression.cpython-36.opt-2.pyc","mode":33188,"size":3890,"sha256":"a20b087f5123d4eaf12b54e7013d1e6ce757fc2938971d030e88169c24cf4f33"},{"path":"/usr/lib64/python3.6/__pycache__/_compression.cpython-36.pyc","mode":33188,"size":4106,"sha256":"4490261a7026887202dd4bae54b9c7f57954b58fb175211c39d91760b8f230ea"},{"path":"/usr/lib64/python3.6/__pycache__/_dummy_thread.cpython-36.opt-1.pyc","mode":33188,"size":4853,"sha256":"a4a76be11c951f0540f2ce4cc7f8752e51e67d847c5d8b326ec61435e779f805"},{"path":"/usr/lib64/python3.6/__pycache__/_dummy_thread.cpython-36.opt-2.pyc","mode":33188,"size":2645,"sha256":"8de67e5b0223e43c717413965fe7a3e7be42328a3908cd353dae00076fd7b9f1"},{"path":"/usr/lib64/python3.6/__pycache__/_dummy_thread.cpython-36.pyc","mode":33188,"size":4853,"sha256":"a4a76be11c951f0540f2ce4cc7f8752e51e67d847c5d8b326ec61435e779f805"},{"path":"/usr/lib64/python3.6/__pycache__/_markupbase.cpython-36.opt-1.pyc","mode":33188,"size":7824,"sha256":"09d6ffc7b987ec391865742624f7034c010cc5d022f1e30fe9c45dc4933c4cbf"},{"path":"/usr/lib64/python3.6/__pycache__/_markupbase.cpython-36.opt-2.pyc","mode":33188,"size":7444,"sha256":"c8154baa5a65509ce8dbfcccea309a86eaaa141819286c8b080a978c86fa0a8c"},{"path":"/usr/lib64/python3.6/__pycache__/_markupbase.cpython-36.pyc","mode":33188,"size":7993,"sha256":"c25c9d233c2c988ec51f50780e8e9719b056ad9d175271302db641f80e9ffb67"},{"path":"/usr/lib64/python3.6/__pycache__/_osx_support.cpython-36.opt-1.pyc","mode":33188,"size":9708,"sha256":"5c3c94da484b622fe04416450dab0b59203f4dbe78532aa4c47d567f5e7ef608"},{"path":"/usr/lib64/python3.6/__pycache__/_osx_support.cpython-36.opt-2.pyc","mode":33188,"size":7259,"sha256":"7cdb0f99c918b422197c23698cf949ae2f9c20ec8238b711f9ef6def59daa785"},{"path":"/usr/lib64/python3.6/__pycache__/_osx_support.cpython-36.pyc","mode":33188,"size":9708,"sha256":"5c3c94da484b622fe04416450dab0b59203f4dbe78532aa4c47d567f5e7ef608"},{"path":"/usr/lib64/python3.6/__pycache__/_pydecimal.cpython-36.opt-1.pyc","mode":33188,"size":163404,"sha256":"02f7bf9a0b1ab962eeedbb0749a40094953fadcdf53ceb1c318a51b1392723e2"},{"path":"/usr/lib64/python3.6/__pycache__/_pydecimal.cpython-36.opt-2.pyc","mode":33188,"size":81997,"sha256":"a1d851863f9d471e2d63681745592b9329d5b4fba29ce55a0510eefddda5e36b"},{"path":"/usr/lib64/python3.6/__pycache__/_pydecimal.cpython-36.pyc","mode":33188,"size":163404,"sha256":"02f7bf9a0b1ab962eeedbb0749a40094953fadcdf53ceb1c318a51b1392723e2"},{"path":"/usr/lib64/python3.6/__pycache__/_pyio.cpython-36.opt-1.pyc","mode":33188,"size":71370,"sha256":"069ec8c781686f9eec2f8f5a5bfce2fb783ad96a2939a8043323450c224a3fdd"},{"path":"/usr/lib64/python3.6/__pycache__/_pyio.cpython-36.opt-2.pyc","mode":33188,"size":48975,"sha256":"db0e6e97faec23d528a17dfb8780245f56082a5a46547a158f10a521c3c6ece4"},{"path":"/usr/lib64/python3.6/__pycache__/_pyio.cpython-36.pyc","mode":33188,"size":71388,"sha256":"35cfc631a070afdc72ca707060bf19896af5c283d87199f4946605416a9153bb"},{"path":"/usr/lib64/python3.6/__pycache__/_sitebuiltins.cpython-36.opt-1.pyc","mode":33188,"size":3437,"sha256":"f35841d252ff8af862b400de72d8de0e2477f4130ae72f29e037009ac508f507"},{"path":"/usr/lib64/python3.6/__pycache__/_sitebuiltins.cpython-36.opt-2.pyc","mode":33188,"size":2913,"sha256":"ef4a0de0657436dc9185c29f414c9c0742a6ca986231334e0bb9f5e77581df5c"},{"path":"/usr/lib64/python3.6/__pycache__/_sitebuiltins.cpython-36.pyc","mode":33188,"size":3437,"sha256":"f35841d252ff8af862b400de72d8de0e2477f4130ae72f29e037009ac508f507"},{"path":"/usr/lib64/python3.6/__pycache__/_strptime.cpython-36.opt-1.pyc","mode":33188,"size":15965,"sha256":"8a85d9ec10cc3657e49a1187dff7e09cc94a4feff0dbe83d02967554633442c7"},{"path":"/usr/lib64/python3.6/__pycache__/_strptime.cpython-36.opt-2.pyc","mode":33188,"size":12235,"sha256":"2b01a37dce183f9f095c29bf5c11d5a8f0bf8e96ba312b22a8d7b83d9e887b1d"},{"path":"/usr/lib64/python3.6/__pycache__/_strptime.cpython-36.pyc","mode":33188,"size":15965,"sha256":"8a85d9ec10cc3657e49a1187dff7e09cc94a4feff0dbe83d02967554633442c7"},{"path":"/usr/lib64/python3.6/__pycache__/_sysconfigdata_dm_linux_x86_64-linux-gnu.cpython-36.opt-1.pyc","mode":33188,"size":21910,"sha256":"7d767bfb50abe0f1c5620b840e1e1125f2f6aa81d9b3fc4c00f42a2b0f317a49"},{"path":"/usr/lib64/python3.6/__pycache__/_sysconfigdata_dm_linux_x86_64-linux-gnu.cpython-36.opt-2.pyc","mode":33188,"size":21910,"sha256":"7d767bfb50abe0f1c5620b840e1e1125f2f6aa81d9b3fc4c00f42a2b0f317a49"},{"path":"/usr/lib64/python3.6/__pycache__/_sysconfigdata_dm_linux_x86_64-linux-gnu.cpython-36.pyc","mode":33188,"size":21910,"sha256":"7d767bfb50abe0f1c5620b840e1e1125f2f6aa81d9b3fc4c00f42a2b0f317a49"},{"path":"/usr/lib64/python3.6/__pycache__/_sysconfigdata_m_linux_x86_64-linux-gnu.cpython-36.opt-1.pyc","mode":33188,"size":22036,"sha256":"5bd6942a5c2a88d9d76f8799d3aeac78b4b75888f5b32e982fb397152592925b"},{"path":"/usr/lib64/python3.6/__pycache__/_sysconfigdata_m_linux_x86_64-linux-gnu.cpython-36.opt-2.pyc","mode":33188,"size":22036,"sha256":"5bd6942a5c2a88d9d76f8799d3aeac78b4b75888f5b32e982fb397152592925b"},{"path":"/usr/lib64/python3.6/__pycache__/_sysconfigdata_m_linux_x86_64-linux-gnu.cpython-36.pyc","mode":33188,"size":22036,"sha256":"5bd6942a5c2a88d9d76f8799d3aeac78b4b75888f5b32e982fb397152592925b"},{"path":"/usr/lib64/python3.6/__pycache__/_threading_local.cpython-36.opt-1.pyc","mode":33188,"size":6427,"sha256":"e844b217dfa9bc8a66953b989cd9efa4bbe4fdb750c0a8c87db3f288ed68f279"},{"path":"/usr/lib64/python3.6/__pycache__/_threading_local.cpython-36.opt-2.pyc","mode":33188,"size":3112,"sha256":"cd6a4532e66d6e28843cff47757a8343033893ec7543e3f64e08e5cdf876d447"},{"path":"/usr/lib64/python3.6/__pycache__/_threading_local.cpython-36.pyc","mode":33188,"size":6427,"sha256":"e844b217dfa9bc8a66953b989cd9efa4bbe4fdb750c0a8c87db3f288ed68f279"},{"path":"/usr/lib64/python3.6/__pycache__/_weakrefset.cpython-36.opt-1.pyc","mode":33188,"size":7830,"sha256":"9e16f75d846fca52fe3e01e1a0fe731b7c17e691ef085799a2be87a3c30979ce"},{"path":"/usr/lib64/python3.6/__pycache__/_weakrefset.cpython-36.opt-2.pyc","mode":33188,"size":7830,"sha256":"9e16f75d846fca52fe3e01e1a0fe731b7c17e691ef085799a2be87a3c30979ce"},{"path":"/usr/lib64/python3.6/__pycache__/_weakrefset.cpython-36.pyc","mode":33188,"size":7830,"sha256":"9e16f75d846fca52fe3e01e1a0fe731b7c17e691ef085799a2be87a3c30979ce"},{"path":"/usr/lib64/python3.6/__pycache__/abc.cpython-36.opt-1.pyc","mode":33188,"size":7474,"sha256":"64efc2de0de84dcdfd5398fe191e24adc7d94f29bee7bfb98d91656ba5520908"},{"path":"/usr/lib64/python3.6/__pycache__/abc.cpython-36.opt-2.pyc","mode":33188,"size":4110,"sha256":"2c9fb2e2f4740532a57f814396e2b4812e589a9d6c84e77dcb643c3da9876758"},{"path":"/usr/lib64/python3.6/__pycache__/abc.cpython-36.pyc","mode":33188,"size":7517,"sha256":"a642b8a9cf907c9ad955080c631164fce6039f49f841537bf5c7d0c0afbb4a9a"},{"path":"/usr/lib64/python3.6/__pycache__/aifc.cpython-36.opt-1.pyc","mode":33188,"size":25945,"sha256":"e198d642d2a9376d2c83559bd2d90b07239516c2803094b0c7d06ceea02aebb0"},{"path":"/usr/lib64/python3.6/__pycache__/aifc.cpython-36.opt-2.pyc","mode":33188,"size":20740,"sha256":"c02bf6601d4d4acc41f6ba34c6dcd2d298c374b1328b2e72a158da0d90246872"},{"path":"/usr/lib64/python3.6/__pycache__/aifc.cpython-36.pyc","mode":33188,"size":25945,"sha256":"e198d642d2a9376d2c83559bd2d90b07239516c2803094b0c7d06ceea02aebb0"},{"path":"/usr/lib64/python3.6/__pycache__/antigravity.cpython-36.opt-1.pyc","mode":33188,"size":781,"sha256":"f92a3cb73038e910e1c340a8e54a2fb3857dcf4fc709c26ad2cc239c0fb87a5a"},{"path":"/usr/lib64/python3.6/__pycache__/antigravity.cpython-36.opt-2.pyc","mode":33188,"size":637,"sha256":"7b15cbde93c51c11188d608f40fc910eb871dbf937a0aa4a94bdc9f881b972aa"},{"path":"/usr/lib64/python3.6/__pycache__/antigravity.cpython-36.pyc","mode":33188,"size":781,"sha256":"f92a3cb73038e910e1c340a8e54a2fb3857dcf4fc709c26ad2cc239c0fb87a5a"},{"path":"/usr/lib64/python3.6/__pycache__/argparse.cpython-36.opt-1.pyc","mode":33188,"size":60058,"sha256":"ea29d21bb713f06136c14e9bcefe2dddc5e62812c99cb5c2bd1b2c3cd24bae53"},{"path":"/usr/lib64/python3.6/__pycache__/argparse.cpython-36.opt-2.pyc","mode":33188,"size":50817,"sha256":"8eddab9227ece801e300c6f3b87e314c957d98bbb93fda0649f8f04f5716b08a"},{"path":"/usr/lib64/python3.6/__pycache__/argparse.cpython-36.pyc","mode":33188,"size":60192,"sha256":"ac41e4d2e265655e4348953959da953dc07ed285a85f57a5eac5a4e7ceb79055"},{"path":"/usr/lib64/python3.6/__pycache__/ast.cpython-36.opt-1.pyc","mode":33188,"size":11706,"sha256":"314347f2f9ed37b5b01dc99ab269addb9f6121270feecf700747337f56894801"},{"path":"/usr/lib64/python3.6/__pycache__/ast.cpython-36.opt-2.pyc","mode":33188,"size":6121,"sha256":"e466f5b14dcde97fd6a0eac238ee9f59bde1fabaf2d5d6a9141e704553fc048f"},{"path":"/usr/lib64/python3.6/__pycache__/ast.cpython-36.pyc","mode":33188,"size":11706,"sha256":"314347f2f9ed37b5b01dc99ab269addb9f6121270feecf700747337f56894801"},{"path":"/usr/lib64/python3.6/__pycache__/asynchat.cpython-36.opt-1.pyc","mode":33188,"size":6817,"sha256":"c08d736933aeeecab26c9fb37d4b6282ba5c79ee314cba51de7c59d85b6ecfd8"},{"path":"/usr/lib64/python3.6/__pycache__/asynchat.cpython-36.opt-2.pyc","mode":33188,"size":5441,"sha256":"f410ce2b707dec8fd5508a8bf160a7b577582198c8a46b7e1816f098805586cd"},{"path":"/usr/lib64/python3.6/__pycache__/asynchat.cpython-36.pyc","mode":33188,"size":6817,"sha256":"c08d736933aeeecab26c9fb37d4b6282ba5c79ee314cba51de7c59d85b6ecfd8"},{"path":"/usr/lib64/python3.6/__pycache__/asyncore.cpython-36.opt-1.pyc","mode":33188,"size":15840,"sha256":"b64be8bfe93bb032495efff4d8929a715b17637066030dd33786c1ccadd65060"},{"path":"/usr/lib64/python3.6/__pycache__/asyncore.cpython-36.opt-2.pyc","mode":33188,"size":14636,"sha256":"ec2c37a22eb2f9098bbf2894261918b8d0f29985a7ed9dc9a53e0f1b8d7c1b5e"},{"path":"/usr/lib64/python3.6/__pycache__/asyncore.cpython-36.pyc","mode":33188,"size":15840,"sha256":"b64be8bfe93bb032495efff4d8929a715b17637066030dd33786c1ccadd65060"},{"path":"/usr/lib64/python3.6/__pycache__/base64.cpython-36.opt-1.pyc","mode":33188,"size":16903,"sha256":"09b9479ae80a03e4700590058d7ba5f3d303e0d2d45d15a426627fa7845b8f74"},{"path":"/usr/lib64/python3.6/__pycache__/base64.cpython-36.opt-2.pyc","mode":33188,"size":11305,"sha256":"98219064b6860556778dc4d2f1ad00312ebb66d41c8b1a4d80f08989f63fce0d"},{"path":"/usr/lib64/python3.6/__pycache__/base64.cpython-36.pyc","mode":33188,"size":17061,"sha256":"ea252683c1066bedf2b03f8bc8be0ecc4c1f08c84ba2964370ece0750b102133"},{"path":"/usr/lib64/python3.6/__pycache__/bdb.cpython-36.opt-1.pyc","mode":33188,"size":17035,"sha256":"bb11ea15f1d79a35a0b3bc4577b3eb99a9a355a5d054a15481feeb2a76b6233a"},{"path":"/usr/lib64/python3.6/__pycache__/bdb.cpython-36.opt-2.pyc","mode":33188,"size":15309,"sha256":"876320f43a1d187e0826e15de6ee86b1bbc8f6f20299d881dffab8948dec03ec"},{"path":"/usr/lib64/python3.6/__pycache__/bdb.cpython-36.pyc","mode":33188,"size":17035,"sha256":"bb11ea15f1d79a35a0b3bc4577b3eb99a9a355a5d054a15481feeb2a76b6233a"},{"path":"/usr/lib64/python3.6/__pycache__/binhex.cpython-36.opt-1.pyc","mode":33188,"size":12088,"sha256":"c633a02e31afed9e0080b4087daacf943aca0de1167fa088e511a259bbbdfdac"},{"path":"/usr/lib64/python3.6/__pycache__/binhex.cpython-36.opt-2.pyc","mode":33188,"size":11555,"sha256":"eda5e0d549146ce17a7c54aab109d9a7c570024d01769c567d56f7f571dc9ff1"},{"path":"/usr/lib64/python3.6/__pycache__/binhex.cpython-36.pyc","mode":33188,"size":12088,"sha256":"c633a02e31afed9e0080b4087daacf943aca0de1167fa088e511a259bbbdfdac"},{"path":"/usr/lib64/python3.6/__pycache__/bisect.cpython-36.opt-1.pyc","mode":33188,"size":2678,"sha256":"f34e1351465f02641e57136644beca7113e9c0f2fb8122e10d7709210ef34c27"},{"path":"/usr/lib64/python3.6/__pycache__/bisect.cpython-36.opt-2.pyc","mode":33188,"size":1382,"sha256":"feae2a45b76658e13b00fc6398d9f4ce7113f99a54c09dc2feb85578fab2b50f"},{"path":"/usr/lib64/python3.6/__pycache__/bisect.cpython-36.pyc","mode":33188,"size":2678,"sha256":"f34e1351465f02641e57136644beca7113e9c0f2fb8122e10d7709210ef34c27"},{"path":"/usr/lib64/python3.6/__pycache__/bz2.cpython-36.opt-1.pyc","mode":33188,"size":11284,"sha256":"c73c3771cb560c76cc1e1586165a2f4523e0ee41633f69244ce97b38c7c11803"},{"path":"/usr/lib64/python3.6/__pycache__/bz2.cpython-36.opt-2.pyc","mode":33188,"size":6227,"sha256":"1cd9249baacee0f54f1f1c45fd7a7d1622189a3b75fad191de4279f1ce4e67de"},{"path":"/usr/lib64/python3.6/__pycache__/bz2.cpython-36.pyc","mode":33188,"size":11284,"sha256":"c73c3771cb560c76cc1e1586165a2f4523e0ee41633f69244ce97b38c7c11803"},{"path":"/usr/lib64/python3.6/__pycache__/cProfile.cpython-36.opt-1.pyc","mode":33188,"size":4296,"sha256":"74f6c4dd2458236c15d130c4558df3cb74726842f8a4593398ff8113e5fd06e0"},{"path":"/usr/lib64/python3.6/__pycache__/cProfile.cpython-36.opt-2.pyc","mode":33188,"size":3835,"sha256":"fdebc45437aec5a37f41e51ff16e51b08235c2c3553451df4abba0bf6778a62c"},{"path":"/usr/lib64/python3.6/__pycache__/cProfile.cpython-36.pyc","mode":33188,"size":4296,"sha256":"74f6c4dd2458236c15d130c4558df3cb74726842f8a4593398ff8113e5fd06e0"},{"path":"/usr/lib64/python3.6/__pycache__/calendar.cpython-36.opt-1.pyc","mode":33188,"size":25884,"sha256":"025ce8144edc4126918afbd4e32d6f54ace8308d2647bf5b0107d6cf2a5895d1"},{"path":"/usr/lib64/python3.6/__pycache__/calendar.cpython-36.opt-2.pyc","mode":33188,"size":21357,"sha256":"c98813e5a7df5ab8ab236767d870e570125de15f5173916db0a86b0085b31ff3"},{"path":"/usr/lib64/python3.6/__pycache__/calendar.cpython-36.pyc","mode":33188,"size":25884,"sha256":"025ce8144edc4126918afbd4e32d6f54ace8308d2647bf5b0107d6cf2a5895d1"},{"path":"/usr/lib64/python3.6/__pycache__/cgi.cpython-36.opt-1.pyc","mode":33188,"size":28418,"sha256":"39736eef86e7c93da0c06b786c8452c81ad652c95f85750878d62d239c918f1b"},{"path":"/usr/lib64/python3.6/__pycache__/cgi.cpython-36.opt-2.pyc","mode":33188,"size":19385,"sha256":"acd301c27a5d2844b0a874d95f59aa61c73c6a4bc094672a653798dd9457a3e8"},{"path":"/usr/lib64/python3.6/__pycache__/cgi.cpython-36.pyc","mode":33188,"size":28418,"sha256":"39736eef86e7c93da0c06b786c8452c81ad652c95f85750878d62d239c918f1b"},{"path":"/usr/lib64/python3.6/__pycache__/cgitb.cpython-36.opt-1.pyc","mode":33188,"size":10082,"sha256":"87127586469f948de1905f0e326ce2a5a9895337f274f0b39376d8f8eef2f182"},{"path":"/usr/lib64/python3.6/__pycache__/cgitb.cpython-36.opt-2.pyc","mode":33188,"size":8483,"sha256":"8190abe84458c44d4d5dfca9896e8bc63d97cc23b6db49474d3d13a30d5f8fb6"},{"path":"/usr/lib64/python3.6/__pycache__/cgitb.cpython-36.pyc","mode":33188,"size":10082,"sha256":"87127586469f948de1905f0e326ce2a5a9895337f274f0b39376d8f8eef2f182"},{"path":"/usr/lib64/python3.6/__pycache__/chunk.cpython-36.opt-1.pyc","mode":33188,"size":4902,"sha256":"7bd335c1d70a7c2885741ff75b93c75fb519bbe1a8fe2c0aa0265964f14ee5d7"},{"path":"/usr/lib64/python3.6/__pycache__/chunk.cpython-36.opt-2.pyc","mode":33188,"size":2756,"sha256":"9ac92072a5f9231e678bd055d803ca16d6a1b2de59f369e35b52fd537640e021"},{"path":"/usr/lib64/python3.6/__pycache__/chunk.cpython-36.pyc","mode":33188,"size":4902,"sha256":"7bd335c1d70a7c2885741ff75b93c75fb519bbe1a8fe2c0aa0265964f14ee5d7"},{"path":"/usr/lib64/python3.6/__pycache__/cmd.cpython-36.opt-1.pyc","mode":33188,"size":12577,"sha256":"fb5ebf63d53ef55a76078a3963fc2a71e8b1fb1027a05e31cbbb6735db62dbec"},{"path":"/usr/lib64/python3.6/__pycache__/cmd.cpython-36.opt-2.pyc","mode":33188,"size":7138,"sha256":"8c9335d6825e9ca3c9efcddab46c920d07923d49aeea6ab8a10a3c86925de01e"},{"path":"/usr/lib64/python3.6/__pycache__/cmd.cpython-36.pyc","mode":33188,"size":12577,"sha256":"fb5ebf63d53ef55a76078a3963fc2a71e8b1fb1027a05e31cbbb6735db62dbec"},{"path":"/usr/lib64/python3.6/__pycache__/code.cpython-36.opt-1.pyc","mode":33188,"size":9838,"sha256":"0ca6b8361a09eafe2b04e9693493f9b71d9db2f012a5f8dd4fc346075d3531c9"},{"path":"/usr/lib64/python3.6/__pycache__/code.cpython-36.opt-2.pyc","mode":33188,"size":4562,"sha256":"04833d99968658a76ee4c2b2049c9805bea5b6746c52186db63716011fb2ee00"},{"path":"/usr/lib64/python3.6/__pycache__/code.cpython-36.pyc","mode":33188,"size":9838,"sha256":"0ca6b8361a09eafe2b04e9693493f9b71d9db2f012a5f8dd4fc346075d3531c9"},{"path":"/usr/lib64/python3.6/__pycache__/codecs.cpython-36.opt-1.pyc","mode":33188,"size":33902,"sha256":"e02db1010f978cd95d88330cedc7f181a43f0d07371275aaafd5c1bb298b1960"},{"path":"/usr/lib64/python3.6/__pycache__/codecs.cpython-36.opt-2.pyc","mode":33188,"size":18054,"sha256":"68da7ddb1e78aac937efa7abdb0314c4adaaacef0989e8e6eb650bc2e51b777b"},{"path":"/usr/lib64/python3.6/__pycache__/codecs.cpython-36.pyc","mode":33188,"size":33902,"sha256":"e02db1010f978cd95d88330cedc7f181a43f0d07371275aaafd5c1bb298b1960"},{"path":"/usr/lib64/python3.6/__pycache__/codeop.cpython-36.opt-1.pyc","mode":33188,"size":6272,"sha256":"efa5e326bdf7382a9601e2622c6c58bcaac3400d2f2b054ef5321495fa080b90"},{"path":"/usr/lib64/python3.6/__pycache__/codeop.cpython-36.opt-2.pyc","mode":33188,"size":2225,"sha256":"86ec8c83ad77ce1b68df7856c68af01a03120337c88f0162797b6e20092cd191"},{"path":"/usr/lib64/python3.6/__pycache__/codeop.cpython-36.pyc","mode":33188,"size":6272,"sha256":"efa5e326bdf7382a9601e2622c6c58bcaac3400d2f2b054ef5321495fa080b90"},{"path":"/usr/lib64/python3.6/__pycache__/colorsys.cpython-36.opt-1.pyc","mode":33188,"size":3313,"sha256":"8fd8af21f942a5c48a9704d7fc83c9f01748c9be619d32b787db9a338bd460c6"},{"path":"/usr/lib64/python3.6/__pycache__/colorsys.cpython-36.opt-2.pyc","mode":33188,"size":2707,"sha256":"cc8e440fd0d8d9c3840b00a8185bd9f87eb28a19894bb833079d1825bd3c0849"},{"path":"/usr/lib64/python3.6/__pycache__/colorsys.cpython-36.pyc","mode":33188,"size":3313,"sha256":"8fd8af21f942a5c48a9704d7fc83c9f01748c9be619d32b787db9a338bd460c6"},{"path":"/usr/lib64/python3.6/__pycache__/compileall.cpython-36.opt-1.pyc","mode":33188,"size":8280,"sha256":"12c8eaf0f8c47cf370089b67d32658553d9b4d52ba5591e1cf9d30fb9ccccaf4"},{"path":"/usr/lib64/python3.6/__pycache__/compileall.cpython-36.opt-2.pyc","mode":33188,"size":6142,"sha256":"7decf60f2af53073e78474e7985e375b76e45a9dca8b3fb02d55c449855ce679"},{"path":"/usr/lib64/python3.6/__pycache__/compileall.cpython-36.pyc","mode":33188,"size":8280,"sha256":"12c8eaf0f8c47cf370089b67d32658553d9b4d52ba5591e1cf9d30fb9ccccaf4"},{"path":"/usr/lib64/python3.6/__pycache__/configparser.cpython-36.opt-1.pyc","mode":33188,"size":45246,"sha256":"c63ade4738d16262adc76f7d32c77def241b97108dd8518b7aa230d5018cc87e"},{"path":"/usr/lib64/python3.6/__pycache__/configparser.cpython-36.opt-2.pyc","mode":33188,"size":30558,"sha256":"06fe0a669e0ca70bf0ac52a5986da92eaf5272b566bb61559a4a73ea657f10c8"},{"path":"/usr/lib64/python3.6/__pycache__/configparser.cpython-36.pyc","mode":33188,"size":45246,"sha256":"c63ade4738d16262adc76f7d32c77def241b97108dd8518b7aa230d5018cc87e"},{"path":"/usr/lib64/python3.6/__pycache__/contextlib.cpython-36.opt-1.pyc","mode":33188,"size":11160,"sha256":"ef518c5b63ab39d4335b6ef27c95fe1d944ee03948549baf3866ccc0669a13d4"},{"path":"/usr/lib64/python3.6/__pycache__/contextlib.cpython-36.opt-2.pyc","mode":33188,"size":7814,"sha256":"8c39b94b44da3bf08df066528706bfd147837f822c7b6a04cf812c826030d0d6"},{"path":"/usr/lib64/python3.6/__pycache__/contextlib.cpython-36.pyc","mode":33188,"size":11160,"sha256":"ef518c5b63ab39d4335b6ef27c95fe1d944ee03948549baf3866ccc0669a13d4"},{"path":"/usr/lib64/python3.6/__pycache__/copy.cpython-36.opt-1.pyc","mode":33188,"size":7081,"sha256":"7c30eaee91b5c799a3db06302938e45a40ea329c5a25695db3ea0a9c378e323e"},{"path":"/usr/lib64/python3.6/__pycache__/copy.cpython-36.opt-2.pyc","mode":33188,"size":4765,"sha256":"f048c84c1d004f534e55c395d505626d3196699e109a2263c885f40b9de5ab61"},{"path":"/usr/lib64/python3.6/__pycache__/copy.cpython-36.pyc","mode":33188,"size":7081,"sha256":"7c30eaee91b5c799a3db06302938e45a40ea329c5a25695db3ea0a9c378e323e"},{"path":"/usr/lib64/python3.6/__pycache__/copyreg.cpython-36.opt-1.pyc","mode":33188,"size":4211,"sha256":"1a2021f0f0cf9586c0d13d7bc3458902c4bbb59d2a99b176ebb3c9ca7703fc88"},{"path":"/usr/lib64/python3.6/__pycache__/copyreg.cpython-36.opt-2.pyc","mode":33188,"size":3407,"sha256":"c9ed1b21629ad56033a4ca2fd54f8f91b95adac414a647a19c713c212870a19c"},{"path":"/usr/lib64/python3.6/__pycache__/copyreg.cpython-36.pyc","mode":33188,"size":4246,"sha256":"ea1f7b60f4225413ab2e84eb21f36a652416d4ae59b95d5ff8e6f0783575e4de"},{"path":"/usr/lib64/python3.6/__pycache__/crypt.cpython-36.opt-1.pyc","mode":33188,"size":2244,"sha256":"0aad682050ccb1448ba70541799006d80bd72bdcad4a685c9a1e15297c0d7815"},{"path":"/usr/lib64/python3.6/__pycache__/crypt.cpython-36.opt-2.pyc","mode":33188,"size":1580,"sha256":"1fac4a13a68d023509ff44caa3602634a81272986b520a6cd62398747923e6b1"},{"path":"/usr/lib64/python3.6/__pycache__/crypt.cpython-36.pyc","mode":33188,"size":2244,"sha256":"0aad682050ccb1448ba70541799006d80bd72bdcad4a685c9a1e15297c0d7815"},{"path":"/usr/lib64/python3.6/__pycache__/csv.cpython-36.opt-1.pyc","mode":33188,"size":11857,"sha256":"f9cb9e349e2da2a60b28435e41c7fb654a078d7fec662d407caa16c123c8de37"},{"path":"/usr/lib64/python3.6/__pycache__/csv.cpython-36.opt-2.pyc","mode":33188,"size":9818,"sha256":"3a08d1dbae52bcf3fb9606aa6f010310e51ae474bf15a3e0d1d5b1f3c1c5a8d7"},{"path":"/usr/lib64/python3.6/__pycache__/csv.cpython-36.pyc","mode":33188,"size":11857,"sha256":"f9cb9e349e2da2a60b28435e41c7fb654a078d7fec662d407caa16c123c8de37"},{"path":"/usr/lib64/python3.6/__pycache__/datetime.cpython-36.opt-1.pyc","mode":33188,"size":53060,"sha256":"d0dc9696a55b68bb45a08fd1895be62d6b5e741487c5ab1cfe3fa95bb3f6735d"},{"path":"/usr/lib64/python3.6/__pycache__/datetime.cpython-36.opt-2.pyc","mode":33188,"size":44210,"sha256":"52928d6ad8c9bd0f927dc6ac437237d8013df3718b6cbd3b1046103016ddf9a6"},{"path":"/usr/lib64/python3.6/__pycache__/datetime.cpython-36.pyc","mode":33188,"size":54513,"sha256":"a08b3599ac59ec6619a1e099daf988c90ddd9a9773a8e369ce876f893d5cbc4b"},{"path":"/usr/lib64/python3.6/__pycache__/decimal.cpython-36.opt-1.pyc","mode":33188,"size":353,"sha256":"9c7675119e0269c0bd5f788522d0781525282b3e1cccd4a81034c111582b7c3d"},{"path":"/usr/lib64/python3.6/__pycache__/decimal.cpython-36.opt-2.pyc","mode":33188,"size":353,"sha256":"9c7675119e0269c0bd5f788522d0781525282b3e1cccd4a81034c111582b7c3d"},{"path":"/usr/lib64/python3.6/__pycache__/decimal.cpython-36.pyc","mode":33188,"size":353,"sha256":"9c7675119e0269c0bd5f788522d0781525282b3e1cccd4a81034c111582b7c3d"},{"path":"/usr/lib64/python3.6/__pycache__/difflib.cpython-36.opt-1.pyc","mode":33188,"size":59606,"sha256":"83a39d4ea96f0aba12f9a779c0e6b4da6167b394ebff52b89ff3df13dd335a4c"},{"path":"/usr/lib64/python3.6/__pycache__/difflib.cpython-36.opt-2.pyc","mode":33188,"size":25036,"sha256":"986f6da84f10fc46d71e7eebc0178b279fc791cd97e8595b85d34d072039404d"},{"path":"/usr/lib64/python3.6/__pycache__/difflib.cpython-36.pyc","mode":33188,"size":59644,"sha256":"5e06c7da773867ea043d34ef5d29a5dcd01e497d7ce5595943d16f08761e510c"},{"path":"/usr/lib64/python3.6/__pycache__/dis.cpython-36.opt-1.pyc","mode":33188,"size":14183,"sha256":"d579b6afd87a5970b71866af7dd716099435738b61ae8403aac6f03b4ab1cb6d"},{"path":"/usr/lib64/python3.6/__pycache__/dis.cpython-36.opt-2.pyc","mode":33188,"size":10651,"sha256":"0662c089f66209da055a8038861db5ea0380fb354d4fc51e22be18e19e980423"},{"path":"/usr/lib64/python3.6/__pycache__/dis.cpython-36.pyc","mode":33188,"size":14183,"sha256":"d579b6afd87a5970b71866af7dd716099435738b61ae8403aac6f03b4ab1cb6d"},{"path":"/usr/lib64/python3.6/__pycache__/doctest.cpython-36.opt-1.pyc","mode":33188,"size":75346,"sha256":"f60ca9e3ededa8a7e1d7fd11210f1c3d41c988e7b02f29ab470e32bae3d185d8"},{"path":"/usr/lib64/python3.6/__pycache__/doctest.cpython-36.opt-2.pyc","mode":33188,"size":40019,"sha256":"00acd04b436548390cd104f63381b437f1e0af25b3929a62accb940bb8bf0eb6"},{"path":"/usr/lib64/python3.6/__pycache__/doctest.cpython-36.pyc","mode":33188,"size":75591,"sha256":"79e8160c13552d71d009f7f8d8b3a05f91a4cc7217bf6c5dd1b2efb98198a2fd"},{"path":"/usr/lib64/python3.6/__pycache__/dummy_threading.cpython-36.opt-1.pyc","mode":33188,"size":1104,"sha256":"4ce64c49d2a7241220e5ddc2823a68d43b3612175d8bfeef26ee61785c7adcb5"},{"path":"/usr/lib64/python3.6/__pycache__/dummy_threading.cpython-36.opt-2.pyc","mode":33188,"size":731,"sha256":"5cff0dbe8d88c9accd10e3c631a2e1f58d167052ec8c6563ff39249f6b4b1eaf"},{"path":"/usr/lib64/python3.6/__pycache__/dummy_threading.cpython-36.pyc","mode":33188,"size":1104,"sha256":"4ce64c49d2a7241220e5ddc2823a68d43b3612175d8bfeef26ee61785c7adcb5"},{"path":"/usr/lib64/python3.6/__pycache__/enum.cpython-36.opt-1.pyc","mode":33188,"size":23455,"sha256":"d0f7311dfa2ff84e07f5d45eb50e109fc13b685abaae91e24d14337359b86dc5"},{"path":"/usr/lib64/python3.6/__pycache__/enum.cpython-36.opt-2.pyc","mode":33188,"size":19162,"sha256":"6040a546e9545daf7ffbad1df70af2fd3b30c9a2a8bf9075a370b0c4a34d26c3"},{"path":"/usr/lib64/python3.6/__pycache__/enum.cpython-36.pyc","mode":33188,"size":23455,"sha256":"d0f7311dfa2ff84e07f5d45eb50e109fc13b685abaae91e24d14337359b86dc5"},{"path":"/usr/lib64/python3.6/__pycache__/filecmp.cpython-36.opt-1.pyc","mode":33188,"size":8307,"sha256":"f4ac7079a1fc0abdbbe360317f2b7e3b4dbdc7e910d455b53cf31f6ad65133a4"},{"path":"/usr/lib64/python3.6/__pycache__/filecmp.cpython-36.opt-2.pyc","mode":33188,"size":5890,"sha256":"4df9c63285f41c3efa06009789fccb0c6e69205206fe1906ab10568ecec067a0"},{"path":"/usr/lib64/python3.6/__pycache__/filecmp.cpython-36.pyc","mode":33188,"size":8307,"sha256":"f4ac7079a1fc0abdbbe360317f2b7e3b4dbdc7e910d455b53cf31f6ad65133a4"},{"path":"/usr/lib64/python3.6/__pycache__/fileinput.cpython-36.opt-1.pyc","mode":33188,"size":13154,"sha256":"425e804cfd46d6ef6dc530ce04dd16229c1e7051815e8304085d7a4083ea57ce"},{"path":"/usr/lib64/python3.6/__pycache__/fileinput.cpython-36.opt-2.pyc","mode":33188,"size":7615,"sha256":"36d7b36fac9296ef9f116a830c96ddf53a216859ab42bf4e8c98cc238d687204"},{"path":"/usr/lib64/python3.6/__pycache__/fileinput.cpython-36.pyc","mode":33188,"size":13154,"sha256":"425e804cfd46d6ef6dc530ce04dd16229c1e7051815e8304085d7a4083ea57ce"},{"path":"/usr/lib64/python3.6/__pycache__/fnmatch.cpython-36.opt-1.pyc","mode":33188,"size":2876,"sha256":"6341e47d082aa45099527b7c33737f610a08951cba4d2f63c681d553ab7ee4c9"},{"path":"/usr/lib64/python3.6/__pycache__/fnmatch.cpython-36.opt-2.pyc","mode":33188,"size":1687,"sha256":"d27e48f583e2541d3ac931b0c017b32ab462ebad5039b52a39e411f81db44446"},{"path":"/usr/lib64/python3.6/__pycache__/fnmatch.cpython-36.pyc","mode":33188,"size":2876,"sha256":"6341e47d082aa45099527b7c33737f610a08951cba4d2f63c681d553ab7ee4c9"},{"path":"/usr/lib64/python3.6/__pycache__/formatter.cpython-36.opt-1.pyc","mode":33188,"size":17581,"sha256":"b99ca6b3aa418057003b93b0f68bbc0bea04063888b1df50631fd4f4eb1dfb82"},{"path":"/usr/lib64/python3.6/__pycache__/formatter.cpython-36.opt-2.pyc","mode":33188,"size":15141,"sha256":"85ad029c17e93ce8695e1ba9304ba381b9f08e0426015945dec21be78cd1c698"},{"path":"/usr/lib64/python3.6/__pycache__/formatter.cpython-36.pyc","mode":33188,"size":17581,"sha256":"b99ca6b3aa418057003b93b0f68bbc0bea04063888b1df50631fd4f4eb1dfb82"},{"path":"/usr/lib64/python3.6/__pycache__/fractions.cpython-36.opt-1.pyc","mode":33188,"size":18428,"sha256":"f9da2bb5bcde144ee1303e96245118d206220f22955c61ac4797a4c0067d953e"},{"path":"/usr/lib64/python3.6/__pycache__/fractions.cpython-36.opt-2.pyc","mode":33188,"size":11142,"sha256":"41192a1016a3b84f0d49ff2380225ca05284c14dee6a91289207230c453f75e6"},{"path":"/usr/lib64/python3.6/__pycache__/fractions.cpython-36.pyc","mode":33188,"size":18428,"sha256":"f9da2bb5bcde144ee1303e96245118d206220f22955c61ac4797a4c0067d953e"},{"path":"/usr/lib64/python3.6/__pycache__/ftplib.cpython-36.opt-1.pyc","mode":33188,"size":28201,"sha256":"40cdd8c1a99c2f584366a7e72ec3c74cb65685f83ef5ed90b386efbac20d9fbd"},{"path":"/usr/lib64/python3.6/__pycache__/ftplib.cpython-36.opt-2.pyc","mode":33188,"size":18458,"sha256":"0ef64c722b0a04de3c01438cebc05c30ecd0604918aad7643000637926d8369d"},{"path":"/usr/lib64/python3.6/__pycache__/ftplib.cpython-36.pyc","mode":33188,"size":28201,"sha256":"40cdd8c1a99c2f584366a7e72ec3c74cb65685f83ef5ed90b386efbac20d9fbd"},{"path":"/usr/lib64/python3.6/__pycache__/functools.cpython-36.opt-1.pyc","mode":33188,"size":24064,"sha256":"b173ffc243a0babe878d0f9f99ca1e195b594a85ebf55f2272693183c4c957b5"},{"path":"/usr/lib64/python3.6/__pycache__/functools.cpython-36.opt-2.pyc","mode":33188,"size":18093,"sha256":"2f4b366d359a5d73552a7f50d02ad21306ae3e8e77cd7c9c3a63584d4ce632fb"},{"path":"/usr/lib64/python3.6/__pycache__/functools.cpython-36.pyc","mode":33188,"size":24064,"sha256":"b173ffc243a0babe878d0f9f99ca1e195b594a85ebf55f2272693183c4c957b5"},{"path":"/usr/lib64/python3.6/__pycache__/genericpath.cpython-36.opt-1.pyc","mode":33188,"size":3728,"sha256":"36499729208a309e3fdf48a4fd95d45cbac4e292f05a937821646de137c89154"},{"path":"/usr/lib64/python3.6/__pycache__/genericpath.cpython-36.opt-2.pyc","mode":33188,"size":2735,"sha256":"028f22eb8b8709c3dad4dae5729d4e91c744444e8bb240a54169638ee5a96f8b"},{"path":"/usr/lib64/python3.6/__pycache__/genericpath.cpython-36.pyc","mode":33188,"size":3728,"sha256":"36499729208a309e3fdf48a4fd95d45cbac4e292f05a937821646de137c89154"},{"path":"/usr/lib64/python3.6/__pycache__/getopt.cpython-36.opt-1.pyc","mode":33188,"size":6185,"sha256":"6e31dfdc9beae3ed9e04c7774221786b86678e9de4e0c530ccad90fc9dbb441f"},{"path":"/usr/lib64/python3.6/__pycache__/getopt.cpython-36.opt-2.pyc","mode":33188,"size":3631,"sha256":"bd0615110b08a8ad02ea4e3e6ed1a7b197a24512192f576e7caf2a81804f6824"},{"path":"/usr/lib64/python3.6/__pycache__/getopt.cpython-36.pyc","mode":33188,"size":6219,"sha256":"e860b060ff0466752ec4b70fc9cda00a35cded95f367417ee760cbf37e708a16"},{"path":"/usr/lib64/python3.6/__pycache__/getpass.cpython-36.opt-1.pyc","mode":33188,"size":4179,"sha256":"899252c998baa0fcc84246713e2e66bddb690b977b2841de520d61082417c3ee"},{"path":"/usr/lib64/python3.6/__pycache__/getpass.cpython-36.opt-2.pyc","mode":33188,"size":2994,"sha256":"638c61c10f76e424a614f1dff3b1807ab730c3567035098d864902659d8b0f84"},{"path":"/usr/lib64/python3.6/__pycache__/getpass.cpython-36.pyc","mode":33188,"size":4179,"sha256":"899252c998baa0fcc84246713e2e66bddb690b977b2841de520d61082417c3ee"},{"path":"/usr/lib64/python3.6/__pycache__/gettext.cpython-36.opt-1.pyc","mode":33188,"size":14199,"sha256":"a63d6b16a80879437f66c4464751c94cf3c5afd861da59ed809f58fb992173d6"},{"path":"/usr/lib64/python3.6/__pycache__/gettext.cpython-36.opt-2.pyc","mode":33188,"size":13508,"sha256":"b1e33771dce15ad578a1386424800469a5758ac510bcaa9c7759368be03b217d"},{"path":"/usr/lib64/python3.6/__pycache__/gettext.cpython-36.pyc","mode":33188,"size":14199,"sha256":"a63d6b16a80879437f66c4464751c94cf3c5afd861da59ed809f58fb992173d6"},{"path":"/usr/lib64/python3.6/__pycache__/glob.cpython-36.opt-1.pyc","mode":33188,"size":4192,"sha256":"ac2b320bf9d5410439792e67c36801121e0d218d0d4f82003900440fc68b9a8b"},{"path":"/usr/lib64/python3.6/__pycache__/glob.cpython-36.opt-2.pyc","mode":33188,"size":3332,"sha256":"33a166507d7731f7c92df99a148571e47c3ef015d6bc214cbfb498f8706b2bcc"},{"path":"/usr/lib64/python3.6/__pycache__/glob.cpython-36.pyc","mode":33188,"size":4261,"sha256":"8c8a0929c184d806982234cf532f38339c9b5a4387c23c129531e7c02d3fd643"},{"path":"/usr/lib64/python3.6/__pycache__/gzip.cpython-36.opt-1.pyc","mode":33188,"size":16228,"sha256":"5b236a6e587a7d82bed63ada261c0f2ddddf15dacf52f6890f594c524c3d2dce"},{"path":"/usr/lib64/python3.6/__pycache__/gzip.cpython-36.opt-2.pyc","mode":33188,"size":12422,"sha256":"b392150b5bbab6fb8062096d540488364d93e01bb038ce0f5bfa39e6b30a0392"},{"path":"/usr/lib64/python3.6/__pycache__/gzip.cpython-36.pyc","mode":33188,"size":16228,"sha256":"5b236a6e587a7d82bed63ada261c0f2ddddf15dacf52f6890f594c524c3d2dce"},{"path":"/usr/lib64/python3.6/__pycache__/hashlib.cpython-36.opt-1.pyc","mode":33188,"size":5667,"sha256":"f0a722a496d0455a60995e32725b7285131d0be95433105a20d85fcbc9276fb9"},{"path":"/usr/lib64/python3.6/__pycache__/hashlib.cpython-36.opt-2.pyc","mode":33188,"size":5328,"sha256":"ea5f584d906c91f5d5eb90af82cd7f81a8c1c136115b62a2dcf56645c0d75aa9"},{"path":"/usr/lib64/python3.6/__pycache__/hashlib.cpython-36.pyc","mode":33188,"size":5667,"sha256":"f0a722a496d0455a60995e32725b7285131d0be95433105a20d85fcbc9276fb9"},{"path":"/usr/lib64/python3.6/__pycache__/heapq.cpython-36.opt-1.pyc","mode":33188,"size":14294,"sha256":"7b8fd9f1b7043c4a0fd5aee3013d01fa901e27a72e92d6d9b29e03532fd6d962"},{"path":"/usr/lib64/python3.6/__pycache__/heapq.cpython-36.opt-2.pyc","mode":33188,"size":11304,"sha256":"d1a2437196b9c5de96bbb714fd63215f8c875722ce99ebb819037b9c303c7505"},{"path":"/usr/lib64/python3.6/__pycache__/heapq.cpython-36.pyc","mode":33188,"size":14294,"sha256":"7b8fd9f1b7043c4a0fd5aee3013d01fa901e27a72e92d6d9b29e03532fd6d962"},{"path":"/usr/lib64/python3.6/__pycache__/hmac.cpython-36.opt-1.pyc","mode":33188,"size":6015,"sha256":"1f4d231199594db902e4a26e054ab76c014cab4ba957a3d96b0b9d9a7b74f97f"},{"path":"/usr/lib64/python3.6/__pycache__/hmac.cpython-36.opt-2.pyc","mode":33188,"size":4204,"sha256":"403d32fe276f6ed7b36397a6550b5d4bde384b17f3eb4dc6fbba17f97ae743d7"},{"path":"/usr/lib64/python3.6/__pycache__/hmac.cpython-36.pyc","mode":33188,"size":6015,"sha256":"1f4d231199594db902e4a26e054ab76c014cab4ba957a3d96b0b9d9a7b74f97f"},{"path":"/usr/lib64/python3.6/__pycache__/imaplib.cpython-36.opt-1.pyc","mode":33188,"size":39921,"sha256":"04bf313e7a1e01a20afda76209709046346ac197d865d863fac5c09e2af6a3e3"},{"path":"/usr/lib64/python3.6/__pycache__/imaplib.cpython-36.opt-2.pyc","mode":33188,"size":27833,"sha256":"23ae7ab6495d0d69811bf7af83548723fa180f818196c17dc4413355e82dd888"},{"path":"/usr/lib64/python3.6/__pycache__/imaplib.cpython-36.pyc","mode":33188,"size":42140,"sha256":"20668fdb8cb547e95dfb6a5422f3b64aee91296cc95514c5e6edfa319f5224cc"},{"path":"/usr/lib64/python3.6/__pycache__/imghdr.cpython-36.opt-1.pyc","mode":33188,"size":4152,"sha256":"0cb7a2dd07898e9e4b245f4331ed8e56f2b7e7eb9a11bec5a6287c576a700e45"},{"path":"/usr/lib64/python3.6/__pycache__/imghdr.cpython-36.opt-2.pyc","mode":33188,"size":3837,"sha256":"bbf460f5315c24270694927ccaf71c409ff9dd6f0474e1e87f49581a0295f0ce"},{"path":"/usr/lib64/python3.6/__pycache__/imghdr.cpython-36.pyc","mode":33188,"size":4152,"sha256":"0cb7a2dd07898e9e4b245f4331ed8e56f2b7e7eb9a11bec5a6287c576a700e45"},{"path":"/usr/lib64/python3.6/__pycache__/imp.cpython-36.opt-1.pyc","mode":33188,"size":9698,"sha256":"7f170f3954df41a30dc6c8f6e0fe539a55524f5ec3343df2380be6f847ae021b"},{"path":"/usr/lib64/python3.6/__pycache__/imp.cpython-36.opt-2.pyc","mode":33188,"size":7295,"sha256":"a1fad533c261919bbeff86533d0f0eaba7a76b9a17f9669fa4704f4457906024"},{"path":"/usr/lib64/python3.6/__pycache__/imp.cpython-36.pyc","mode":33188,"size":9698,"sha256":"7f170f3954df41a30dc6c8f6e0fe539a55524f5ec3343df2380be6f847ae021b"},{"path":"/usr/lib64/python3.6/__pycache__/inspect.cpython-36.opt-1.pyc","mode":33188,"size":79441,"sha256":"2310ae21574075e4b9e48f84125da0fd5ea506412b2b3937b090011df1101421"},{"path":"/usr/lib64/python3.6/__pycache__/inspect.cpython-36.opt-2.pyc","mode":33188,"size":54026,"sha256":"c989649c4021bdb4f09b3787f6526c432241cdd18dbbd960ba3d49cfbfe46f2c"},{"path":"/usr/lib64/python3.6/__pycache__/inspect.cpython-36.pyc","mode":33188,"size":79741,"sha256":"e8fa5196412e2d3492713a2683314904adcddcddefbd682c6bd5cf2957071e22"},{"path":"/usr/lib64/python3.6/__pycache__/io.cpython-36.opt-1.pyc","mode":33188,"size":3389,"sha256":"8c6367390c8d1775501511677333fbae9ecd77b34f9507e0dc6c38885ccadc03"},{"path":"/usr/lib64/python3.6/__pycache__/io.cpython-36.opt-2.pyc","mode":33188,"size":1898,"sha256":"39b3416f19f359f5ae8a0338ee86f0fd4b8556308071b1d193827b3979c2fb7c"},{"path":"/usr/lib64/python3.6/__pycache__/io.cpython-36.pyc","mode":33188,"size":3389,"sha256":"8c6367390c8d1775501511677333fbae9ecd77b34f9507e0dc6c38885ccadc03"},{"path":"/usr/lib64/python3.6/__pycache__/ipaddress.cpython-36.opt-1.pyc","mode":33188,"size":62374,"sha256":"5584147ff458d96bdb978967093ce38e8f853633bb44ab67881fdf193c161ef2"},{"path":"/usr/lib64/python3.6/__pycache__/ipaddress.cpython-36.opt-2.pyc","mode":33188,"size":36788,"sha256":"4df26d2c1f3e5aecb7bc6ba669ac250eed753c991967a76bfc9d1d1fb35e63d8"},{"path":"/usr/lib64/python3.6/__pycache__/ipaddress.cpython-36.pyc","mode":33188,"size":62374,"sha256":"5584147ff458d96bdb978967093ce38e8f853633bb44ab67881fdf193c161ef2"},{"path":"/usr/lib64/python3.6/__pycache__/keyword.cpython-36.opt-1.pyc","mode":33188,"size":1767,"sha256":"f5d1647e9c1595adfb88a06c89f64dd11cadb37f9ce3e322eb99ececc1b080ae"},{"path":"/usr/lib64/python3.6/__pycache__/keyword.cpython-36.opt-2.pyc","mode":33188,"size":1499,"sha256":"20ad0f2ff2e1bdec5c70cbe0dfd2de4f1b568da0762a65454e9077451d865f5d"},{"path":"/usr/lib64/python3.6/__pycache__/keyword.cpython-36.pyc","mode":33188,"size":1767,"sha256":"f5d1647e9c1595adfb88a06c89f64dd11cadb37f9ce3e322eb99ececc1b080ae"},{"path":"/usr/lib64/python3.6/__pycache__/linecache.cpython-36.opt-1.pyc","mode":33188,"size":3780,"sha256":"40e6a98551b60b82014217743cfdf141789ff4fa3b8831d4cdace92d83e56871"},{"path":"/usr/lib64/python3.6/__pycache__/linecache.cpython-36.opt-2.pyc","mode":33188,"size":2675,"sha256":"9b2b84f5d830eaab692eace2e45716158e90793f74964e1514394fc5f06c23c4"},{"path":"/usr/lib64/python3.6/__pycache__/linecache.cpython-36.pyc","mode":33188,"size":3780,"sha256":"40e6a98551b60b82014217743cfdf141789ff4fa3b8831d4cdace92d83e56871"},{"path":"/usr/lib64/python3.6/__pycache__/locale.cpython-36.opt-1.pyc","mode":33188,"size":34047,"sha256":"9a7b3a81e643797ac4a61baff60ad00ae3f48bf59abea6026ea4db722cd54e50"},{"path":"/usr/lib64/python3.6/__pycache__/locale.cpython-36.opt-2.pyc","mode":33188,"size":29422,"sha256":"b0f330a2c9190cb38b8b54e3592c410982a4d9d6e46c7faeec24fbc4019f27bb"},{"path":"/usr/lib64/python3.6/__pycache__/locale.cpython-36.pyc","mode":33188,"size":34047,"sha256":"9a7b3a81e643797ac4a61baff60ad00ae3f48bf59abea6026ea4db722cd54e50"},{"path":"/usr/lib64/python3.6/__pycache__/lzma.cpython-36.opt-1.pyc","mode":33188,"size":11994,"sha256":"aadad0289c404a0f2949c384dc1502a6c0da68fd7b69a71c4f1a6c30b60b8768"},{"path":"/usr/lib64/python3.6/__pycache__/lzma.cpython-36.opt-2.pyc","mode":33188,"size":5803,"sha256":"4665e6bc13344a1be1b1c8fbac1b017dc6ab9fee6a51bd44fc6fc60a88de36a4"},{"path":"/usr/lib64/python3.6/__pycache__/lzma.cpython-36.pyc","mode":33188,"size":11994,"sha256":"aadad0289c404a0f2949c384dc1502a6c0da68fd7b69a71c4f1a6c30b60b8768"},{"path":"/usr/lib64/python3.6/__pycache__/macpath.cpython-36.opt-1.pyc","mode":33188,"size":5643,"sha256":"f6c59dfca4b40f853bc6258d8083b84c65167979af40d69c9a19ccffa3c31ff4"},{"path":"/usr/lib64/python3.6/__pycache__/macpath.cpython-36.opt-2.pyc","mode":33188,"size":4377,"sha256":"e278ea596b498dacdd356a281e6f589f30ce7cd9ca381ef332745effeb5c1300"},{"path":"/usr/lib64/python3.6/__pycache__/macpath.cpython-36.pyc","mode":33188,"size":5643,"sha256":"f6c59dfca4b40f853bc6258d8083b84c65167979af40d69c9a19ccffa3c31ff4"},{"path":"/usr/lib64/python3.6/__pycache__/macurl2path.cpython-36.opt-1.pyc","mode":33188,"size":1869,"sha256":"984aabaf827de7f19e8c306ffc9b104a0724fff4be6dff76c0c91569bd565e71"},{"path":"/usr/lib64/python3.6/__pycache__/macurl2path.cpython-36.opt-2.pyc","mode":33188,"size":1489,"sha256":"55d22dbb9ee7f9a72b4e6deb992a9ec09c8158eab85244af9ff7e9cb4df93914"},{"path":"/usr/lib64/python3.6/__pycache__/macurl2path.cpython-36.pyc","mode":33188,"size":1869,"sha256":"984aabaf827de7f19e8c306ffc9b104a0724fff4be6dff76c0c91569bd565e71"},{"path":"/usr/lib64/python3.6/__pycache__/mailbox.cpython-36.opt-1.pyc","mode":33188,"size":63672,"sha256":"28a0e22a430e617a3a327db2955d6d35ad890e78374bf1a0f8ce494ecbf3eda2"},{"path":"/usr/lib64/python3.6/__pycache__/mailbox.cpython-36.opt-2.pyc","mode":33188,"size":54525,"sha256":"2e78448aa11d31c79df882338fff5f7371af6a5d93e4066fbc9aea57703a2b1d"},{"path":"/usr/lib64/python3.6/__pycache__/mailbox.cpython-36.pyc","mode":33188,"size":63754,"sha256":"62eb614e707da6036ee0b9dc7f212f2560ac131d6145c55f4d04e58cfd300973"},{"path":"/usr/lib64/python3.6/__pycache__/mailcap.cpython-36.opt-1.pyc","mode":33188,"size":6480,"sha256":"47d4308a1ffe4889baf99892978fb08d8159295383403d58ebb11096807eb7b4"},{"path":"/usr/lib64/python3.6/__pycache__/mailcap.cpython-36.opt-2.pyc","mode":33188,"size":4962,"sha256":"e514505d0e737b24af7759c479132778e987d13c6f0ee5108d70ae792057b051"},{"path":"/usr/lib64/python3.6/__pycache__/mailcap.cpython-36.pyc","mode":33188,"size":6480,"sha256":"47d4308a1ffe4889baf99892978fb08d8159295383403d58ebb11096807eb7b4"},{"path":"/usr/lib64/python3.6/__pycache__/mimetypes.cpython-36.opt-1.pyc","mode":33188,"size":15555,"sha256":"461dd3617d616ce4cd6b9d4ce4f0298e41b422e425e9f8f8ca85342d508feb00"},{"path":"/usr/lib64/python3.6/__pycache__/mimetypes.cpython-36.opt-2.pyc","mode":33188,"size":9557,"sha256":"fa8e6981a6701529ab52d3acfd87b6c7316a2632b480e6c1e2cb745d201d18de"},{"path":"/usr/lib64/python3.6/__pycache__/mimetypes.cpython-36.pyc","mode":33188,"size":15555,"sha256":"461dd3617d616ce4cd6b9d4ce4f0298e41b422e425e9f8f8ca85342d508feb00"},{"path":"/usr/lib64/python3.6/__pycache__/modulefinder.cpython-36.opt-1.pyc","mode":33188,"size":15306,"sha256":"4706fed065d5596f1da9c61b93d9590af5b33ac14723733ab9722c0e11bba9da"},{"path":"/usr/lib64/python3.6/__pycache__/modulefinder.cpython-36.opt-2.pyc","mode":33188,"size":14465,"sha256":"d0f4e3154211693cfe4857db1003e18ec6d736f8e27b08be8f63dbf7c5b43386"},{"path":"/usr/lib64/python3.6/__pycache__/modulefinder.cpython-36.pyc","mode":33188,"size":15368,"sha256":"132fd1d0542d01cefee733ac7303f0ac0abebe63820a869c9b16a0c65c8479a2"},{"path":"/usr/lib64/python3.6/__pycache__/netrc.cpython-36.opt-1.pyc","mode":33188,"size":3838,"sha256":"af12eeb3c05c094602470145c05a92c716943176a048c27adbd9b76e7a129d05"},{"path":"/usr/lib64/python3.6/__pycache__/netrc.cpython-36.opt-2.pyc","mode":33188,"size":3600,"sha256":"232a7c7f73346e59e4a39a8a808cbae71a78b300a1620d9249a826154d54c95d"},{"path":"/usr/lib64/python3.6/__pycache__/netrc.cpython-36.pyc","mode":33188,"size":3838,"sha256":"af12eeb3c05c094602470145c05a92c716943176a048c27adbd9b76e7a129d05"},{"path":"/usr/lib64/python3.6/__pycache__/nntplib.cpython-36.opt-1.pyc","mode":33188,"size":33782,"sha256":"5568cd0633800c17ba6880ed8961847368d60764a1a025ff69e26cc5d3fb5a6f"},{"path":"/usr/lib64/python3.6/__pycache__/nntplib.cpython-36.opt-2.pyc","mode":33188,"size":21241,"sha256":"9f0e9d9e9210493b842e73bdb9889ffa1bae7c10acb05767747e1ffd38248d9d"},{"path":"/usr/lib64/python3.6/__pycache__/nntplib.cpython-36.pyc","mode":33188,"size":33782,"sha256":"5568cd0633800c17ba6880ed8961847368d60764a1a025ff69e26cc5d3fb5a6f"},{"path":"/usr/lib64/python3.6/__pycache__/ntpath.cpython-36.opt-1.pyc","mode":33188,"size":13752,"sha256":"0fac3a1f33b79b1edf8c2ebd9c3c520f31c78b11296bfb8b629e99ffe6e8f0bb"},{"path":"/usr/lib64/python3.6/__pycache__/ntpath.cpython-36.opt-2.pyc","mode":33188,"size":11281,"sha256":"057a6d71c6f05e2398a38ddc6fb36839eeab9787685eb94d017cec05cdded0f8"},{"path":"/usr/lib64/python3.6/__pycache__/ntpath.cpython-36.pyc","mode":33188,"size":13752,"sha256":"0fac3a1f33b79b1edf8c2ebd9c3c520f31c78b11296bfb8b629e99ffe6e8f0bb"},{"path":"/usr/lib64/python3.6/__pycache__/nturl2path.cpython-36.opt-1.pyc","mode":33188,"size":1501,"sha256":"01b771191825a65c1251c9fb8d1c2bda0bf62be5dec856396ba2569d12095f83"},{"path":"/usr/lib64/python3.6/__pycache__/nturl2path.cpython-36.opt-2.pyc","mode":33188,"size":1183,"sha256":"a5ae4110d081b602246adad2b480010fa2234163109557f2a80b0b46cbd74ca4"},{"path":"/usr/lib64/python3.6/__pycache__/nturl2path.cpython-36.pyc","mode":33188,"size":1501,"sha256":"01b771191825a65c1251c9fb8d1c2bda0bf62be5dec856396ba2569d12095f83"},{"path":"/usr/lib64/python3.6/__pycache__/numbers.cpython-36.opt-1.pyc","mode":33188,"size":12144,"sha256":"f034308429697683db85f115af584d620e8f65236861ff2ae08107ecf0d420d8"},{"path":"/usr/lib64/python3.6/__pycache__/numbers.cpython-36.opt-2.pyc","mode":33188,"size":8183,"sha256":"8260009cf2da7c2867bbd1a5b68ea2e46ddb03bd68b00e77011dbdceccb91f27"},{"path":"/usr/lib64/python3.6/__pycache__/numbers.cpython-36.pyc","mode":33188,"size":12144,"sha256":"f034308429697683db85f115af584d620e8f65236861ff2ae08107ecf0d420d8"},{"path":"/usr/lib64/python3.6/__pycache__/opcode.cpython-36.opt-1.pyc","mode":33188,"size":5415,"sha256":"48ef01e74e03d0c1bd112db99eb16625bd9f6527c229aec21d16cb5bdac294ec"},{"path":"/usr/lib64/python3.6/__pycache__/opcode.cpython-36.opt-2.pyc","mode":33188,"size":5275,"sha256":"c6f8fe4bb7e5b78696b8593ea46bda0d234661ea3ecec5f67f63903b549adfe4"},{"path":"/usr/lib64/python3.6/__pycache__/opcode.cpython-36.pyc","mode":33188,"size":5415,"sha256":"48ef01e74e03d0c1bd112db99eb16625bd9f6527c229aec21d16cb5bdac294ec"},{"path":"/usr/lib64/python3.6/__pycache__/operator.cpython-36.opt-1.pyc","mode":33188,"size":13915,"sha256":"9b17592d5280e4ff20879f37c8ce9dcf6a8ab3f31a605f8ae3b52214a882b167"},{"path":"/usr/lib64/python3.6/__pycache__/operator.cpython-36.opt-2.pyc","mode":33188,"size":11456,"sha256":"9e516f8983cf2c228e7540e9a9ac752410968107af50648841b01ff92f805c5a"},{"path":"/usr/lib64/python3.6/__pycache__/operator.cpython-36.pyc","mode":33188,"size":13915,"sha256":"9b17592d5280e4ff20879f37c8ce9dcf6a8ab3f31a605f8ae3b52214a882b167"},{"path":"/usr/lib64/python3.6/__pycache__/optparse.cpython-36.opt-1.pyc","mode":33188,"size":47988,"sha256":"2b953caf2a6091370b9ddd81490727a7d5d9ade5db4c525fe4aa3ca068ce38bf"},{"path":"/usr/lib64/python3.6/__pycache__/optparse.cpython-36.opt-2.pyc","mode":33188,"size":35633,"sha256":"fe4d024e7e1906299b83b8f24715514b7d76199fdf6d6f09d4c073ec869a1477"},{"path":"/usr/lib64/python3.6/__pycache__/optparse.cpython-36.pyc","mode":33188,"size":48056,"sha256":"244525ebc7968bdea578322b9b638762cc07d0ca5963d9e3a72b267d462e6e5f"},{"path":"/usr/lib64/python3.6/__pycache__/os.cpython-36.opt-1.pyc","mode":33188,"size":29630,"sha256":"781eac0fd264abcb36ff0ad423c63c02a1c3678caaf8866c3a0653e00ea150bd"},{"path":"/usr/lib64/python3.6/__pycache__/os.cpython-36.opt-2.pyc","mode":33188,"size":17781,"sha256":"2a6ee217180b746718df8576a4c2f0de6dea0291436ad6b853b9a8dca2ef6ee9"},{"path":"/usr/lib64/python3.6/__pycache__/os.cpython-36.pyc","mode":33188,"size":29630,"sha256":"781eac0fd264abcb36ff0ad423c63c02a1c3678caaf8866c3a0653e00ea150bd"},{"path":"/usr/lib64/python3.6/__pycache__/pathlib.cpython-36.opt-1.pyc","mode":33188,"size":42009,"sha256":"ac3058c48b8c1305d35bcf0d0477666376df07a208ecb1b975cc6962c6c86ac3"},{"path":"/usr/lib64/python3.6/__pycache__/pathlib.cpython-36.opt-2.pyc","mode":33188,"size":34367,"sha256":"2fa72a7b1d00b12a2496b76af98459266e97310219a6845dbaea43b899ea76f5"},{"path":"/usr/lib64/python3.6/__pycache__/pathlib.cpython-36.pyc","mode":33188,"size":42009,"sha256":"ac3058c48b8c1305d35bcf0d0477666376df07a208ecb1b975cc6962c6c86ac3"},{"path":"/usr/lib64/python3.6/__pycache__/pdb.cpython-36.opt-1.pyc","mode":33188,"size":46039,"sha256":"ed86e489a0b4f67720edd9235a337309bac626f0e5074db1d6fe95f4de3a4594"},{"path":"/usr/lib64/python3.6/__pycache__/pdb.cpython-36.opt-2.pyc","mode":33188,"size":31972,"sha256":"7021307d22a9d54e055347453198e7e9f6799a2e180da5bb0652ea29a489ed56"},{"path":"/usr/lib64/python3.6/__pycache__/pdb.cpython-36.pyc","mode":33188,"size":46096,"sha256":"4c9b2ffbec727a437f98b284b540e7f033dd0e34226917bf61550f5a390d0aec"},{"path":"/usr/lib64/python3.6/__pycache__/pickle.cpython-36.opt-1.pyc","mode":33188,"size":42576,"sha256":"28b88f9f200b9a79c432a274883eca2819880522e1af4731e317f83b17e756cb"},{"path":"/usr/lib64/python3.6/__pycache__/pickle.cpython-36.opt-2.pyc","mode":33188,"size":37788,"sha256":"50952dfbeceffeedd86767f3c0b540bd2636fefe443716e16623a7b415e15cff"},{"path":"/usr/lib64/python3.6/__pycache__/pickle.cpython-36.pyc","mode":33188,"size":42693,"sha256":"f0a934783ba8ef87543e1262d57e91ac8c7684fcdc4ef0b51445127b1b0f3201"},{"path":"/usr/lib64/python3.6/__pycache__/pickletools.cpython-36.opt-1.pyc","mode":33188,"size":65171,"sha256":"cfa1ccc9e22fdcf99ec6e18199f57e6bd43af18792d3bbf7e8b3928d90837f49"},{"path":"/usr/lib64/python3.6/__pycache__/pickletools.cpython-36.opt-2.pyc","mode":33188,"size":56430,"sha256":"326c7939135cdf05016184c6b930d8945d876573c818598a08178f0a99a387a9"},{"path":"/usr/lib64/python3.6/__pycache__/pickletools.cpython-36.pyc","mode":33188,"size":66022,"sha256":"d8eff860eaad6fc7a9112c2eda06a701f8d144321c0eebf72503ffec48f82c20"},{"path":"/usr/lib64/python3.6/__pycache__/pipes.cpython-36.opt-1.pyc","mode":33188,"size":7810,"sha256":"3935257b0ace02e8a4d120fd48d114e04c7b9e6e8a12c535dc6392baa5c6b8c9"},{"path":"/usr/lib64/python3.6/__pycache__/pipes.cpython-36.opt-2.pyc","mode":33188,"size":4937,"sha256":"91bab0d1da4833873d1eb6e0e95305b1a5220e73bb914442b7b83af3a315242f"},{"path":"/usr/lib64/python3.6/__pycache__/pipes.cpython-36.pyc","mode":33188,"size":7810,"sha256":"3935257b0ace02e8a4d120fd48d114e04c7b9e6e8a12c535dc6392baa5c6b8c9"},{"path":"/usr/lib64/python3.6/__pycache__/pkgutil.cpython-36.opt-1.pyc","mode":33188,"size":16263,"sha256":"eff867c6c4d8607bbb59d58be1454a67d82f576177f72e99c5cf95fe2d0fbc2b"},{"path":"/usr/lib64/python3.6/__pycache__/pkgutil.cpython-36.opt-2.pyc","mode":33188,"size":11003,"sha256":"7e323f0264c2a6cda0e66235848d2d98207f10303abe6387cf22c6a4633e1919"},{"path":"/usr/lib64/python3.6/__pycache__/pkgutil.cpython-36.pyc","mode":33188,"size":16263,"sha256":"eff867c6c4d8607bbb59d58be1454a67d82f576177f72e99c5cf95fe2d0fbc2b"},{"path":"/usr/lib64/python3.6/__pycache__/platform.cpython-36.opt-1.pyc","mode":33188,"size":28633,"sha256":"ac95d640aa56ce8c3a8be8bc85efdaf9146053da1e359aeeeee7cac3e8f01f45"},{"path":"/usr/lib64/python3.6/__pycache__/platform.cpython-36.opt-2.pyc","mode":33188,"size":19385,"sha256":"b68afb0ff57fb2433f0110cd6084ebbeb00edbecfb8fad0a37bf57b2684fdd08"},{"path":"/usr/lib64/python3.6/__pycache__/platform.cpython-36.pyc","mode":33188,"size":28633,"sha256":"ac95d640aa56ce8c3a8be8bc85efdaf9146053da1e359aeeeee7cac3e8f01f45"},{"path":"/usr/lib64/python3.6/__pycache__/plistlib.cpython-36.opt-1.pyc","mode":33188,"size":27553,"sha256":"798a03e53e8fb06a272a09ebad3411223301e8bf0eebf2cc7d4167ba854395ec"},{"path":"/usr/lib64/python3.6/__pycache__/plistlib.cpython-36.opt-2.pyc","mode":33188,"size":24299,"sha256":"c5c5870f402351a8078ade3469b94faf1c0a696e363e468f4a9f085fb909099f"},{"path":"/usr/lib64/python3.6/__pycache__/plistlib.cpython-36.pyc","mode":33188,"size":27620,"sha256":"2162d05cd123051a099b5e673c8da1bbd742ad1635c26391179f18e56fbb8459"},{"path":"/usr/lib64/python3.6/__pycache__/poplib.cpython-36.opt-1.pyc","mode":33188,"size":13331,"sha256":"88fef4f97f0b48a2d1f16a38f33c826e24feda8a900292a2faa8c4724d5071dd"},{"path":"/usr/lib64/python3.6/__pycache__/poplib.cpython-36.opt-2.pyc","mode":33188,"size":8400,"sha256":"7bf2c93dab180fbd86206a5a4c2d25c148a3be28fd8b88062126ee43c12ccd0b"},{"path":"/usr/lib64/python3.6/__pycache__/poplib.cpython-36.pyc","mode":33188,"size":13331,"sha256":"88fef4f97f0b48a2d1f16a38f33c826e24feda8a900292a2faa8c4724d5071dd"},{"path":"/usr/lib64/python3.6/__pycache__/posixpath.cpython-36.opt-1.pyc","mode":33188,"size":10425,"sha256":"d33b8b0c05706787b065f7b7333668519c53dc9d45128c004bedb0fdd030f70d"},{"path":"/usr/lib64/python3.6/__pycache__/posixpath.cpython-36.opt-2.pyc","mode":33188,"size":8704,"sha256":"2bff96712ac8a5765dcb132b558dae76c81d819256d1a6a52b3310c949ac3a69"},{"path":"/usr/lib64/python3.6/__pycache__/posixpath.cpython-36.pyc","mode":33188,"size":10425,"sha256":"d33b8b0c05706787b065f7b7333668519c53dc9d45128c004bedb0fdd030f70d"},{"path":"/usr/lib64/python3.6/__pycache__/pprint.cpython-36.opt-1.pyc","mode":33188,"size":15771,"sha256":"65c83fe3be7af654d7816da1d17fb959010a04b9c56c825da5deefc3e2217158"},{"path":"/usr/lib64/python3.6/__pycache__/pprint.cpython-36.opt-2.pyc","mode":33188,"size":13707,"sha256":"3179ebf059a9637a7fd19c3e20758edf35cfb5fc393f7d93802bf9a444b7d292"},{"path":"/usr/lib64/python3.6/__pycache__/pprint.cpython-36.pyc","mode":33188,"size":15826,"sha256":"5965cf32d881ae972eed5e1090822c08e02e73ae4bf4aa21f12b538b95cfdae4"},{"path":"/usr/lib64/python3.6/__pycache__/profile.cpython-36.opt-1.pyc","mode":33188,"size":13697,"sha256":"67efbade0bd987eb0f6e8a0bf812e5454f439d296230198f7781b292184a611f"},{"path":"/usr/lib64/python3.6/__pycache__/profile.cpython-36.opt-2.pyc","mode":33188,"size":10715,"sha256":"40afad1d7c82b74a224437356bae80372b36b565bafc7b198f300dd6f6acf54f"},{"path":"/usr/lib64/python3.6/__pycache__/profile.cpython-36.pyc","mode":33188,"size":13903,"sha256":"9d10c821d88fc90ff7eff46fcc46d025c2c83827304b5022ecf59033c2c463ee"},{"path":"/usr/lib64/python3.6/__pycache__/pstats.cpython-36.opt-1.pyc","mode":33188,"size":21859,"sha256":"7cedf9c1941e45d6895ee81c347074d2e554862d9cedecd31e750dc8a104876c"},{"path":"/usr/lib64/python3.6/__pycache__/pstats.cpython-36.opt-2.pyc","mode":33188,"size":19405,"sha256":"a829a1b6eba96c60e4bf25a99cdda68001aaddc806bfe4aea9fa6545b0e54cfb"},{"path":"/usr/lib64/python3.6/__pycache__/pstats.cpython-36.pyc","mode":33188,"size":21859,"sha256":"7cedf9c1941e45d6895ee81c347074d2e554862d9cedecd31e750dc8a104876c"},{"path":"/usr/lib64/python3.6/__pycache__/pty.cpython-36.opt-1.pyc","mode":33188,"size":3863,"sha256":"b7b062e5e8433cc6115d62c6c41931aa3b71c839f10db5a1e96545b3a26bd990"},{"path":"/usr/lib64/python3.6/__pycache__/pty.cpython-36.opt-2.pyc","mode":33188,"size":3010,"sha256":"416370fa6c8a8269f146789bb4dac7e1965377cb89d1490d9bab003265446fc0"},{"path":"/usr/lib64/python3.6/__pycache__/pty.cpython-36.pyc","mode":33188,"size":3863,"sha256":"b7b062e5e8433cc6115d62c6c41931aa3b71c839f10db5a1e96545b3a26bd990"},{"path":"/usr/lib64/python3.6/__pycache__/py_compile.cpython-36.opt-1.pyc","mode":33188,"size":6546,"sha256":"f8ad121584a338b9a11d34a7702e759c3204bdc572a3c12c9bc531eba37d715e"},{"path":"/usr/lib64/python3.6/__pycache__/py_compile.cpython-36.opt-2.pyc","mode":33188,"size":2942,"sha256":"89aa2c2f5ff23e7ee984099dcb005f9050ebb7d0e14c5f4db19abb808954f975"},{"path":"/usr/lib64/python3.6/__pycache__/py_compile.cpython-36.pyc","mode":33188,"size":6546,"sha256":"f8ad121584a338b9a11d34a7702e759c3204bdc572a3c12c9bc531eba37d715e"},{"path":"/usr/lib64/python3.6/__pycache__/pyclbr.cpython-36.opt-1.pyc","mode":33188,"size":8367,"sha256":"bc1dd65f8538c297063d9cf63a69a36b526a1f444a9f888994db08efb907c8fb"},{"path":"/usr/lib64/python3.6/__pycache__/pyclbr.cpython-36.opt-2.pyc","mode":33188,"size":5571,"sha256":"0d9bab368956678b1cc2cd241422c82090dc99f80f1345ed8c1e118784e3b7f4"},{"path":"/usr/lib64/python3.6/__pycache__/pyclbr.cpython-36.pyc","mode":33188,"size":8367,"sha256":"bc1dd65f8538c297063d9cf63a69a36b526a1f444a9f888994db08efb907c8fb"},{"path":"/usr/lib64/python3.6/__pycache__/pydoc.cpython-36.opt-1.pyc","mode":33188,"size":84180,"sha256":"22b559a2af81194bb631f48d18bc63da3b82f572aabbc75335401bda82eca02b"},{"path":"/usr/lib64/python3.6/__pycache__/pydoc.cpython-36.opt-2.pyc","mode":33188,"size":74932,"sha256":"5b439433b482f48fd0ea6132fab196440516bb8bacc602735ff5bf351707ff42"},{"path":"/usr/lib64/python3.6/__pycache__/pydoc.cpython-36.pyc","mode":33188,"size":84233,"sha256":"92879e32b187165dd3eee7256448c83102c310aed54327febbe5c6562a9a8c1d"},{"path":"/usr/lib64/python3.6/__pycache__/queue.cpython-36.opt-1.pyc","mode":33188,"size":8757,"sha256":"345e9ba02e6f6b3165810adf25a230c30d386c1116728a7255c54fe8084d7505"},{"path":"/usr/lib64/python3.6/__pycache__/queue.cpython-36.opt-2.pyc","mode":33188,"size":4967,"sha256":"dc112c9df916f7a9187cd85d662693f3b873c5d0e1171cd45758e18f96da08e4"},{"path":"/usr/lib64/python3.6/__pycache__/queue.cpython-36.pyc","mode":33188,"size":8757,"sha256":"345e9ba02e6f6b3165810adf25a230c30d386c1116728a7255c54fe8084d7505"},{"path":"/usr/lib64/python3.6/__pycache__/quopri.cpython-36.opt-1.pyc","mode":33188,"size":5600,"sha256":"51b0519435ada0c938efabc32be017ede77fbbe00941a188f446d06fb3826895"},{"path":"/usr/lib64/python3.6/__pycache__/quopri.cpython-36.opt-2.pyc","mode":33188,"size":4564,"sha256":"603af078799bdc5dd984df26c36b1c298a6923c50d036fc5a845f18fae09cad7"},{"path":"/usr/lib64/python3.6/__pycache__/quopri.cpython-36.pyc","mode":33188,"size":5775,"sha256":"ac09e41bfe111ebd1b4bcf0663751c1b7b6269564ef0430e370e9da4bb3f3d1c"},{"path":"/usr/lib64/python3.6/__pycache__/random.cpython-36.opt-1.pyc","mode":33188,"size":19332,"sha256":"49c1f91df764a8100784adb196d33741b06da30f4d085ee42fca7e175319c571"},{"path":"/usr/lib64/python3.6/__pycache__/random.cpython-36.opt-2.pyc","mode":33188,"size":12791,"sha256":"f760ef6661a8fe232ec497f44dbf72455ab4a17661dcfe75f62e0dc5a70df9f0"},{"path":"/usr/lib64/python3.6/__pycache__/random.cpython-36.pyc","mode":33188,"size":19332,"sha256":"49c1f91df764a8100784adb196d33741b06da30f4d085ee42fca7e175319c571"},{"path":"/usr/lib64/python3.6/__pycache__/re.cpython-36.opt-1.pyc","mode":33188,"size":14060,"sha256":"73b03201b1f5784b3b723d31a90887afa60a32147d408daf321ca23d7695050c"},{"path":"/usr/lib64/python3.6/__pycache__/re.cpython-36.opt-2.pyc","mode":33188,"size":5780,"sha256":"2be4679859245703fb1e094948d7c14892dcc84320b36424646340f1a532fad2"},{"path":"/usr/lib64/python3.6/__pycache__/re.cpython-36.pyc","mode":33188,"size":14060,"sha256":"73b03201b1f5784b3b723d31a90887afa60a32147d408daf321ca23d7695050c"},{"path":"/usr/lib64/python3.6/__pycache__/reprlib.cpython-36.opt-1.pyc","mode":33188,"size":5402,"sha256":"f0759c3f23e7b593aaca6cb007107cb9fc1ec0ae5336e483e3b903001d4f7561"},{"path":"/usr/lib64/python3.6/__pycache__/reprlib.cpython-36.opt-2.pyc","mode":33188,"size":5246,"sha256":"b2727cffd2f8456f0c6d2617aca2157d6515929b0fe6af2478d9014652f23482"},{"path":"/usr/lib64/python3.6/__pycache__/reprlib.cpython-36.pyc","mode":33188,"size":5402,"sha256":"f0759c3f23e7b593aaca6cb007107cb9fc1ec0ae5336e483e3b903001d4f7561"},{"path":"/usr/lib64/python3.6/__pycache__/rlcompleter.cpython-36.opt-1.pyc","mode":33188,"size":5782,"sha256":"0c8cb474dd1f7c4495b349d7dcbe204b140c09f7cb2ba2a58f601483e1c7d15e"},{"path":"/usr/lib64/python3.6/__pycache__/rlcompleter.cpython-36.opt-2.pyc","mode":33188,"size":3119,"sha256":"baf732ed0ef9d8c47c8907282a0860cd5f8ccb30c4e5d3e9069be74388853637"},{"path":"/usr/lib64/python3.6/__pycache__/rlcompleter.cpython-36.pyc","mode":33188,"size":5782,"sha256":"0c8cb474dd1f7c4495b349d7dcbe204b140c09f7cb2ba2a58f601483e1c7d15e"},{"path":"/usr/lib64/python3.6/__pycache__/runpy.cpython-36.opt-1.pyc","mode":33188,"size":7984,"sha256":"f6c6bec25ce082e647a90e31e619e233665819cf2a1a482f76df8b9c255a4531"},{"path":"/usr/lib64/python3.6/__pycache__/runpy.cpython-36.opt-2.pyc","mode":33188,"size":6441,"sha256":"a0f949a97efa17fd44e6eec758f5759934591e370531ec97832fac81e330fff4"},{"path":"/usr/lib64/python3.6/__pycache__/runpy.cpython-36.pyc","mode":33188,"size":7984,"sha256":"f6c6bec25ce082e647a90e31e619e233665819cf2a1a482f76df8b9c255a4531"},{"path":"/usr/lib64/python3.6/__pycache__/sched.cpython-36.opt-1.pyc","mode":33188,"size":6566,"sha256":"fa74f75dc3e5eb2cd52ca607cb89936b5a15cad268da1ff1fc60f94016a73fbe"},{"path":"/usr/lib64/python3.6/__pycache__/sched.cpython-36.opt-2.pyc","mode":33188,"size":3526,"sha256":"6e113e7638dcb5724841a88a2b1622c2f2075f05a8c2d93816683a5b0216f2f8"},{"path":"/usr/lib64/python3.6/__pycache__/sched.cpython-36.pyc","mode":33188,"size":6566,"sha256":"fa74f75dc3e5eb2cd52ca607cb89936b5a15cad268da1ff1fc60f94016a73fbe"},{"path":"/usr/lib64/python3.6/__pycache__/secrets.cpython-36.opt-1.pyc","mode":33188,"size":2164,"sha256":"0044870a40669f99783a778b1da9537c744a3c995190dfa9710acda1f84acf35"},{"path":"/usr/lib64/python3.6/__pycache__/secrets.cpython-36.opt-2.pyc","mode":33188,"size":1106,"sha256":"4f6e37f0e326aa42bea500833332185bbf6542a6326e416113dc685d36a037b8"},{"path":"/usr/lib64/python3.6/__pycache__/secrets.cpython-36.pyc","mode":33188,"size":2164,"sha256":"0044870a40669f99783a778b1da9537c744a3c995190dfa9710acda1f84acf35"},{"path":"/usr/lib64/python3.6/__pycache__/selectors.cpython-36.opt-1.pyc","mode":33188,"size":17699,"sha256":"d0b8d8be16125d3e8ead289969681325c6a69991fb1c0203d6a6a3d803f4d12b"},{"path":"/usr/lib64/python3.6/__pycache__/selectors.cpython-36.opt-2.pyc","mode":33188,"size":13723,"sha256":"c7bcfe5ee737182f7e09e222f9f968061e9f6bf77685a354e10bc9efdaa5cae7"},{"path":"/usr/lib64/python3.6/__pycache__/selectors.cpython-36.pyc","mode":33188,"size":17699,"sha256":"d0b8d8be16125d3e8ead289969681325c6a69991fb1c0203d6a6a3d803f4d12b"},{"path":"/usr/lib64/python3.6/__pycache__/shelve.cpython-36.opt-1.pyc","mode":33188,"size":9460,"sha256":"7b15266d9f4de4e8d7d38144f918cfce0c13e91e7336e8ca76a1ded7dc3fb8e1"},{"path":"/usr/lib64/python3.6/__pycache__/shelve.cpython-36.opt-2.pyc","mode":33188,"size":5307,"sha256":"beb0943dd42306fe1d4594f063e44ceddbd929147e24e2c3490d19860769e5f3"},{"path":"/usr/lib64/python3.6/__pycache__/shelve.cpython-36.pyc","mode":33188,"size":9460,"sha256":"7b15266d9f4de4e8d7d38144f918cfce0c13e91e7336e8ca76a1ded7dc3fb8e1"},{"path":"/usr/lib64/python3.6/__pycache__/shlex.cpython-36.opt-1.pyc","mode":33188,"size":6972,"sha256":"56347f58daea36c7578277d705a95a6d67faa44bfa17c277c32e537e8b8dda81"},{"path":"/usr/lib64/python3.6/__pycache__/shlex.cpython-36.opt-2.pyc","mode":33188,"size":6460,"sha256":"59dc81718a927f29f734ac1221937ac2620feb3e1519d535980d17a9e22f3895"},{"path":"/usr/lib64/python3.6/__pycache__/shlex.cpython-36.pyc","mode":33188,"size":6972,"sha256":"56347f58daea36c7578277d705a95a6d67faa44bfa17c277c32e537e8b8dda81"},{"path":"/usr/lib64/python3.6/__pycache__/shutil.cpython-36.opt-1.pyc","mode":33188,"size":30706,"sha256":"9fa18df37bb53a0af0ee45e5178632f3f4802ad1061df255fb6ea481017f86c8"},{"path":"/usr/lib64/python3.6/__pycache__/shutil.cpython-36.opt-2.pyc","mode":33188,"size":19933,"sha256":"a681243fbe6e0dab3ebb79d35f03bdab8552553b259094d75c2ed0143ee22b2d"},{"path":"/usr/lib64/python3.6/__pycache__/shutil.cpython-36.pyc","mode":33188,"size":30706,"sha256":"9fa18df37bb53a0af0ee45e5178632f3f4802ad1061df255fb6ea481017f86c8"},{"path":"/usr/lib64/python3.6/__pycache__/signal.cpython-36.opt-1.pyc","mode":33188,"size":2517,"sha256":"3e2527741f4098d40df6949e514e1f78688769bb24ff5a49ce717983bca3862a"},{"path":"/usr/lib64/python3.6/__pycache__/signal.cpython-36.opt-2.pyc","mode":33188,"size":2289,"sha256":"3d31b20f9b4874b3277a967bf081ffa4c64ed9dfbd735a9c25ea5e7574ead95f"},{"path":"/usr/lib64/python3.6/__pycache__/signal.cpython-36.pyc","mode":33188,"size":2517,"sha256":"3e2527741f4098d40df6949e514e1f78688769bb24ff5a49ce717983bca3862a"},{"path":"/usr/lib64/python3.6/__pycache__/site.cpython-36.opt-1.pyc","mode":33188,"size":16361,"sha256":"40ae6524a4eaefaa0d775c4bd0e990fc133e66e08ae6d675074e3806b866b181"},{"path":"/usr/lib64/python3.6/__pycache__/site.cpython-36.opt-2.pyc","mode":33188,"size":10675,"sha256":"ced284ab485b0ae3f9a6275f2ea19b88ac8b6659dcf1e1170fdd7529574c5683"},{"path":"/usr/lib64/python3.6/__pycache__/site.cpython-36.pyc","mode":33188,"size":16361,"sha256":"40ae6524a4eaefaa0d775c4bd0e990fc133e66e08ae6d675074e3806b866b181"},{"path":"/usr/lib64/python3.6/__pycache__/smtpd.cpython-36.opt-1.pyc","mode":33188,"size":26685,"sha256":"8a654bb3e751e11e634d81d4bb302edf57556c260031ad7bc6d4e76ed509ba73"},{"path":"/usr/lib64/python3.6/__pycache__/smtpd.cpython-36.opt-2.pyc","mode":33188,"size":24066,"sha256":"e1d26386159714374cf1887ae52e4b91a89c31e9372f32191c9c0ef4db2e90a2"},{"path":"/usr/lib64/python3.6/__pycache__/smtpd.cpython-36.pyc","mode":33188,"size":26685,"sha256":"8a654bb3e751e11e634d81d4bb302edf57556c260031ad7bc6d4e76ed509ba73"},{"path":"/usr/lib64/python3.6/__pycache__/smtplib.cpython-36.opt-1.pyc","mode":33188,"size":35281,"sha256":"a9a9611a8e68df546c25830b9b7627b12d92ff86fc8c9143e33da2d4aafb32f2"},{"path":"/usr/lib64/python3.6/__pycache__/smtplib.cpython-36.opt-2.pyc","mode":33188,"size":18869,"sha256":"984f84fc7c4bf6fed0cf0269a66e6dad727a3fc811443192dc91257c6e43ba16"},{"path":"/usr/lib64/python3.6/__pycache__/smtplib.cpython-36.pyc","mode":33188,"size":35342,"sha256":"ab625f9d2aa2e92b7259b041c33a566b693734c348af2455f712531cd4cb9f42"},{"path":"/usr/lib64/python3.6/__pycache__/sndhdr.cpython-36.opt-1.pyc","mode":33188,"size":6915,"sha256":"4481b87f3308084adf9a4a719dc5499df3337d24fed1ea9326d72de4763da52d"},{"path":"/usr/lib64/python3.6/__pycache__/sndhdr.cpython-36.opt-2.pyc","mode":33188,"size":5640,"sha256":"d652c051ffba1cdb78f47fbef8aa87691f645fd47cbbda11a290668f4cd210e6"},{"path":"/usr/lib64/python3.6/__pycache__/sndhdr.cpython-36.pyc","mode":33188,"size":6915,"sha256":"4481b87f3308084adf9a4a719dc5499df3337d24fed1ea9326d72de4763da52d"},{"path":"/usr/lib64/python3.6/__pycache__/socket.cpython-36.opt-1.pyc","mode":33188,"size":21975,"sha256":"204460c5f9377c05447bfc446810c798fc63eda959fe29fc9be1976cb5f5635b"},{"path":"/usr/lib64/python3.6/__pycache__/socket.cpython-36.opt-2.pyc","mode":33188,"size":14541,"sha256":"a47d353e3751debcac097b0cde678fb6f8abefc3f284023e2ebacb74a58d7a13"},{"path":"/usr/lib64/python3.6/__pycache__/socket.cpython-36.pyc","mode":33188,"size":22015,"sha256":"65449ab0239d925d94d4bb81db4fe3a0257f31da9b7b9be1f8c70d49c6f9d3ce"},{"path":"/usr/lib64/python3.6/__pycache__/socketserver.cpython-36.opt-1.pyc","mode":33188,"size":24252,"sha256":"55ba754e47d9d05131b48a84dbbfe584f1fd190c861e6ec945290e60a0deafea"},{"path":"/usr/lib64/python3.6/__pycache__/socketserver.cpython-36.opt-2.pyc","mode":33188,"size":13327,"sha256":"595ed0798842eb8c8a3ecc8c04117d614921072b45803b9d6292ba4251ffd277"},{"path":"/usr/lib64/python3.6/__pycache__/socketserver.cpython-36.pyc","mode":33188,"size":24252,"sha256":"55ba754e47d9d05131b48a84dbbfe584f1fd190c861e6ec945290e60a0deafea"},{"path":"/usr/lib64/python3.6/__pycache__/sre_compile.cpython-36.opt-1.pyc","mode":33188,"size":10140,"sha256":"439450d1df68281817d1d5cf920a978bab5df095dccb9ad7959af9c393a21441"},{"path":"/usr/lib64/python3.6/__pycache__/sre_compile.cpython-36.opt-2.pyc","mode":33188,"size":9726,"sha256":"3ab1595cb19900bb980cfc6697312217ccd6cdc27ea83316a8c02ff30d361f07"},{"path":"/usr/lib64/python3.6/__pycache__/sre_compile.cpython-36.pyc","mode":33188,"size":10280,"sha256":"4bf18662175c3f0176d131b6a74e7e363d5ca7061cfa44fa5593a1b8b5e305c0"},{"path":"/usr/lib64/python3.6/__pycache__/sre_constants.cpython-36.opt-1.pyc","mode":33188,"size":5974,"sha256":"c5bc1f5ca1e8df53486c2d168e9639d139590726fc52ecf2d53116db85688d0f"},{"path":"/usr/lib64/python3.6/__pycache__/sre_constants.cpython-36.opt-2.pyc","mode":33188,"size":5549,"sha256":"cacdfb57fa745a6c81ff064b5d3ca5433c3c7fb1bc17a341d94310cf80fdb266"},{"path":"/usr/lib64/python3.6/__pycache__/sre_constants.cpython-36.pyc","mode":33188,"size":5974,"sha256":"c5bc1f5ca1e8df53486c2d168e9639d139590726fc52ecf2d53116db85688d0f"},{"path":"/usr/lib64/python3.6/__pycache__/sre_parse.cpython-36.opt-1.pyc","mode":33188,"size":20313,"sha256":"d8be8330c6f5550d9da4c96f4cba9f3f7d0cc60e60dd3128d91b7c9a2a6471ed"},{"path":"/usr/lib64/python3.6/__pycache__/sre_parse.cpython-36.opt-2.pyc","mode":33188,"size":20265,"sha256":"a11de5ee258ae653164b8494cf80c3aede2125334011a5591ad95dea5476952c"},{"path":"/usr/lib64/python3.6/__pycache__/sre_parse.cpython-36.pyc","mode":33188,"size":20360,"sha256":"0d03967e2c51bbd9c90b936528678650559b575ad2e3b3d1c4d0986a02cd1ae0"},{"path":"/usr/lib64/python3.6/__pycache__/ssl.cpython-36.opt-1.pyc","mode":33188,"size":35969,"sha256":"c1e42eebb60756cf84af3d5090b24a5605537a6869c5c08116b18aaab76da7b2"},{"path":"/usr/lib64/python3.6/__pycache__/ssl.cpython-36.opt-2.pyc","mode":33188,"size":26445,"sha256":"11b89c8135d77a719dcac96210728812096c51c33949bf547ea2c0f55b36ab98"},{"path":"/usr/lib64/python3.6/__pycache__/ssl.cpython-36.pyc","mode":33188,"size":35969,"sha256":"c1e42eebb60756cf84af3d5090b24a5605537a6869c5c08116b18aaab76da7b2"},{"path":"/usr/lib64/python3.6/__pycache__/stat.cpython-36.opt-1.pyc","mode":33188,"size":3853,"sha256":"692c79abb2ef4788432135fd956c65529eeb4d1c05004e6e1154a51e69f815b8"},{"path":"/usr/lib64/python3.6/__pycache__/stat.cpython-36.opt-2.pyc","mode":33188,"size":3175,"sha256":"4fdb815ed6d2596935e6c9b216257dc9446b1556f64a1ab0de72cd235d63c7ae"},{"path":"/usr/lib64/python3.6/__pycache__/stat.cpython-36.pyc","mode":33188,"size":3853,"sha256":"692c79abb2ef4788432135fd956c65529eeb4d1c05004e6e1154a51e69f815b8"},{"path":"/usr/lib64/python3.6/__pycache__/statistics.cpython-36.opt-1.pyc","mode":33188,"size":17935,"sha256":"151712671d077c6d6d01ef799bd38bd7b07a99e7bfaa953ee6ebe425d11c8431"},{"path":"/usr/lib64/python3.6/__pycache__/statistics.cpython-36.opt-2.pyc","mode":33188,"size":7248,"sha256":"0e411703ae4e504a791dcfeee984e3cee1f6cf76d0610a83c853bd475a1f01c5"},{"path":"/usr/lib64/python3.6/__pycache__/statistics.cpython-36.pyc","mode":33188,"size":18176,"sha256":"8699baf5d4ced98dbdb71561a45080f26fb4ba00abc0c5a3956db310f900fd6c"},{"path":"/usr/lib64/python3.6/__pycache__/string.cpython-36.opt-1.pyc","mode":33188,"size":7966,"sha256":"1beb74d0d7857001be5cb8b3268aaa6ab50919cc45d0a3e91563fb20204e381d"},{"path":"/usr/lib64/python3.6/__pycache__/string.cpython-36.opt-2.pyc","mode":33188,"size":6860,"sha256":"334a109e8359bcdf26bac62522dfbda59fc8eadde9fef34ab5335f3fc3eaee0c"},{"path":"/usr/lib64/python3.6/__pycache__/string.cpython-36.pyc","mode":33188,"size":7966,"sha256":"1beb74d0d7857001be5cb8b3268aaa6ab50919cc45d0a3e91563fb20204e381d"},{"path":"/usr/lib64/python3.6/__pycache__/stringprep.cpython-36.opt-1.pyc","mode":33188,"size":9974,"sha256":"b06ac9c852f9c4524a754d5f3fa40ca6b5865306730cafbb709e99cdc366342a"},{"path":"/usr/lib64/python3.6/__pycache__/stringprep.cpython-36.opt-2.pyc","mode":33188,"size":9754,"sha256":"477d2851436f35009f35adc44129b2da106cc32b0928a008c1e09d3490f8482a"},{"path":"/usr/lib64/python3.6/__pycache__/stringprep.cpython-36.pyc","mode":33188,"size":10032,"sha256":"ada306e07fb7d4ee59f60bc5b484b54aa7590dca96bd8cff949d064fd3fe49a2"},{"path":"/usr/lib64/python3.6/__pycache__/struct.cpython-36.opt-1.pyc","mode":33188,"size":314,"sha256":"e5740564579624bc68dbfdeca61e0acda2c86593f2706224121f1195ff16f252"},{"path":"/usr/lib64/python3.6/__pycache__/struct.cpython-36.opt-2.pyc","mode":33188,"size":314,"sha256":"e5740564579624bc68dbfdeca61e0acda2c86593f2706224121f1195ff16f252"},{"path":"/usr/lib64/python3.6/__pycache__/struct.cpython-36.pyc","mode":33188,"size":314,"sha256":"e5740564579624bc68dbfdeca61e0acda2c86593f2706224121f1195ff16f252"},{"path":"/usr/lib64/python3.6/__pycache__/subprocess.cpython-36.opt-1.pyc","mode":33188,"size":35386,"sha256":"23930b74c0118180ff5a669dea01cb07100a14c4678fab740b54b80cfe32d524"},{"path":"/usr/lib64/python3.6/__pycache__/subprocess.cpython-36.opt-2.pyc","mode":33188,"size":24672,"sha256":"c61dd50e862e866c4cb670a5af1e9d02310c52de87ddedbe236a2447de311c45"},{"path":"/usr/lib64/python3.6/__pycache__/subprocess.cpython-36.pyc","mode":33188,"size":35487,"sha256":"f665900fd5cb07fe0e72bcebcb3e86e618f83dc21defabf043d667772e88c195"},{"path":"/usr/lib64/python3.6/__pycache__/sunau.cpython-36.opt-1.pyc","mode":33188,"size":16940,"sha256":"5398b1ac3b9bbab47720a1732948d5189a7f5fd82379828a2f22ccaab7f78c14"},{"path":"/usr/lib64/python3.6/__pycache__/sunau.cpython-36.opt-2.pyc","mode":33188,"size":12350,"sha256":"54f39b4afb61f85896682da43fa8b232d1a5fbbbec50c136d920b7166512f637"},{"path":"/usr/lib64/python3.6/__pycache__/sunau.cpython-36.pyc","mode":33188,"size":16940,"sha256":"5398b1ac3b9bbab47720a1732948d5189a7f5fd82379828a2f22ccaab7f78c14"},{"path":"/usr/lib64/python3.6/__pycache__/symbol.cpython-36.opt-1.pyc","mode":33188,"size":2519,"sha256":"363bacf92cfbe880a8ffa163a70fb75b1d666dfcee049ee1d4dcb9b41d26a652"},{"path":"/usr/lib64/python3.6/__pycache__/symbol.cpython-36.opt-2.pyc","mode":33188,"size":2443,"sha256":"77b4943a3dbfcf4f990576dd0e87dc990a6e6763e0905d4182e08fe17abec0bf"},{"path":"/usr/lib64/python3.6/__pycache__/symbol.cpython-36.pyc","mode":33188,"size":2519,"sha256":"363bacf92cfbe880a8ffa163a70fb75b1d666dfcee049ee1d4dcb9b41d26a652"},{"path":"/usr/lib64/python3.6/__pycache__/symtable.cpython-36.opt-1.pyc","mode":33188,"size":10323,"sha256":"4e67e312cd0de8f7728fc9440c48b9895885bbc42ca88ec142c640cb0ef1baf9"},{"path":"/usr/lib64/python3.6/__pycache__/symtable.cpython-36.opt-2.pyc","mode":33188,"size":9626,"sha256":"c09e6772fadd634f95c50cdaa55a7148d7962f124ff4c7bd4aaaf4ced31882a3"},{"path":"/usr/lib64/python3.6/__pycache__/symtable.cpython-36.pyc","mode":33188,"size":10430,"sha256":"119e32f6b0998bb62b7d22add53f6b9135f4de9c614e3280755153f30b40b323"},{"path":"/usr/lib64/python3.6/__pycache__/sysconfig.cpython-36.opt-1.pyc","mode":33188,"size":15929,"sha256":"48ca74886832840b23f140db5e4cee49f6cc3f1c34d10826d0dd4fc8d605bda8"},{"path":"/usr/lib64/python3.6/__pycache__/sysconfig.cpython-36.opt-2.pyc","mode":33188,"size":13362,"sha256":"5e519b677c5eccab568014781c10b81105843db03d565a3562da6e8d3c684768"},{"path":"/usr/lib64/python3.6/__pycache__/sysconfig.cpython-36.pyc","mode":33188,"size":15929,"sha256":"48ca74886832840b23f140db5e4cee49f6cc3f1c34d10826d0dd4fc8d605bda8"},{"path":"/usr/lib64/python3.6/__pycache__/tabnanny.cpython-36.opt-1.pyc","mode":33188,"size":6977,"sha256":"c1b4970c29b06af83e71b338f04039469a8aa7dc998e368581fd881d2129d3ff"},{"path":"/usr/lib64/python3.6/__pycache__/tabnanny.cpython-36.opt-2.pyc","mode":33188,"size":6044,"sha256":"8d3673eb569f9ecbd94c15967da702ccfc9cfc97a9e34f3725ed38cf1e6a7230"},{"path":"/usr/lib64/python3.6/__pycache__/tabnanny.cpython-36.pyc","mode":33188,"size":6977,"sha256":"c1b4970c29b06af83e71b338f04039469a8aa7dc998e368581fd881d2129d3ff"},{"path":"/usr/lib64/python3.6/__pycache__/tarfile.cpython-36.opt-1.pyc","mode":33188,"size":62649,"sha256":"9abeff3d958b2a3bd18a0e66b1966fe27679a4fdd146aed8350710d7d4c4b388"},{"path":"/usr/lib64/python3.6/__pycache__/tarfile.cpython-36.opt-2.pyc","mode":33188,"size":48850,"sha256":"19efd5b45d8d08cd615ab3e660a7818e830a5f4aa871f3f66bc56a6e130e8923"},{"path":"/usr/lib64/python3.6/__pycache__/tarfile.cpython-36.pyc","mode":33188,"size":62649,"sha256":"9abeff3d958b2a3bd18a0e66b1966fe27679a4fdd146aed8350710d7d4c4b388"},{"path":"/usr/lib64/python3.6/__pycache__/telnetlib.cpython-36.opt-1.pyc","mode":33188,"size":18099,"sha256":"2d3386d4a0c4e7c0e801c0c9e307d0099cb01a447d92069eff86ca5b165ba766"},{"path":"/usr/lib64/python3.6/__pycache__/telnetlib.cpython-36.opt-2.pyc","mode":33188,"size":10589,"sha256":"7e8618333a4ca880b6c650f12a8e1342ce558614f04668fec20e275f380ed7a4"},{"path":"/usr/lib64/python3.6/__pycache__/telnetlib.cpython-36.pyc","mode":33188,"size":18099,"sha256":"2d3386d4a0c4e7c0e801c0c9e307d0099cb01a447d92069eff86ca5b165ba766"},{"path":"/usr/lib64/python3.6/__pycache__/tempfile.cpython-36.opt-1.pyc","mode":33188,"size":22229,"sha256":"6c5032440eddb82de8238bb01ec25e389140221a57100472ebfcade9c572ca9f"},{"path":"/usr/lib64/python3.6/__pycache__/tempfile.cpython-36.opt-2.pyc","mode":33188,"size":15757,"sha256":"c9b82b0a83ee9e9764dbf180099f39ca8f4485c9e4dccbfc32e2823156e90740"},{"path":"/usr/lib64/python3.6/__pycache__/tempfile.cpython-36.pyc","mode":33188,"size":22229,"sha256":"6c5032440eddb82de8238bb01ec25e389140221a57100472ebfcade9c572ca9f"},{"path":"/usr/lib64/python3.6/__pycache__/textwrap.cpython-36.opt-1.pyc","mode":33188,"size":13612,"sha256":"27bc952bcff768fdaa733ecb60bbcaa7ac6d4f6856069660249a8e4bab63fc4b"},{"path":"/usr/lib64/python3.6/__pycache__/textwrap.cpython-36.opt-2.pyc","mode":33188,"size":6315,"sha256":"41b6df15e19383f9d08338ff27df546345607a2d223c03efdc20ba3c9695dcce"},{"path":"/usr/lib64/python3.6/__pycache__/textwrap.cpython-36.pyc","mode":33188,"size":13686,"sha256":"0d3c8718dce68ad6fe6906f3087fa58566892f87ede37bb062c949033a3ebd68"},{"path":"/usr/lib64/python3.6/__pycache__/this.cpython-36.opt-1.pyc","mode":33188,"size":1267,"sha256":"dd4f00b602ca38b8a1ff5c170547c8e66dfcd333063eb96173c4b5ac417f412b"},{"path":"/usr/lib64/python3.6/__pycache__/this.cpython-36.opt-2.pyc","mode":33188,"size":1267,"sha256":"dd4f00b602ca38b8a1ff5c170547c8e66dfcd333063eb96173c4b5ac417f412b"},{"path":"/usr/lib64/python3.6/__pycache__/this.cpython-36.pyc","mode":33188,"size":1267,"sha256":"dd4f00b602ca38b8a1ff5c170547c8e66dfcd333063eb96173c4b5ac417f412b"},{"path":"/usr/lib64/python3.6/__pycache__/threading.cpython-36.opt-1.pyc","mode":33188,"size":36583,"sha256":"8a506630c1d3ae27e2fce6cfd3fec57d7940613662d39ed7e84f15a9f55747a6"},{"path":"/usr/lib64/python3.6/__pycache__/threading.cpython-36.opt-2.pyc","mode":33188,"size":20542,"sha256":"41941d10c5bdf38f0d01f5346a85a2824fb66315e7330a005909edd693ef9b8f"},{"path":"/usr/lib64/python3.6/__pycache__/threading.cpython-36.pyc","mode":33188,"size":37236,"sha256":"1eb6038dd92cefa76aba6f6b016b20ce8967884b6e86ed015169b6b99980e513"},{"path":"/usr/lib64/python3.6/__pycache__/timeit.cpython-36.opt-1.pyc","mode":33188,"size":11605,"sha256":"8bfa38d16282e252c7b0b8380f197505bdd563667c99868131a81ab36a440309"},{"path":"/usr/lib64/python3.6/__pycache__/timeit.cpython-36.opt-2.pyc","mode":33188,"size":5624,"sha256":"390ac834c7f3053c4abcdbede55b740abbbcc04d0f6877419f1fa05553bf61df"},{"path":"/usr/lib64/python3.6/__pycache__/timeit.cpython-36.pyc","mode":33188,"size":11605,"sha256":"8bfa38d16282e252c7b0b8380f197505bdd563667c99868131a81ab36a440309"},{"path":"/usr/lib64/python3.6/__pycache__/token.cpython-36.opt-1.pyc","mode":33188,"size":3322,"sha256":"61c95fc8cbf4fd76d58f941cf6afde4c757a71f362fbb1111a301b88480af25a"},{"path":"/usr/lib64/python3.6/__pycache__/token.cpython-36.opt-2.pyc","mode":33188,"size":3272,"sha256":"c3159f495b6ff5227301df923c133918c508fff8fdc80d73dce70ec44ae9df84"},{"path":"/usr/lib64/python3.6/__pycache__/token.cpython-36.pyc","mode":33188,"size":3322,"sha256":"61c95fc8cbf4fd76d58f941cf6afde4c757a71f362fbb1111a301b88480af25a"},{"path":"/usr/lib64/python3.6/__pycache__/tokenize.cpython-36.opt-1.pyc","mode":33188,"size":18603,"sha256":"8b6e13bc37f111effb36757a45d8611d0c48888b0184bedc88ccec6007ca1508"},{"path":"/usr/lib64/python3.6/__pycache__/tokenize.cpython-36.opt-2.pyc","mode":33188,"size":15003,"sha256":"bf207741f20de109292b58774a7b75d0eeb688b3fc2b0a24ae954a8ec1e75e97"},{"path":"/usr/lib64/python3.6/__pycache__/tokenize.cpython-36.pyc","mode":33188,"size":18649,"sha256":"1d056af338121cdd6d07c553affb360681103d6a973928917c9901d6589d8ff1"},{"path":"/usr/lib64/python3.6/__pycache__/trace.cpython-36.opt-1.pyc","mode":33188,"size":19497,"sha256":"1495a2cb9930b5bcc4cc6ad5af7eee1752b64bd5ffede6ad164a98e95220d026"},{"path":"/usr/lib64/python3.6/__pycache__/trace.cpython-36.opt-2.pyc","mode":33188,"size":16494,"sha256":"e804ba5700387a5b00ed20742000b7e635488fe7208f8a3315a8c72e3e9fc174"},{"path":"/usr/lib64/python3.6/__pycache__/trace.cpython-36.pyc","mode":33188,"size":19497,"sha256":"1495a2cb9930b5bcc4cc6ad5af7eee1752b64bd5ffede6ad164a98e95220d026"},{"path":"/usr/lib64/python3.6/__pycache__/traceback.cpython-36.opt-1.pyc","mode":33188,"size":19648,"sha256":"47775f5e6149c49a9cbee7e17bd8fc819432a9072c2b570de85ce285c4faa089"},{"path":"/usr/lib64/python3.6/__pycache__/traceback.cpython-36.opt-2.pyc","mode":33188,"size":10747,"sha256":"fec5cfda7847a2240daa9bef36489d60109c07efb1c9eaa2a3526932fab662ee"},{"path":"/usr/lib64/python3.6/__pycache__/traceback.cpython-36.pyc","mode":33188,"size":19648,"sha256":"47775f5e6149c49a9cbee7e17bd8fc819432a9072c2b570de85ce285c4faa089"},{"path":"/usr/lib64/python3.6/__pycache__/tracemalloc.cpython-36.opt-1.pyc","mode":33188,"size":17231,"sha256":"6f559809ffc1f04abf78d82c53340d23d144649e206aad597ae97bf6486a02de"},{"path":"/usr/lib64/python3.6/__pycache__/tracemalloc.cpython-36.opt-2.pyc","mode":33188,"size":15815,"sha256":"9f987a22e71fd5098960abc0b800b66cc190d5cda1e1b7b3102c597687d9556a"},{"path":"/usr/lib64/python3.6/__pycache__/tracemalloc.cpython-36.pyc","mode":33188,"size":17231,"sha256":"6f559809ffc1f04abf78d82c53340d23d144649e206aad597ae97bf6486a02de"},{"path":"/usr/lib64/python3.6/__pycache__/tty.cpython-36.opt-1.pyc","mode":33188,"size":1074,"sha256":"ac1bc9666ec3ada1a63c089372c04e50cbb12d396cb50925e60614aa0cc57002"},{"path":"/usr/lib64/python3.6/__pycache__/tty.cpython-36.opt-2.pyc","mode":33188,"size":973,"sha256":"4c98ea8d6822d0aa7bb25cb64dc31b3cac6bb13619a30bcccbfdd4ffc3f893ee"},{"path":"/usr/lib64/python3.6/__pycache__/tty.cpython-36.pyc","mode":33188,"size":1074,"sha256":"ac1bc9666ec3ada1a63c089372c04e50cbb12d396cb50925e60614aa0cc57002"},{"path":"/usr/lib64/python3.6/__pycache__/types.cpython-36.opt-1.pyc","mode":33188,"size":8203,"sha256":"e293814a398a846efa9e069e09e5bb2566d980dca9498d7a5f66e5f9868b6843"},{"path":"/usr/lib64/python3.6/__pycache__/types.cpython-36.opt-2.pyc","mode":33188,"size":7036,"sha256":"a8556630a6793dd6de1953f493b2e806d391384389d8bb25781cfbf833a05313"},{"path":"/usr/lib64/python3.6/__pycache__/types.cpython-36.pyc","mode":33188,"size":8203,"sha256":"e293814a398a846efa9e069e09e5bb2566d980dca9498d7a5f66e5f9868b6843"},{"path":"/usr/lib64/python3.6/__pycache__/typing.cpython-36.opt-1.pyc","mode":33188,"size":72900,"sha256":"8dbac34c03e4fec33bb2f2461d86f2279b890961656c099aac9615cea5f9fd33"},{"path":"/usr/lib64/python3.6/__pycache__/typing.cpython-36.opt-2.pyc","mode":33188,"size":56049,"sha256":"8ec4523ccb2bb1bb2ac397c0ed2fffd22743740f01eb0c42fb792839ec18049a"},{"path":"/usr/lib64/python3.6/__pycache__/typing.cpython-36.pyc","mode":33188,"size":73308,"sha256":"7836454ddb785d426efc6bfcb4fa6b6ac3c974b6efd09ff260e61b497b40895d"},{"path":"/usr/lib64/python3.6/__pycache__/uu.cpython-36.opt-1.pyc","mode":33188,"size":3500,"sha256":"04b3a134f964af97ae6c62e78dba35c992e4fbf200dd3dee9d41c8e460f74b85"},{"path":"/usr/lib64/python3.6/__pycache__/uu.cpython-36.opt-2.pyc","mode":33188,"size":3282,"sha256":"513c3743b55a2bdfc4ccec204de3b776b3e6fcad83de9d18c615c87ee708d7db"},{"path":"/usr/lib64/python3.6/__pycache__/uu.cpython-36.pyc","mode":33188,"size":3500,"sha256":"04b3a134f964af97ae6c62e78dba35c992e4fbf200dd3dee9d41c8e460f74b85"},{"path":"/usr/lib64/python3.6/__pycache__/uuid.cpython-36.opt-1.pyc","mode":33188,"size":20812,"sha256":"6b972cd6db1b24889c2e7641c2eee267dabafba719fefa69445a6247a0273039"},{"path":"/usr/lib64/python3.6/__pycache__/uuid.cpython-36.opt-2.pyc","mode":33188,"size":14144,"sha256":"cc357cfe0919058a96c8dee5f24a367ffcbda2ecabe90b5544adb0b2cf9386c7"},{"path":"/usr/lib64/python3.6/__pycache__/uuid.cpython-36.pyc","mode":33188,"size":20948,"sha256":"5f117f804cf3f9c4a5c5041f6014038da4445ca113b44fb3f63de7907513d8ff"},{"path":"/usr/lib64/python3.6/__pycache__/warnings.cpython-36.opt-1.pyc","mode":33188,"size":12668,"sha256":"91c8eee1e644dcb49e939ea13bf1e4e8d400cb976b126fc4a21ce844d81ad59f"},{"path":"/usr/lib64/python3.6/__pycache__/warnings.cpython-36.opt-2.pyc","mode":33188,"size":10288,"sha256":"50c32e77bcbb2757b07cd61a5d692e24a4023e7ec55cadc916e17f7a1602ace3"},{"path":"/usr/lib64/python3.6/__pycache__/warnings.cpython-36.pyc","mode":33188,"size":13260,"sha256":"8d240f3548122fa1aa398cc4d64a3bf41c733b131d5eb5eecd02d5230188a137"},{"path":"/usr/lib64/python3.6/__pycache__/wave.cpython-36.opt-1.pyc","mode":33188,"size":17835,"sha256":"ef10e6d8f70fe20bdd9b9b7ad3e0cd9c3195450aee1e59c7a8a6571eb1fdf172"},{"path":"/usr/lib64/python3.6/__pycache__/wave.cpython-36.opt-2.pyc","mode":33188,"size":11844,"sha256":"a5f1dc77e98bae2a36aefe1b09780c5e04e827d70621ad6de74db8b192cde74c"},{"path":"/usr/lib64/python3.6/__pycache__/wave.cpython-36.pyc","mode":33188,"size":17887,"sha256":"df4e147f27e70ab5ef79feb209133f120a3d9f66eb74c7a86a93d5607b1aea84"},{"path":"/usr/lib64/python3.6/__pycache__/weakref.cpython-36.opt-1.pyc","mode":33188,"size":19115,"sha256":"e63aefebab5a6c2746edf507a858d84475070b50c0a88eda4d35aba1ab8abb62"},{"path":"/usr/lib64/python3.6/__pycache__/weakref.cpython-36.opt-2.pyc","mode":33188,"size":15815,"sha256":"056542509c7b0c8a8adf285c01abbf5caa82dcbac7b59d6a693f94fd270a5486"},{"path":"/usr/lib64/python3.6/__pycache__/weakref.cpython-36.pyc","mode":33188,"size":19145,"sha256":"04d80fc29f6eafe4048c37b767f7390190c8896035c59908805d550b6d0d5dce"},{"path":"/usr/lib64/python3.6/__pycache__/webbrowser.cpython-36.opt-1.pyc","mode":33188,"size":15766,"sha256":"cb28ec01486cf66f4c468796ac4a0651627d466b51b5ec0ecfd280f3bd225bee"},{"path":"/usr/lib64/python3.6/__pycache__/webbrowser.cpython-36.opt-2.pyc","mode":33188,"size":13897,"sha256":"ee8e7a1c7d5f2335ca3d1241771426aa61d5055045741ae90468b4076cc27405"},{"path":"/usr/lib64/python3.6/__pycache__/webbrowser.cpython-36.pyc","mode":33188,"size":15799,"sha256":"e6e258baf04af3ddf659e556ecbae533eb700736dedeefda8374d6636ae2ed56"},{"path":"/usr/lib64/python3.6/__pycache__/xdrlib.cpython-36.opt-1.pyc","mode":33188,"size":8304,"sha256":"4a1b63d0ed933d72c276afc62b3412c43cdd2265601892f93c422c649ea00d66"},{"path":"/usr/lib64/python3.6/__pycache__/xdrlib.cpython-36.opt-2.pyc","mode":33188,"size":7819,"sha256":"551083a8d400a9d4db89c6aee197d3498630fe384c72135d207f61d1ea4284d3"},{"path":"/usr/lib64/python3.6/__pycache__/xdrlib.cpython-36.pyc","mode":33188,"size":8304,"sha256":"4a1b63d0ed933d72c276afc62b3412c43cdd2265601892f93c422c649ea00d66"},{"path":"/usr/lib64/python3.6/__pycache__/zipapp.cpython-36.opt-1.pyc","mode":33188,"size":5536,"sha256":"4cd90bf69a5afb1dacf12951f436c1f597cf8bd3b0cada4dd69ef4d5fdffa05d"},{"path":"/usr/lib64/python3.6/__pycache__/zipapp.cpython-36.opt-2.pyc","mode":33188,"size":4360,"sha256":"b47512ee322231c94686e39ae3b03fab968f7800f1072f4698938957fbb88874"},{"path":"/usr/lib64/python3.6/__pycache__/zipapp.cpython-36.pyc","mode":33188,"size":5536,"sha256":"4cd90bf69a5afb1dacf12951f436c1f597cf8bd3b0cada4dd69ef4d5fdffa05d"},{"path":"/usr/lib64/python3.6/__pycache__/zipfile.cpython-36.opt-1.pyc","mode":33188,"size":48604,"sha256":"2e28c6740e03c13f3a27a5b538ccd0f00d7ec84609a308af64dced209959d685"},{"path":"/usr/lib64/python3.6/__pycache__/zipfile.cpython-36.opt-2.pyc","mode":33188,"size":42101,"sha256":"03cbf1aa8b7a162874c73fbb455f8a528d17254d0b9ffae6df80a4e2d2a28212"},{"path":"/usr/lib64/python3.6/__pycache__/zipfile.cpython-36.pyc","mode":33188,"size":48672,"sha256":"3097e5aec0d7fa0adc523ec01a88a63de2744cbe3d95e16f19b99ae54851026c"},{"path":"/usr/lib64/python3.6/_bootlocale.py","mode":33188,"size":1301,"sha256":"f9f34905abf0feaf7db40193b6e34d2225ca8924c5b91cb40a1000b3cb03aba4"},{"path":"/usr/lib64/python3.6/_collections_abc.py","mode":33188,"size":26392,"sha256":"36e57ff3a6481219af29a7b8c6eeb4ae5a703232df55f494f299d483ecba7765"},{"path":"/usr/lib64/python3.6/_compat_pickle.py","mode":33188,"size":8749,"sha256":"71248216fb1cc2b9a0a1faa305daa8c680d9c637141cb2db283e407684209cab"},{"path":"/usr/lib64/python3.6/_compression.py","mode":33188,"size":5340,"sha256":"326755377c7b8d98cf71333d62e5b4cb1c4e06519d704961da025f5933dee08d"},{"path":"/usr/lib64/python3.6/_dummy_thread.py","mode":33188,"size":5118,"sha256":"09c292c80346d122af79d64a20fa511a366eaf19e5561ff848cd766e363a4f0b"},{"path":"/usr/lib64/python3.6/_markupbase.py","mode":33188,"size":14598,"sha256":"3e4c98938db0d1932ab2ddc1a50b663f99b76e64986e2ea1232879a6dd34c559"},{"path":"/usr/lib64/python3.6/_osx_support.py","mode":33188,"size":19138,"sha256":"ec8b5726de04e4fe0cf38613444758d3a656929ae53724d4dfae395a1e9eee0d"},{"path":"/usr/lib64/python3.6/_pydecimal.py","mode":33188,"size":230228,"sha256":"0c375ff14f2c671699860846ca040cbba5d9367f6315e5ee890d69dbc14da156"},{"path":"/usr/lib64/python3.6/_pyio.py","mode":33188,"size":88097,"sha256":"03095178e084f7f65704110a7557b7e1ba161a749c96573acf4e898c0a349911"},{"path":"/usr/lib64/python3.6/_sitebuiltins.py","mode":33188,"size":3115,"sha256":"e9d3761e39a049203c19f4c4cd9259f3636f10a2c0f58cea579f0400fa453294"},{"path":"/usr/lib64/python3.6/_strptime.py","mode":33188,"size":24747,"sha256":"548ccd2eac49d58016a00660de1c1a3796939ad9e5293102685d166b69bc027f"},{"path":"/usr/lib64/python3.6/_sysconfigdata_dm_linux_x86_64-linux-gnu.py","mode":33188,"size":26977,"sha256":"f9e622347b71039eb3241146c5d15795191f627dd57e8e397d6df8be1e117695"},{"path":"/usr/lib64/python3.6/_sysconfigdata_m_linux_x86_64-linux-gnu.py","mode":33188,"size":27146,"sha256":"58d67f0feaf79b3615136e05663a362806392475699030ed666a549edae04c75"},{"path":"/usr/lib64/python3.6/_threading_local.py","mode":33188,"size":7214,"sha256":"61ba527d954d86c9db6eb84b74f98b5552fc7359803445a3c0ce34591252d97c"},{"path":"/usr/lib64/python3.6/_weakrefset.py","mode":33188,"size":5705,"sha256":"1ef5a903b7dcfedf9cdf7bdc85dbbb466fa934eb6985cf4022e4601b86c234b5"},{"path":"/usr/lib64/python3.6/abc.py","mode":33188,"size":8727,"sha256":"899b1ad16e1be88c7febc9c82fec022752e86e8b17af21945aef9e9c9a8000fd"},{"path":"/usr/lib64/python3.6/aifc.py","mode":33188,"size":32454,"sha256":"ae3e99e3d6319ec172e74f6dcbc99e5ac9f61801614600b1743d854dce596bc9"},{"path":"/usr/lib64/python3.6/antigravity.py","mode":33188,"size":477,"sha256":"703c075b720139e390d16836827d6c8452695b92d8192f333e4fe7e5b3d84d21"},{"path":"/usr/lib64/python3.6/argparse.py","mode":33188,"size":90372,"sha256":"691cba856bd171bd655b6ffe3d760520168821df182f9757dbd33c7565d3ba08"},{"path":"/usr/lib64/python3.6/ast.py","mode":33188,"size":12166,"sha256":"56d532b9b51967ccd68f5fb520e1fb24e5c43e010a06876aeee73f66b80af44a"},{"path":"/usr/lib64/python3.6/asynchat.py","mode":33188,"size":11328,"sha256":"76c3c3b10276c70a15974f1b2f3a0c7ecf4fcfeefb3a9340e411e394868904cf"},{"path":"/usr/lib64/python3.6/asyncio/__init__.py","mode":33188,"size":1436,"sha256":"2890ac5e22181b67787ce07c3d3eb11c0bbed17ae2c72231e752859f4818f566"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":780,"sha256":"ed085419f3f9e83e0012368752499d6b6cf7a6141e7d9d2ec724c5ccae7d55bc"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":724,"sha256":"2de84f9b64c204bafeebf6c0ee740f4e31655f2b41c3563f2ef5112bbcbf0a9b"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":780,"sha256":"ed085419f3f9e83e0012368752499d6b6cf7a6141e7d9d2ec724c5ccae7d55bc"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_events.cpython-36.opt-1.pyc","mode":33188,"size":39109,"sha256":"33ead85e4c8d9a3762563a44b871b22aae7e55dfdfa30d40ff7c250990c8c910"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_events.cpython-36.opt-2.pyc","mode":33188,"size":31257,"sha256":"d11891b9b833078dcf7b7ce314c21e3a79c326714bdc98d05d5b984c0d752ae2"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_events.cpython-36.pyc","mode":33188,"size":39347,"sha256":"e824d129ef1c5ee168ad8cd672b3c29480fff2bd996b69b1b4c041f1cc56fa25"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_futures.cpython-36.opt-1.pyc","mode":33188,"size":2049,"sha256":"d25ae0530e43f4ecda6bb132e238d9e553ecbb32a288c4a539bfb6eea303d617"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_futures.cpython-36.opt-2.pyc","mode":33188,"size":1705,"sha256":"9cac6724535de94f39cac1d97840dfa75da3d6feb108ab304173386ffcbad315"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_futures.cpython-36.pyc","mode":33188,"size":2049,"sha256":"d25ae0530e43f4ecda6bb132e238d9e553ecbb32a288c4a539bfb6eea303d617"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_subprocess.cpython-36.opt-1.pyc","mode":33188,"size":9168,"sha256":"88d036a45a8f8e357b74d273654985f2579c21ce9757aa76ee1701c839b750c2"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_subprocess.cpython-36.opt-2.pyc","mode":33188,"size":9066,"sha256":"f2f288b9872daf61230188544ab5c7c6be774ac6a2b13a2e7744be2582dba9a8"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_subprocess.cpython-36.pyc","mode":33188,"size":9264,"sha256":"2a9ee9faffcc115649e1d802532cff2846af0a2b925f20f8273b87d02474826d"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_tasks.cpython-36.opt-1.pyc","mode":33188,"size":1863,"sha256":"0bd9cccf306191ad699c7eee4f6596329f523004d32e0c180bb72c8c4704123b"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_tasks.cpython-36.opt-2.pyc","mode":33188,"size":1863,"sha256":"0bd9cccf306191ad699c7eee4f6596329f523004d32e0c180bb72c8c4704123b"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/base_tasks.cpython-36.pyc","mode":33188,"size":1863,"sha256":"0bd9cccf306191ad699c7eee4f6596329f523004d32e0c180bb72c8c4704123b"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/compat.cpython-36.opt-1.pyc","mode":33188,"size":734,"sha256":"bdba3aecd33c6eed4d34e73d18a610c7010859ca3d454cdf05685c815d843ada"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/compat.cpython-36.opt-2.pyc","mode":33188,"size":615,"sha256":"1fa31ec6425d262c929ffd75f104949828ffa20dbea744cb9a435eccb7fa0cf9"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/compat.cpython-36.pyc","mode":33188,"size":734,"sha256":"bdba3aecd33c6eed4d34e73d18a610c7010859ca3d454cdf05685c815d843ada"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/constants.cpython-36.opt-1.pyc","mode":33188,"size":253,"sha256":"9e522bd38d505fc85a9562c59627a316110f175dfdcb5de55a2f6660cc39b575"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/constants.cpython-36.opt-2.pyc","mode":33188,"size":226,"sha256":"5afcf274f52d83bb8a937878b02146ed4c92f945098eec983aa0d45be0ff6ff1"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/constants.cpython-36.pyc","mode":33188,"size":253,"sha256":"9e522bd38d505fc85a9562c59627a316110f175dfdcb5de55a2f6660cc39b575"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/coroutines.cpython-36.opt-1.pyc","mode":33188,"size":8446,"sha256":"2d9e63c5b104a574b3e0e2b77868751aba8467c76e860168a50895894175c2a7"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/coroutines.cpython-36.opt-2.pyc","mode":33188,"size":8214,"sha256":"85e2379b3dc8d6b82c7d0883648ab95b274d76831fe1e878a224a97492bc9772"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/coroutines.cpython-36.pyc","mode":33188,"size":8554,"sha256":"13ef4ae1a62cb8257523bcd4d51452fb94fb07ed73aecb2918555085cc5a3488"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/events.cpython-36.opt-1.pyc","mode":33188,"size":25232,"sha256":"1c4910518c009065f04ce57996ceba529851c3f3c676629a43da44b21987fd35"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/events.cpython-36.opt-2.pyc","mode":33188,"size":17657,"sha256":"6310f8b27e1f0b05e1aa409c0b1575d13b8238bce62ccc20837958b452ec886d"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/events.cpython-36.pyc","mode":33188,"size":25340,"sha256":"363f35128c711bd37cbbd8fafb1ab2b4e777369ca9f1ae3158ff049cc72eac04"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/futures.cpython-36.opt-1.pyc","mode":33188,"size":13504,"sha256":"f7ff3d00318b81692a1b12ba3608c08ec268562b4997a30cb1467b539bb201af"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/futures.cpython-36.opt-2.pyc","mode":33188,"size":7634,"sha256":"b1836e42e84a5da94f4848d2cce655a3dd67776b4082f013221fc4eb5314245c"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/futures.cpython-36.pyc","mode":33188,"size":13749,"sha256":"72e1596d72f9e458142a84d89e454ccc534564b9717444f7f6a3efbbc1f2507e"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/locks.cpython-36.opt-1.pyc","mode":33188,"size":15450,"sha256":"1031c2b765eef70b95e8a54bfbbf5f1f4d2ea8c0c2fb50ac44dd70702c6e961d"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/locks.cpython-36.opt-2.pyc","mode":33188,"size":8912,"sha256":"11b14d295603df39165e1977bcb5fa8e8dde2448fa003f7f95852a22a08284f0"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/locks.cpython-36.pyc","mode":33188,"size":15450,"sha256":"1031c2b765eef70b95e8a54bfbbf5f1f4d2ea8c0c2fb50ac44dd70702c6e961d"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/log.cpython-36.opt-1.pyc","mode":33188,"size":220,"sha256":"e85d20e9393290ed2aac04b71c2e2e85a7199bd0933ab95ab35a98aa93b25d8c"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/log.cpython-36.opt-2.pyc","mode":33188,"size":181,"sha256":"0263472aacc70371f90adf50d678fb1ea075fa3de6e2b7caba203a086cfb6e46"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/log.cpython-36.pyc","mode":33188,"size":220,"sha256":"e85d20e9393290ed2aac04b71c2e2e85a7199bd0933ab95ab35a98aa93b25d8c"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/proactor_events.cpython-36.opt-1.pyc","mode":33188,"size":16639,"sha256":"f361ab9fd4426b9a6e5c682564a654dd4121da1024482755173778596a5373d0"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/proactor_events.cpython-36.opt-2.pyc","mode":33188,"size":16239,"sha256":"516ecf1f351d6234d948ce89dade41d8ba8b8950473a2b915d12f89cbab0ea74"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/proactor_events.cpython-36.pyc","mode":33188,"size":16824,"sha256":"bdd59bd7cc26fe9d0c43694b7a227a396acf9b7b99dee9d5b261fd2d2970b145"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/protocols.cpython-36.opt-1.pyc","mode":33188,"size":5979,"sha256":"342a7988c449c140970a6f75c5aba10bb6b8facefafe1e60ff348495327a49ce"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/protocols.cpython-36.opt-2.pyc","mode":33188,"size":2222,"sha256":"0e2319fd54ccb04bbcda1350b75a8d1924fcaa9812be380cb9de778f6f966457"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/protocols.cpython-36.pyc","mode":33188,"size":5979,"sha256":"342a7988c449c140970a6f75c5aba10bb6b8facefafe1e60ff348495327a49ce"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/queues.cpython-36.opt-1.pyc","mode":33188,"size":8406,"sha256":"acf631462663e983e223af142a9027fe9ebc4800e3dbc70a075b1807d0ffe63f"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/queues.cpython-36.opt-2.pyc","mode":33188,"size":5543,"sha256":"5bda814783cf9f91415558c8deb4d75c25c555350c5ecd443d9996c6dd2cb237"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/queues.cpython-36.pyc","mode":33188,"size":8406,"sha256":"acf631462663e983e223af142a9027fe9ebc4800e3dbc70a075b1807d0ffe63f"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/selector_events.cpython-36.opt-1.pyc","mode":33188,"size":29511,"sha256":"2b0b05cb8f685d22490a538a7e48fc2cadb09aea45f10240f94646ac8d02952d"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/selector_events.cpython-36.opt-2.pyc","mode":33188,"size":27920,"sha256":"47e8342e5b228f7b4fa68cf75693f1937b62d864d85e868f928b6c4dc52e936c"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/selector_events.cpython-36.pyc","mode":33188,"size":29569,"sha256":"da2d319557e1631478418828a572ad28f63bee124d6f06fb2d8c1d10e5f2d63a"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/sslproto.cpython-36.opt-1.pyc","mode":33188,"size":20143,"sha256":"abbe4cc29af91cbec4d4db91c2755cb4a0c822a2ecfc0ce080be917186051eab"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/sslproto.cpython-36.opt-2.pyc","mode":33188,"size":13313,"sha256":"16f3e2e1eed28d4883b200e4e4d0cb9e1e0ffb43f8c4da398ba1e88c666b09f4"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/sslproto.cpython-36.pyc","mode":33188,"size":20345,"sha256":"70a1b20c0617776134b6c880367949baf1c75d2f9f606532c2978778199095f5"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/streams.cpython-36.opt-1.pyc","mode":33188,"size":19636,"sha256":"acf64ccda39a0a48cb7f4c006557bc0459d2904c7be5ce6a93c6bcd7ab32d597"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/streams.cpython-36.opt-2.pyc","mode":33188,"size":13358,"sha256":"17814b61f7692376074d67dc3e1f63bcb19e0477caff356521185b9c9e6308b8"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/streams.cpython-36.pyc","mode":33188,"size":19917,"sha256":"1730e53ed2ab3821c7c5c26b27b97b511dab762718c74ae82ef52417e1b55e88"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/subprocess.cpython-36.opt-1.pyc","mode":33188,"size":6796,"sha256":"b992bfb75aae3338f8808c714c8a337f281d685437a9d9fdb04532d5f2e83add"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/subprocess.cpython-36.opt-2.pyc","mode":33188,"size":6629,"sha256":"0251fc37cf2db138a5ddedd852bef6d820c04ad58bb1230c7427b04dfad2c9f5"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/subprocess.cpython-36.pyc","mode":33188,"size":6826,"sha256":"7a92f30f2078b934bfb334d9ea7bec25cb862d049c2108e112874e88cd375acf"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/tasks.cpython-36.opt-1.pyc","mode":33188,"size":18917,"sha256":"abc5d62b92894fece88ecd8080504de5a2bbbd0759586d33e0fb17150dcae8e1"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/tasks.cpython-36.opt-2.pyc","mode":33188,"size":12014,"sha256":"d161bf86a76cf1e4867f077817ef76ec1efb7e4fe2c67f73a950f064c8dd27fd"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/tasks.cpython-36.pyc","mode":33188,"size":19095,"sha256":"54317bbcc4fa7c5cd5e0c73980daa8a8e98774d227de478ea1131f547b2d8516"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/test_utils.cpython-36.opt-1.pyc","mode":33188,"size":17517,"sha256":"0733f0c744a654fc161ff84251b05f184968da71300478d7df50c623a7f40d1b"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/test_utils.cpython-36.opt-2.pyc","mode":33188,"size":16219,"sha256":"fdab6161a7e856916843788259ed4be503ffc9a409abcb141ec5b06bbb964dcc"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/test_utils.cpython-36.pyc","mode":33188,"size":17683,"sha256":"8db97cb98f82f940902530590039ebfaf3d0234fcd656dafde44b70318f30b67"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/transports.cpython-36.opt-1.pyc","mode":33188,"size":12032,"sha256":"3f0e345e20bc6bd4cb1de7d575afa181246ff361c45655517dedc3e2f24f5007"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/transports.cpython-36.opt-2.pyc","mode":33188,"size":6415,"sha256":"7fd133fadd1d9c0747cc19e085fc4c4a43aa8fed87528a243e08d006b863b683"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/transports.cpython-36.pyc","mode":33188,"size":12062,"sha256":"a3ff04fcc564ca8f9089c37f03a05a07b7ffc5e0cff02d145041f7a5bd018767"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/unix_events.cpython-36.opt-1.pyc","mode":33188,"size":30214,"sha256":"9292478b5ac55f1711a52cda360b1e8311de94aed26d911a6511c33b8f62cd78"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/unix_events.cpython-36.opt-2.pyc","mode":33188,"size":26515,"sha256":"8328f18b873cd01ed2524f89846483014288b5aabc1c227eb800e87be7e5394e"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/unix_events.cpython-36.pyc","mode":33188,"size":30557,"sha256":"f6f4e910756e781bf464c36007868d758de738d522717e24da46f5d22db859c2"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/windows_events.cpython-36.opt-1.pyc","mode":33188,"size":21496,"sha256":"dde35e34a9f2ab2fca44e666a66e6366841de1bf672f2d1f4fac91af30830b41"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/windows_events.cpython-36.opt-2.pyc","mode":33188,"size":20384,"sha256":"fb440c9c23bdb430084925eb9a8d6e3c20c7ac6d3022b71f6feeea2a48def7cd"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/windows_events.cpython-36.pyc","mode":33188,"size":21496,"sha256":"dde35e34a9f2ab2fca44e666a66e6366841de1bf672f2d1f4fac91af30830b41"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/windows_utils.cpython-36.opt-1.pyc","mode":33188,"size":5294,"sha256":"7911d41520bb450b5d2c354af6940ad0571d968a2c4496b6c11d20fbb91f68b4"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/windows_utils.cpython-36.opt-2.pyc","mode":33188,"size":4709,"sha256":"47b0f56cd4b49fb2183edb123d633bde6e4fc7f5e360bdc15c7686846fbac1cd"},{"path":"/usr/lib64/python3.6/asyncio/__pycache__/windows_utils.cpython-36.pyc","mode":33188,"size":5384,"sha256":"7799c98e3a529d3a0ed4d81d3b86541936c2da9bd20802c50ccc1e17b2f0a5db"},{"path":"/usr/lib64/python3.6/asyncio/base_events.py","mode":33188,"size":57346,"sha256":"653dea9f6a2a2711174a257bbed6bda2a3aff2f6d9b5f62e4a2da696e3c092fe"},{"path":"/usr/lib64/python3.6/asyncio/base_futures.py","mode":33188,"size":2074,"sha256":"00e0386d0c138905c852df6f39aa00cbad412387d529c22e93012bb664fd5863"},{"path":"/usr/lib64/python3.6/asyncio/base_subprocess.py","mode":33188,"size":9096,"sha256":"eca93117f2fcc5aa16ec0353b08bc94dfb9742e08756bfb3775d40a5062b2fc5"},{"path":"/usr/lib64/python3.6/asyncio/base_tasks.py","mode":33188,"size":2186,"sha256":"649cd8a7462f712f3c49ff35fbfa9c6812f40d47eb1933bb2462cdd304a4d860"},{"path":"/usr/lib64/python3.6/asyncio/compat.py","mode":33188,"size":543,"sha256":"224cbb8c9232106d4484e8cb6e7f90f697ce6a84c2bca7f4f759babe5a078f70"},{"path":"/usr/lib64/python3.6/asyncio/constants.py","mode":33188,"size":371,"sha256":"03ae52059bcdac6c2133a9a561a7f9107ee6edeeb055731445c616b54284a09f"},{"path":"/usr/lib64/python3.6/asyncio/coroutines.py","mode":33188,"size":11135,"sha256":"15ffac399e19d1d2a770e662bd54868d02c1d86aa0fc384bfe5a16b767a4f586"},{"path":"/usr/lib64/python3.6/asyncio/events.py","mode":33188,"size":23511,"sha256":"33e8b488badf85ad8781b6e22c5bc0e42837ec4c1fd58f9e425d6cc1717a9f43"},{"path":"/usr/lib64/python3.6/asyncio/futures.py","mode":33188,"size":15901,"sha256":"d0fc9aa0aafd0bd79f248e6c2a633955f4dd16d32cb6ae393b39b39fce01a5cc"},{"path":"/usr/lib64/python3.6/asyncio/locks.py","mode":33188,"size":15582,"sha256":"8ac4214c53faf9014de518755692db485febdd4c15548dcdcdc9cf486b083ac5"},{"path":"/usr/lib64/python3.6/asyncio/log.py","mode":33188,"size":124,"sha256":"80e4cc3ded4b138baba486519e7444801a23d6ac35f229d336a407a96af7e8d2"},{"path":"/usr/lib64/python3.6/asyncio/proactor_events.py","mode":33188,"size":20403,"sha256":"9afcd7c04b33ce9a52071d7bef9cc3862b68a23c4f1ac36b04598621e480568d"},{"path":"/usr/lib64/python3.6/asyncio/protocols.py","mode":33188,"size":4512,"sha256":"ff913fa20e1f0da183c431e17eff186d38b78f9f282b33821db3dab8cf71cb10"},{"path":"/usr/lib64/python3.6/asyncio/queues.py","mode":33188,"size":7957,"sha256":"24852aa90f29846bec832a2e95f3069c3eec95ff936613ed3f379d66b1cbcbe6"},{"path":"/usr/lib64/python3.6/asyncio/selector_events.py","mode":33188,"size":41640,"sha256":"1eed1bbf87da4d32a9f1f8c6169235984763a91b0af6936533dc79039c934860"},{"path":"/usr/lib64/python3.6/asyncio/sslproto.py","mode":33188,"size":26005,"sha256":"da5c8120fc207d806b3f325231c20c49089d7868f8af2402231432647249d46c"},{"path":"/usr/lib64/python3.6/asyncio/streams.py","mode":33188,"size":24472,"sha256":"7b748ff8967442b7d3c8b06d58db81b9ef0234acab7620be7d61fb94e486b7cb"},{"path":"/usr/lib64/python3.6/asyncio/subprocess.py","mode":33188,"size":7626,"sha256":"87c84b899ae458e58f4b5872550f6f3e8f93328f72a5e48c103498bcf270915a"},{"path":"/usr/lib64/python3.6/asyncio/tasks.py","mode":33188,"size":25060,"sha256":"9cb101f9a1a6e7be287b6d69f342d09b426c6a9c909f800ef5a3e6e167aa1878"},{"path":"/usr/lib64/python3.6/asyncio/test_utils.py","mode":33188,"size":15091,"sha256":"9d25af76e266072106db79f9e37783bc925e33aeedeab30b4002946d3533955b"},{"path":"/usr/lib64/python3.6/asyncio/transports.py","mode":33188,"size":10066,"sha256":"1264b6add166ade125e62c923501ef0e61b88d2bc7eac29781faafeb6e571971"},{"path":"/usr/lib64/python3.6/asyncio/unix_events.py","mode":33188,"size":37268,"sha256":"a6a962790e94ee28a82a0eea5f3665d084ca86cb6537dc2019cee942437fb1b8"},{"path":"/usr/lib64/python3.6/asyncio/windows_events.py","mode":33188,"size":27831,"sha256":"07117494d4f5efbff8e53d12c0d524afd16e9e6aef0fc92c48e91630c1f956b6"},{"path":"/usr/lib64/python3.6/asyncio/windows_utils.py","mode":33188,"size":6883,"sha256":"e7e0380444ffa0e0032fd2410cb9258a8e697082e9b00e0ff44c82e392a1ef4a"},{"path":"/usr/lib64/python3.6/asyncore.py","mode":33188,"size":20159,"sha256":"69434664078278dcbcf5df6fb6c14891f60b72e4d7b2a92fe271af8eaf0d9f41"},{"path":"/usr/lib64/python3.6/base64.py","mode":33261,"size":20388,"sha256":"b7e4164fa339b02a168932c5b906e5b73de61abe807fe425124e9da913ea2350"},{"path":"/usr/lib64/python3.6/bdb.py","mode":33188,"size":23556,"sha256":"0a5f2d9c8630cb115a15c901ee3e2671bc122fa7b5e45c52710d0fea96aba501"},{"path":"/usr/lib64/python3.6/binhex.py","mode":33188,"size":13954,"sha256":"725194a37c9d3dc75ff8f6843de625fea59f94cf38542ae6c5af3ea0a5f22735"},{"path":"/usr/lib64/python3.6/bisect.py","mode":33188,"size":2595,"sha256":"c743dca30b4809474e1c5e5774922c25bdebfca0fdd3e9888964dfb6fcf5f2ad"},{"path":"/usr/lib64/python3.6/bz2.py","mode":33188,"size":12478,"sha256":"0418fe23c9d67914f7f6162c16e24c7bbef13533137cabf51c0bfd981b7993ec"},{"path":"/usr/lib64/python3.6/cProfile.py","mode":33261,"size":5380,"sha256":"8f253975a95654bf7e4dc83c3aa49847f8ea33024737eee3019f814eef965cb5"},{"path":"/usr/lib64/python3.6/calendar.py","mode":33188,"size":23213,"sha256":"cd97284cf7df2917c0bc8672b40a48870c722b384a6665d8d3b5e3ea83d72101"},{"path":"/usr/lib64/python3.6/cgi.py","mode":33261,"size":36801,"sha256":"14722d1b0249b09c6069be58afab9f6a742dc6c7a81c4d5628adf42c4b709d26"},{"path":"/usr/lib64/python3.6/cgitb.py","mode":33188,"size":12018,"sha256":"6793fcf73fca7fdb51e3f118a5bf61b51692cb7b07827fab6b58e47e6a21b2f5"},{"path":"/usr/lib64/python3.6/chunk.py","mode":33188,"size":5425,"sha256":"c3859af8f37ae6a55ce507b32e01d37e4eef16af76ce0637cc99d2e5bbeeee4d"},{"path":"/usr/lib64/python3.6/cmd.py","mode":33188,"size":14860,"sha256":"1b18b978b7f2e2a587aa77f0bc7a6130718c4b680dd19cc749eb2ee7eb8b9590"},{"path":"/usr/lib64/python3.6/code.py","mode":33188,"size":10614,"sha256":"5e694ac0e6d7eb581e81725ea6c2819096578ebd792ec6ab799893b5fd59d593"},{"path":"/usr/lib64/python3.6/codecs.py","mode":33188,"size":36276,"sha256":"86cc1bbdbde916b92732b8813d0195c12c1d06eea277202118dc007637d0f725"},{"path":"/usr/lib64/python3.6/codeop.py","mode":33188,"size":5994,"sha256":"1df789d387eeccef0b13466e2e80b7809a1c9f57ae8d40792669a4c890b03cde"},{"path":"/usr/lib64/python3.6/collections/__init__.py","mode":33188,"size":45812,"sha256":"825e0bbe2610bbe0fcdeb44b9c5584b45b80bf0ae14898c7e08764baa532e1b8"},{"path":"/usr/lib64/python3.6/collections/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":45818,"sha256":"2bd1f762bd7cf243d8a5d79e6e14450d087032ff4052ee1bd929b5002f950350"},{"path":"/usr/lib64/python3.6/collections/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":35346,"sha256":"3a540530de2f21655756a68a4d824645ed0ac46fa2498ca0eba6f643bcdb17e8"},{"path":"/usr/lib64/python3.6/collections/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":45818,"sha256":"2bd1f762bd7cf243d8a5d79e6e14450d087032ff4052ee1bd929b5002f950350"},{"path":"/usr/lib64/python3.6/collections/__pycache__/abc.cpython-36.opt-1.pyc","mode":33188,"size":185,"sha256":"476a82a0fe743a834409b8eb66fcb35b185a3648a8425bd9b2b0524a994176f6"},{"path":"/usr/lib64/python3.6/collections/__pycache__/abc.cpython-36.opt-2.pyc","mode":33188,"size":185,"sha256":"476a82a0fe743a834409b8eb66fcb35b185a3648a8425bd9b2b0524a994176f6"},{"path":"/usr/lib64/python3.6/collections/__pycache__/abc.cpython-36.pyc","mode":33188,"size":185,"sha256":"476a82a0fe743a834409b8eb66fcb35b185a3648a8425bd9b2b0524a994176f6"},{"path":"/usr/lib64/python3.6/collections/abc.py","mode":33188,"size":68,"sha256":"ff7e06408ce45d25e7bc473a9c8bb69b440be429a9d3bec6506b9c0721529d46"},{"path":"/usr/lib64/python3.6/colorsys.py","mode":33188,"size":4064,"sha256":"134f6ffca766df778fc0aa49ada506fc1b351911da50fd83191dde19d80ea9a1"},{"path":"/usr/lib64/python3.6/compileall.py","mode":33188,"size":12125,"sha256":"e2adcfabad474466937803e24fbfc7c2d24af9d4dbd5e705e87c400834d12cb9"},{"path":"/usr/lib64/python3.6/concurrent/__init__.py","mode":33188,"size":38,"sha256":"87ad5c8954dd56fbbca04517bf87477ff4dce575170c7dd1281d7ef1f4214ac8"},{"path":"/usr/lib64/python3.6/concurrent/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":126,"sha256":"3f3cbdd8b706e1086ad08f7b464536e342c6f4ba6e49f97b653f24d9c1106509"},{"path":"/usr/lib64/python3.6/concurrent/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":126,"sha256":"3f3cbdd8b706e1086ad08f7b464536e342c6f4ba6e49f97b653f24d9c1106509"},{"path":"/usr/lib64/python3.6/concurrent/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":126,"sha256":"3f3cbdd8b706e1086ad08f7b464536e342c6f4ba6e49f97b653f24d9c1106509"},{"path":"/usr/lib64/python3.6/concurrent/futures/__init__.py","mode":33188,"size":800,"sha256":"e8aaaf62976a6f64efb7b1e338cb775abab16ee46e3d7ac7f2a67efbde2abded"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":642,"sha256":"7d19d76880942b05288903d9b7c94b3275b8846f8c1d7a49814f6b5f1c9cbb4f"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":562,"sha256":"8f5fc231bf7a86b76f0cb87b84e577561479b1da476f296ba4c9931bc13236c0"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":642,"sha256":"7d19d76880942b05288903d9b7c94b3275b8846f8c1d7a49814f6b5f1c9cbb4f"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/_base.cpython-36.opt-1.pyc","mode":33188,"size":20634,"sha256":"c3420c466f101b2b5572c32d29b6a3caedde8feab990162c67ecbe61cafd06a1"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/_base.cpython-36.opt-2.pyc","mode":33188,"size":12972,"sha256":"6ae869b3990c688af2766fd1a83d8946e0e06342229fd4ecae88a68658e6e03f"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/_base.cpython-36.pyc","mode":33188,"size":20634,"sha256":"c3420c466f101b2b5572c32d29b6a3caedde8feab990162c67ecbe61cafd06a1"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/process.cpython-36.opt-1.pyc","mode":33188,"size":15793,"sha256":"65d6b503644dd8c7b98594e5f11d4cdfeaf1ccffed091d15c502b2e2175f1bbe"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/process.cpython-36.opt-2.pyc","mode":33188,"size":9666,"sha256":"6871c541027b40f7107570a637a89951990d1e547fa6351a44a283cdf056e91c"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/process.cpython-36.pyc","mode":33188,"size":15831,"sha256":"509bbce0e7a500cf4ce5284fbd099c88f4a562e21b7abd23c1cef63857509f97"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/thread.cpython-36.opt-1.pyc","mode":33188,"size":3914,"sha256":"a3311e8192715edffd482b64539cccf856f89d8fae1b016be6f6ae473a79e8f7"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/thread.cpython-36.opt-2.pyc","mode":33188,"size":3603,"sha256":"fc4ab772727b25b646334e2d16a1db9657e0d347aa2f5fbb8c4653dbfeae306c"},{"path":"/usr/lib64/python3.6/concurrent/futures/__pycache__/thread.cpython-36.pyc","mode":33188,"size":3914,"sha256":"a3311e8192715edffd482b64539cccf856f89d8fae1b016be6f6ae473a79e8f7"},{"path":"/usr/lib64/python3.6/concurrent/futures/_base.py","mode":33188,"size":21235,"sha256":"57a307ef59d7dafef4e2eb70f8c44903b4030dd57d85b11c0caccc62024ef464"},{"path":"/usr/lib64/python3.6/concurrent/futures/process.py","mode":33188,"size":20492,"sha256":"aaf8bbce6f8d840f0641d9ad8e67c099516fae9ccdd6fdebe136f1a7f7c6cdcb"},{"path":"/usr/lib64/python3.6/concurrent/futures/thread.py","mode":33188,"size":5511,"sha256":"29280699736207d24d37241cccbb89f66318cba69ab5be3d1eae826c07426458"},{"path":"/usr/lib64/python3.6/config-3.6m-x86_64-linux-gnu/Makefile","mode":33188,"size":71683,"sha256":"6397202687bbd43c991201e587e07401f0e7b3d54823c290972454ecd6a1446d"},{"path":"/usr/lib64/python3.6/configparser.py","mode":33188,"size":53592,"sha256":"dbb2f08fb6e296ce47b10483a0527bd1abba0020e34b3308ae491505f482af06"},{"path":"/usr/lib64/python3.6/contextlib.py","mode":33188,"size":13162,"sha256":"7e616e9f16f30ff05ac7f60bb8be72704ec1d782e6e69cc3cee775d97eaec956"},{"path":"/usr/lib64/python3.6/copy.py","mode":33188,"size":8815,"sha256":"8fb9475ad4b1f770717b6d21b48c1ccbcc67e8acacff8c9b22c4abe4eda2f618"},{"path":"/usr/lib64/python3.6/copyreg.py","mode":33188,"size":7007,"sha256":"94e53fb03522ff29949d88e4982d5ba1a98451b80fd06ccafbec29b95eb1b02d"},{"path":"/usr/lib64/python3.6/crypt.py","mode":33188,"size":1864,"sha256":"4f420dbf9406b57165a1ab1fe392407b9007de709268073c6586164c31842691"},{"path":"/usr/lib64/python3.6/csv.py","mode":33188,"size":16180,"sha256":"0f46b397bda6998a4b7083478f22cd02bd6454a3dd1219a5874562eb3784244d"},{"path":"/usr/lib64/python3.6/ctypes/__init__.py","mode":33188,"size":16433,"sha256":"ef7bed390d4666e5c0c6b2cee1564d14d0f3fd5ec9cf40bdad262363bb8a6f4e"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":15925,"sha256":"de99151c75fd19f21cbf88d4d34c4fb7edc8fbf794512c2ab6f1dd465ff92e64"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":13657,"sha256":"367ced3ca47e08f73fa12f47bd5ec345c3dcb7c46f85afdc45d9397e0438e67c"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":15925,"sha256":"de99151c75fd19f21cbf88d4d34c4fb7edc8fbf794512c2ab6f1dd465ff92e64"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/_endian.cpython-36.opt-1.pyc","mode":33188,"size":1926,"sha256":"2b09471f7ae5029ff2b71731b9b1d74ba4ae2441e9df53547d400e13a216f1e2"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/_endian.cpython-36.opt-2.pyc","mode":33188,"size":1580,"sha256":"015b69fc67c9e3b54d430ed740baca896dfe7acbf78508916727b2eff9a738fc"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/_endian.cpython-36.pyc","mode":33188,"size":1926,"sha256":"2b09471f7ae5029ff2b71731b9b1d74ba4ae2441e9df53547d400e13a216f1e2"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/util.cpython-36.opt-1.pyc","mode":33188,"size":7228,"sha256":"0c0a2933a677f56ec14138107511c3ca6ae2caadc9641faf530ddb286123f1b3"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/util.cpython-36.opt-2.pyc","mode":33188,"size":6980,"sha256":"2a05c9884a011d764017525bbbb971426f924be8133f459fb11bd7450bba0ae2"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/util.cpython-36.pyc","mode":33188,"size":7228,"sha256":"0c0a2933a677f56ec14138107511c3ca6ae2caadc9641faf530ddb286123f1b3"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/wintypes.cpython-36.opt-1.pyc","mode":33188,"size":5097,"sha256":"437f709bc35449f6da1212a9e375fd12199f9ae155a3a3c84516a6804723226f"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/wintypes.cpython-36.opt-2.pyc","mode":33188,"size":5097,"sha256":"437f709bc35449f6da1212a9e375fd12199f9ae155a3a3c84516a6804723226f"},{"path":"/usr/lib64/python3.6/ctypes/__pycache__/wintypes.cpython-36.pyc","mode":33188,"size":5097,"sha256":"437f709bc35449f6da1212a9e375fd12199f9ae155a3a3c84516a6804723226f"},{"path":"/usr/lib64/python3.6/ctypes/_endian.py","mode":33188,"size":2000,"sha256":"4c9944875236d4227e8fd80ca0439417870ef387a532403393da91bf7ff67e16"},{"path":"/usr/lib64/python3.6/ctypes/macholib/README.ctypes","mode":33188,"size":296,"sha256":"dc29d1da83b6a0a09a41647e4111eee878ed079c2d6b54a98fd6d8b88dd581f2"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__init__.py","mode":33188,"size":154,"sha256":"1e77c01eec8f167ed10b754f153c0c743c8e5196ae9c81dffc08f129ab56dbfd"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":293,"sha256":"4cee7d895ff7727631416227f3a7b67e7e272b47933fe316e0913df2b90215c4"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":150,"sha256":"60a3b61d224c76579e6b71e58b55c7066f7fe7b045a4d6d4dd6f0c95b8e98c16"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":293,"sha256":"4cee7d895ff7727631416227f3a7b67e7e272b47933fe316e0913df2b90215c4"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/dyld.cpython-36.opt-1.pyc","mode":33188,"size":4161,"sha256":"587695ff6533b3c172f92286b0c3e68038cd2658fc28c04ef86d045257b13b4d"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/dyld.cpython-36.opt-2.pyc","mode":33188,"size":3819,"sha256":"7cfa89e09fffdf77f5b7bf9f9a571b45fb1f14f307c535e8a43c3f98e408e584"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/dyld.cpython-36.pyc","mode":33188,"size":4333,"sha256":"fd04d3ad9c2510b47d30ebee0aeda036420857678bc57242412b55258e78336c"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/dylib.cpython-36.opt-1.pyc","mode":33188,"size":1475,"sha256":"b7d6b947fcaddee53a68032fde009bf9e0ad8fac649adfee874e6a885ac75623"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/dylib.cpython-36.opt-2.pyc","mode":33188,"size":859,"sha256":"f82dd8e25e53ba60437b73c614562c3fbea4c533d6fb3487a9d9bda18a5432c0"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/dylib.cpython-36.pyc","mode":33188,"size":1920,"sha256":"7e13a65521753de18498a685c6c7365ed19abc718cb69a454cd5e71aa1fc5933"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/framework.cpython-36.opt-1.pyc","mode":33188,"size":1609,"sha256":"77ad02a44469476a593223584d74e310a6c1e4fcefae38c7ffff5c72797a18eb"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/framework.cpython-36.opt-2.pyc","mode":33188,"size":913,"sha256":"ba84a467d66a33279bd3842dbc655233395b4c1864260252c652f958625c3f8e"},{"path":"/usr/lib64/python3.6/ctypes/macholib/__pycache__/framework.cpython-36.pyc","mode":33188,"size":2200,"sha256":"c78581906dfb2d6f8bf08534bae08b2b313bfdb04234bd4714836998452ac4ec"},{"path":"/usr/lib64/python3.6/ctypes/macholib/dyld.py","mode":33188,"size":4933,"sha256":"a70186d3f9aa8f54297469cf3f560f631b8de18a24d9572bba4cddbeecaece39"},{"path":"/usr/lib64/python3.6/ctypes/macholib/dylib.py","mode":33188,"size":1828,"sha256":"17de9f3d36c6ccbd97ed4ca15a908ad06663a84aa5d485714b202db7fe8e171a"},{"path":"/usr/lib64/python3.6/ctypes/macholib/fetch_macholib","mode":33261,"size":84,"sha256":"a9f6faacdb1aa00ac2f68043cd445171de9639a732b861bd5e64090a2865ab23"},{"path":"/usr/lib64/python3.6/ctypes/macholib/framework.py","mode":33188,"size":2201,"sha256":"bf15187b7ea40c0255f14095e1091c13953c2efd98d96b409debc67669defc56"},{"path":"/usr/lib64/python3.6/ctypes/util.py","mode":33188,"size":11749,"sha256":"2238b7df25a2f1391b600c8488e48f167ee70a079b4d82b9f2366b33ef54f898"},{"path":"/usr/lib64/python3.6/ctypes/wintypes.py","mode":33188,"size":5628,"sha256":"c8f29e6cb1b05223e423391242f671381546130acae1fd7baafb65ba849f2a00"},{"path":"/usr/lib64/python3.6/curses/__init__.py","mode":33188,"size":3366,"sha256":"8cf902a0e85c6c0cbf78159e5a83ef8415357a267c2da16a026076994042b946"},{"path":"/usr/lib64/python3.6/curses/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":1785,"sha256":"4cf4398699fc64c6f4bc4a9edac7040d6e243da4c2a2fbb8c621a710ddc76fe2"},{"path":"/usr/lib64/python3.6/curses/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":1263,"sha256":"22c6c3734cca77058ae67ba51165034364beee770a0fd0d0cfcde7a44d85d632"},{"path":"/usr/lib64/python3.6/curses/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":1785,"sha256":"4cf4398699fc64c6f4bc4a9edac7040d6e243da4c2a2fbb8c621a710ddc76fe2"},{"path":"/usr/lib64/python3.6/curses/__pycache__/ascii.cpython-36.opt-1.pyc","mode":33188,"size":3923,"sha256":"98f334225235963e4a30753800adf8373eb4aea795b869edf5b6501e14cfd196"},{"path":"/usr/lib64/python3.6/curses/__pycache__/ascii.cpython-36.opt-2.pyc","mode":33188,"size":3855,"sha256":"57f148583d3cc01d6faaf585d2e7184520c42366e9b61e1357950b31e567b2fa"},{"path":"/usr/lib64/python3.6/curses/__pycache__/ascii.cpython-36.pyc","mode":33188,"size":3923,"sha256":"98f334225235963e4a30753800adf8373eb4aea795b869edf5b6501e14cfd196"},{"path":"/usr/lib64/python3.6/curses/__pycache__/has_key.cpython-36.opt-1.pyc","mode":33188,"size":4247,"sha256":"5925f89f436c91f9be1a55597ce9de542e1ca0cb9f4ecfd306cbb3a262e318c9"},{"path":"/usr/lib64/python3.6/curses/__pycache__/has_key.cpython-36.opt-2.pyc","mode":33188,"size":4247,"sha256":"5925f89f436c91f9be1a55597ce9de542e1ca0cb9f4ecfd306cbb3a262e318c9"},{"path":"/usr/lib64/python3.6/curses/__pycache__/has_key.cpython-36.pyc","mode":33188,"size":4247,"sha256":"5925f89f436c91f9be1a55597ce9de542e1ca0cb9f4ecfd306cbb3a262e318c9"},{"path":"/usr/lib64/python3.6/curses/__pycache__/panel.cpython-36.opt-1.pyc","mode":33188,"size":217,"sha256":"273ddf46f8bb14a497486574c4cbeec315c924aaedd0067ad829133fba9d09e5"},{"path":"/usr/lib64/python3.6/curses/__pycache__/panel.cpython-36.opt-2.pyc","mode":33188,"size":149,"sha256":"eead0db5cee14e57506fe793b29632a531d1600a573351757ccfc01103f83893"},{"path":"/usr/lib64/python3.6/curses/__pycache__/panel.cpython-36.pyc","mode":33188,"size":217,"sha256":"273ddf46f8bb14a497486574c4cbeec315c924aaedd0067ad829133fba9d09e5"},{"path":"/usr/lib64/python3.6/curses/__pycache__/textpad.cpython-36.opt-1.pyc","mode":33188,"size":5910,"sha256":"482559eb0de9bb61fc5695383afa45912ccc923342f9ec81a8bcde6208385f62"},{"path":"/usr/lib64/python3.6/curses/__pycache__/textpad.cpython-36.opt-2.pyc","mode":33188,"size":4349,"sha256":"efb2f9973cca7691c182b4efb6d3d07b20947cda6da69b8a380397a58969b98b"},{"path":"/usr/lib64/python3.6/curses/__pycache__/textpad.cpython-36.pyc","mode":33188,"size":5910,"sha256":"482559eb0de9bb61fc5695383afa45912ccc923342f9ec81a8bcde6208385f62"},{"path":"/usr/lib64/python3.6/curses/ascii.py","mode":33188,"size":2547,"sha256":"cf0137c2143c5e5bea2ccd25bfc61f3a274c5d8fdab3bc4c2c7329412ce7b656"},{"path":"/usr/lib64/python3.6/curses/has_key.py","mode":33188,"size":5634,"sha256":"15a052812d9ae80124bb25b3f5b9ffae38e2b03073774e163abf3d773140cfb3"},{"path":"/usr/lib64/python3.6/curses/panel.py","mode":33188,"size":87,"sha256":"13ef404a30da1825a612ca3e453db88c305d45deef4441c4c9e2ef7ee0ef50c7"},{"path":"/usr/lib64/python3.6/curses/textpad.py","mode":33188,"size":7657,"sha256":"bbc4634b3396bb6aa89f186206b9e236047e443ffd727116f45b537f4dce0759"},{"path":"/usr/lib64/python3.6/datetime.py","mode":33188,"size":82034,"sha256":"9a2cd7048ba27937346ba657499442fdcf94823c9f2b53f4c8f3e2ff61159add"},{"path":"/usr/lib64/python3.6/dbm/__init__.py","mode":33188,"size":5783,"sha256":"82cbe361d931d58c3785da0fe2e91588660c481877ba3acb84a641f4cd96e9b6"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":4171,"sha256":"ff9464142c2151e1475387e9d37eb42576bda26cfcca52fd900efee47e8621fb"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":2228,"sha256":"9e7cd896be160a945b416d27f31b8d72550e7f1020291dba2bcae38810d11874"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":4171,"sha256":"ff9464142c2151e1475387e9d37eb42576bda26cfcca52fd900efee47e8621fb"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/dumb.cpython-36.opt-1.pyc","mode":33188,"size":8215,"sha256":"a4bc6261aec0f7d5a7f90f1974e805e06de36b9ca550e875549eff14231a8923"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/dumb.cpython-36.opt-2.pyc","mode":33188,"size":6924,"sha256":"0791dc0fd54c51756178e3c883272efb92eb16986a599d130b08842679151c1d"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/dumb.cpython-36.pyc","mode":33188,"size":8215,"sha256":"a4bc6261aec0f7d5a7f90f1974e805e06de36b9ca550e875549eff14231a8923"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/gnu.cpython-36.opt-1.pyc","mode":33188,"size":197,"sha256":"af75b338dadc2744806d4312a1561ccec7e52f5713d29be440164d416a529793"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/gnu.cpython-36.opt-2.pyc","mode":33188,"size":136,"sha256":"c0c23b48296164491fdb49fb52c81564c1e442abbfb824aad96a23be006c9791"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/gnu.cpython-36.pyc","mode":33188,"size":197,"sha256":"af75b338dadc2744806d4312a1561ccec7e52f5713d29be440164d416a529793"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/ndbm.cpython-36.opt-1.pyc","mode":33188,"size":196,"sha256":"44c1dde81bd2f0bf49697473accf96fb5fe9dd411444cd2398aa73723cb89e2d"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/ndbm.cpython-36.opt-2.pyc","mode":33188,"size":136,"sha256":"6517b7ce151fbe331bd4938a2940402e0228cc6111d50768074b0debc56681cd"},{"path":"/usr/lib64/python3.6/dbm/__pycache__/ndbm.cpython-36.pyc","mode":33188,"size":196,"sha256":"44c1dde81bd2f0bf49697473accf96fb5fe9dd411444cd2398aa73723cb89e2d"},{"path":"/usr/lib64/python3.6/dbm/dumb.py","mode":33188,"size":11989,"sha256":"894ecf660d37ac2e1cb6ad2361fe9345afdfe4b2cc809a3eef41b7b8ee56a646"},{"path":"/usr/lib64/python3.6/dbm/gnu.py","mode":33188,"size":72,"sha256":"36cd4904f50e00c4df4ad9d450b3970e150957425f47c00cf979ba73eff49778"},{"path":"/usr/lib64/python3.6/dbm/ndbm.py","mode":33188,"size":70,"sha256":"1bcc2d9b2fad1901f3421a174eeecb5b8ccc6763283b87bbe0705b404c71904b"},{"path":"/usr/lib64/python3.6/decimal.py","mode":33188,"size":320,"sha256":"000c00bad31d126b054c6ec7f3e02b27c0f9a4d579f987d3c4f879cee1bacb81"},{"path":"/usr/lib64/python3.6/difflib.py","mode":33188,"size":84377,"sha256":"d58cdf9944fee6e2bd4513d5f172e34b3b29967bb5d1a6aaef983e34381f0023"},{"path":"/usr/lib64/python3.6/dis.py","mode":33188,"size":18132,"sha256":"aa85b95f39b3f4b4989447f74fc51792054e7a02b7a948ed6c589d203fcf852d"},{"path":"/usr/lib64/python3.6/distutils/README","mode":33188,"size":295,"sha256":"7c8dd7dc035b7050c051056ddb91023a0ec92e6582a0987de13953551eca2759"},{"path":"/usr/lib64/python3.6/distutils/__init__.py","mode":33188,"size":236,"sha256":"6e2c4b7ba17bd010296d63aab23e13145c3da3552700bd09032489db88eee0af"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":378,"sha256":"9e37dc16b7f23d40dcf76b69ae1bbe7618bc10568b9c3b9e60f983780f5dd8cf"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":196,"sha256":"296422d5e0d9368c163df03c228d29e5eb73a89ecad54fe475553cc9ac043a7f"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":378,"sha256":"9e37dc16b7f23d40dcf76b69ae1bbe7618bc10568b9c3b9e60f983780f5dd8cf"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/_msvccompiler.cpython-36.opt-1.pyc","mode":33188,"size":13501,"sha256":"e8251968e39712a20cf849dfbdc1887c9f7e01e8a12fd80193eb5f95529a8a06"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/_msvccompiler.cpython-36.opt-2.pyc","mode":33188,"size":12689,"sha256":"86cf6c24b46dff88ec873bcba1a51a3459f99b692a2a7f59299d42af39dde570"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/_msvccompiler.cpython-36.pyc","mode":33188,"size":13562,"sha256":"49bfcc9f9616028cec898a3fc898ab8de34866e3db61ba7033c14e0a84648bb5"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/archive_util.cpython-36.opt-1.pyc","mode":33188,"size":6527,"sha256":"4556d6924d1f7146f5cdc92aa77d0dc43adfb52a9f4ce05cf2f501000ef5a2c7"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/archive_util.cpython-36.opt-2.pyc","mode":33188,"size":4486,"sha256":"f1587652fd4b5a68806d1bee643fd549279c848e514063976c7681d794420d13"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/archive_util.cpython-36.pyc","mode":33188,"size":6527,"sha256":"4556d6924d1f7146f5cdc92aa77d0dc43adfb52a9f4ce05cf2f501000ef5a2c7"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/bcppcompiler.cpython-36.opt-1.pyc","mode":33188,"size":6481,"sha256":"18d54d6eb4651d843b1ca0fea47063bdb793a736ebe52aff93c8d5108750eeda"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/bcppcompiler.cpython-36.opt-2.pyc","mode":33188,"size":6193,"sha256":"a4b5ea952c6e3ab7b5631412a00e555028a7b7d0b486952628623097c87de7ac"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/bcppcompiler.cpython-36.pyc","mode":33188,"size":6481,"sha256":"18d54d6eb4651d843b1ca0fea47063bdb793a736ebe52aff93c8d5108750eeda"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/ccompiler.cpython-36.opt-1.pyc","mode":33188,"size":33220,"sha256":"d020d0402fb4f1a13fe343f49f4a10b83c7743332c920fcea20cb0cac20d0013"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/ccompiler.cpython-36.opt-2.pyc","mode":33188,"size":16870,"sha256":"9d9125aeab89954025fff55b909ab27352f46e0c2e242c4430f44513644454f8"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/ccompiler.cpython-36.pyc","mode":33188,"size":33347,"sha256":"28090406daefeb916ed3764dc82fe071e293caaae961bd95e5559b0da3b78ac6"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/cmd.cpython-36.opt-1.pyc","mode":33188,"size":14988,"sha256":"b7d4d7a8e20eb1c7b11ef72058e0caa8231da721a68364747e70b2347bec3867"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/cmd.cpython-36.opt-2.pyc","mode":33188,"size":8991,"sha256":"e3842b6eb8b104b2eb9dc3f5819b25bb9e57b92e68fca7c3774a99b03aef7172"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/cmd.cpython-36.pyc","mode":33188,"size":14988,"sha256":"b7d4d7a8e20eb1c7b11ef72058e0caa8231da721a68364747e70b2347bec3867"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/config.cpython-36.opt-1.pyc","mode":33188,"size":3487,"sha256":"a72e7660c4a6b5445dc388e4e44560a56bcdd693dd0b310df353f6769493deaa"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/config.cpython-36.opt-2.pyc","mode":33188,"size":3095,"sha256":"614505b2ead1cef2cd1594479f29ff6402a3ca4e9e2e55c4d70be513b1f4b09d"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/config.cpython-36.pyc","mode":33188,"size":3487,"sha256":"a72e7660c4a6b5445dc388e4e44560a56bcdd693dd0b310df353f6769493deaa"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/core.cpython-36.opt-1.pyc","mode":33188,"size":6803,"sha256":"d289f33be22969387f6a6c8919f86b4f112207e592e26469efbb09b1d30a59a1"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/core.cpython-36.opt-2.pyc","mode":33188,"size":3416,"sha256":"da3ed0ab1c53a6529567501d2accde65e2bf5f74413c99020150866fe94b3f38"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/core.cpython-36.pyc","mode":33188,"size":6803,"sha256":"d289f33be22969387f6a6c8919f86b4f112207e592e26469efbb09b1d30a59a1"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/cygwinccompiler.cpython-36.opt-1.pyc","mode":33188,"size":8508,"sha256":"0ae4d28133f682be270890e9b9249f8ddad476fddcad6fbef7163193215c06be"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/cygwinccompiler.cpython-36.opt-2.pyc","mode":33188,"size":6878,"sha256":"8952a8a8bce704a130f16077b53f32764bf9ad68fcd1f755d76b149c35b085b4"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/cygwinccompiler.cpython-36.pyc","mode":33188,"size":8508,"sha256":"0ae4d28133f682be270890e9b9249f8ddad476fddcad6fbef7163193215c06be"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/debug.cpython-36.opt-1.pyc","mode":33188,"size":188,"sha256":"f0d27b0fd8f4c20b0c27a51cab2250ee134a904696511f56c729456ee3454ccd"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/debug.cpython-36.opt-2.pyc","mode":33188,"size":188,"sha256":"f0d27b0fd8f4c20b0c27a51cab2250ee134a904696511f56c729456ee3454ccd"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/debug.cpython-36.pyc","mode":33188,"size":188,"sha256":"f0d27b0fd8f4c20b0c27a51cab2250ee134a904696511f56c729456ee3454ccd"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dep_util.cpython-36.opt-1.pyc","mode":33188,"size":2704,"sha256":"0210a0928e8122b503c13aca687c36e4eca6e1beb6ae1769f60dbc9a96b4d927"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dep_util.cpython-36.opt-2.pyc","mode":33188,"size":1260,"sha256":"99bde948b2ae2dc9e9aa6e713ab7f0076196ae843af37ed0ca7c00005a221dca"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dep_util.cpython-36.pyc","mode":33188,"size":2704,"sha256":"0210a0928e8122b503c13aca687c36e4eca6e1beb6ae1769f60dbc9a96b4d927"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dir_util.cpython-36.opt-1.pyc","mode":33188,"size":5804,"sha256":"e29001457dc45836c92c8742e9f9877666d17fbbebd80e4ea4f43a9aff83e6e0"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dir_util.cpython-36.opt-2.pyc","mode":33188,"size":3426,"sha256":"d9a9976bc243d4ad0f51fb3dfed966250a16c05b6abb7ca7a1a5dc0485d60f60"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dir_util.cpython-36.pyc","mode":33188,"size":5804,"sha256":"e29001457dc45836c92c8742e9f9877666d17fbbebd80e4ea4f43a9aff83e6e0"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dist.cpython-36.opt-1.pyc","mode":33188,"size":34213,"sha256":"a1441fe39adf5946a52b9297d5519f8a946c4a61746b887c4d99599fbfb197c8"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dist.cpython-36.opt-2.pyc","mode":33188,"size":24917,"sha256":"807f544f00dd5aaae70f1145e9adff1ddd818289886b4079718910010f92851b"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/dist.cpython-36.pyc","mode":33188,"size":34213,"sha256":"a1441fe39adf5946a52b9297d5519f8a946c4a61746b887c4d99599fbfb197c8"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/errors.cpython-36.opt-1.pyc","mode":33188,"size":5474,"sha256":"a5596537ae13c007516a9e6b3e4888368646d38afaf2863cd54c87441787ce10"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/errors.cpython-36.opt-2.pyc","mode":33188,"size":2836,"sha256":"705e67fd799f43ee68ebfe4f453511f9c26c6e0b3a901017e66623738c282db8"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/errors.cpython-36.pyc","mode":33188,"size":5474,"sha256":"a5596537ae13c007516a9e6b3e4888368646d38afaf2863cd54c87441787ce10"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/extension.cpython-36.opt-1.pyc","mode":33188,"size":6950,"sha256":"babd94e3800dd53d621854e3269fca61d38a44a190fbd7b58243d3e14d50072d"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/extension.cpython-36.opt-2.pyc","mode":33188,"size":3460,"sha256":"ca39bfa3973d2c30c778e49900bf5d21f6d0d85d741fd0c503ac182630d7f6fb"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/extension.cpython-36.pyc","mode":33188,"size":6950,"sha256":"babd94e3800dd53d621854e3269fca61d38a44a190fbd7b58243d3e14d50072d"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/fancy_getopt.cpython-36.opt-1.pyc","mode":33188,"size":10503,"sha256":"bd343279a47e097d0b0c9e139465343f76e7306522bd74bcbd061340dcc5ce98"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/fancy_getopt.cpython-36.opt-2.pyc","mode":33188,"size":7692,"sha256":"acf985d68256e28fcad2aadbff57ff44b666bbf3032f5e7b85d465555f3d29f3"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/fancy_getopt.cpython-36.pyc","mode":33188,"size":10653,"sha256":"7ef334c7b2e2d05361a6046d23fb08010130aaeba2a627583ab1e9c2b23234a3"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/file_util.cpython-36.opt-1.pyc","mode":33188,"size":5897,"sha256":"26cd5305d748a5b1a5a0f046d61ca4eb80778b606d4c0f867768610d1529a536"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/file_util.cpython-36.opt-2.pyc","mode":33188,"size":3760,"sha256":"749d099fa7bf9de1184774ea1cea449aac622d60ce96515ab92c0980c8bfafcf"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/file_util.cpython-36.pyc","mode":33188,"size":5897,"sha256":"26cd5305d748a5b1a5a0f046d61ca4eb80778b606d4c0f867768610d1529a536"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/filelist.cpython-36.opt-1.pyc","mode":33188,"size":9775,"sha256":"5fccb526d9efd92323dee5d5f5298a059f6ddd78a24b9d221c170184ab446c69"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/filelist.cpython-36.opt-2.pyc","mode":33188,"size":6904,"sha256":"10ec344ff4e221336ee9b131e666711d9b6fda6e9e93265bd60769b103ce678c"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/filelist.cpython-36.pyc","mode":33188,"size":9865,"sha256":"6dbcf34c26ab34b58b932c5d2dc7b60f4bc1a50fb308a6279559621c557e1b1e"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/log.cpython-36.opt-1.pyc","mode":33188,"size":2299,"sha256":"7522a67130b76d01b407a937dc05fa1ecd3419f8951a0126c0200e0fc53cb425"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/log.cpython-36.opt-2.pyc","mode":33188,"size":2238,"sha256":"dfb5492e94be163a3e3a8122648cd280209ccbfc6375293a8cbd12fd01a6fad8"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/log.cpython-36.pyc","mode":33188,"size":2299,"sha256":"7522a67130b76d01b407a937dc05fa1ecd3419f8951a0126c0200e0fc53cb425"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/msvc9compiler.cpython-36.opt-1.pyc","mode":33188,"size":17381,"sha256":"fee786e68c8d3c446811e53e3ced971bcc545d06fabf05a94c2d293923b22098"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/msvc9compiler.cpython-36.opt-2.pyc","mode":33188,"size":15764,"sha256":"1d4cf511c8dba6ad8ec832d9934726883132486ff8f045246edb10f42d0e1860"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/msvc9compiler.cpython-36.pyc","mode":33188,"size":17444,"sha256":"cad0dc62ff39e8220e590f663614d8cc65941a695ea4caafe34ff61cb176592d"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/msvccompiler.cpython-36.opt-1.pyc","mode":33188,"size":14568,"sha256":"237345968560983bbd6e207a1548cbed4b0cbbb13807a3b13f50ef286fd593cb"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/msvccompiler.cpython-36.opt-2.pyc","mode":33188,"size":12987,"sha256":"cdddac3b33230f8de4127074ed6d2070bbce06288d39667761ff34b6d115b66d"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/msvccompiler.cpython-36.pyc","mode":33188,"size":14568,"sha256":"237345968560983bbd6e207a1548cbed4b0cbbb13807a3b13f50ef286fd593cb"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/spawn.cpython-36.opt-1.pyc","mode":33188,"size":4993,"sha256":"a00558832e6a845f01a71558d324edb464365512c324ae77aa377fad277298cb"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/spawn.cpython-36.opt-2.pyc","mode":33188,"size":3689,"sha256":"1d9a45040d656bd84a334931775a7a6c30603d46d3310e946b2d264910abf8bd"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/spawn.cpython-36.pyc","mode":33188,"size":4993,"sha256":"a00558832e6a845f01a71558d324edb464365512c324ae77aa377fad277298cb"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/sysconfig.cpython-36.opt-1.pyc","mode":33188,"size":11946,"sha256":"67a21b4e7f0c0d8d33e66a263d19b5fac86528000a5d9f257e106ae37302d411"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/sysconfig.cpython-36.opt-2.pyc","mode":33188,"size":8461,"sha256":"3ad59805152f2870aa78b6c12f249b774e267c3296b67b9a417d51a652b9a088"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/sysconfig.cpython-36.pyc","mode":33188,"size":11946,"sha256":"67a21b4e7f0c0d8d33e66a263d19b5fac86528000a5d9f257e106ae37302d411"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/text_file.cpython-36.opt-1.pyc","mode":33188,"size":8458,"sha256":"7e438e74f9ea0515dc4981a8a155a4783d73b138f86fa06759d4096434af88b4"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/text_file.cpython-36.opt-2.pyc","mode":33188,"size":3356,"sha256":"9744f9944b4b46868fe43899c61f83c9e72ffc24d22ce082135f5befe08ac377"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/text_file.cpython-36.pyc","mode":33188,"size":8458,"sha256":"7e438e74f9ea0515dc4981a8a155a4783d73b138f86fa06759d4096434af88b4"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/unixccompiler.cpython-36.opt-1.pyc","mode":33188,"size":6851,"sha256":"a8e9484fb5b7b842784b9cae73dc68881de5dd02f7cc9f2907ef5fbab66845c1"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/unixccompiler.cpython-36.opt-2.pyc","mode":33188,"size":6222,"sha256":"7f72324196b94c24519758e639e1eb589c747ebd3ff3f174fbf0d1ed19296e00"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/unixccompiler.cpython-36.pyc","mode":33188,"size":6851,"sha256":"a8e9484fb5b7b842784b9cae73dc68881de5dd02f7cc9f2907ef5fbab66845c1"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/util.cpython-36.opt-1.pyc","mode":33188,"size":15523,"sha256":"88691fc034cac1d103158d8c1a4a325e3b1de5050334c976d04fda8d78403b48"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/util.cpython-36.opt-2.pyc","mode":33188,"size":9462,"sha256":"7a4d8e0b57577d95bf7bd31930357c9a92ccdaa665677a30955868af05bb717d"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/util.cpython-36.pyc","mode":33188,"size":15523,"sha256":"4f90b371d05b43ec5dab868f95c04114c39e8bf5c71d375cfb511d6609ca487e"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/version.cpython-36.opt-1.pyc","mode":33188,"size":7309,"sha256":"84e310e2882e876d5546c54251b4be473452bb20436c556b033623f7e85bb26c"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/version.cpython-36.opt-2.pyc","mode":33188,"size":4024,"sha256":"ff40c41696a51bc66ec60e290ff188b4c5b0c575ebbeed382a31c221ef62e25c"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/version.cpython-36.pyc","mode":33188,"size":7354,"sha256":"366d5cc6fa2d360616ac351509af68cf2ed47a733b14f4727705d42ef936a06b"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/versionpredicate.cpython-36.opt-1.pyc","mode":33188,"size":5083,"sha256":"d930e295850e0b9303fb8eb981ba5bb1172e6842a691cdc41c5a7c20cf0617e7"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/versionpredicate.cpython-36.opt-2.pyc","mode":33188,"size":2603,"sha256":"ac0624241eeabb0c7598c45a9fc533ba3aca532deae00dd2484a08a013e0930b"},{"path":"/usr/lib64/python3.6/distutils/__pycache__/versionpredicate.cpython-36.pyc","mode":33188,"size":5083,"sha256":"d930e295850e0b9303fb8eb981ba5bb1172e6842a691cdc41c5a7c20cf0617e7"},{"path":"/usr/lib64/python3.6/distutils/_msvccompiler.py","mode":33188,"size":21579,"sha256":"3c29ae381d343690369cc71482c9259acfc7a2f3e77470b1cfea9542ac3ba984"},{"path":"/usr/lib64/python3.6/distutils/archive_util.py","mode":33188,"size":8518,"sha256":"271685f68d5dd86a2e4d87b27fb48b82c267b09077d3358066e5584998eaf3b9"},{"path":"/usr/lib64/python3.6/distutils/bcppcompiler.py","mode":33188,"size":14935,"sha256":"c086082101989a2d631e7d8c7cd73ee70f4424e7161d37b180de82b05034fcc2"},{"path":"/usr/lib64/python3.6/distutils/ccompiler.py","mode":33188,"size":47415,"sha256":"cc5595f40e1d5fd68c3f1ebf681c9bd1aa859703a3461939b55956a12f77d0e6"},{"path":"/usr/lib64/python3.6/distutils/cmd.py","mode":33188,"size":19129,"sha256":"628a7dfce087cf6219058a464b43a1aeae9f25a2c3483978a3bf7672274f1a2b"},{"path":"/usr/lib64/python3.6/distutils/command/__init__.py","mode":33188,"size":799,"sha256":"d9303eae5343973788f9cb1b5875c58c60fcb8e62a00b31fc963a14f8f670ba8"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":535,"sha256":"f6d6786ab788678af9ab40b98a8dad362e30021e25fe7102ce90a6c8d9278d4c"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":426,"sha256":"2348d54b7c918bc58705ebbd3b32f3ee0176a0af5640d1f3e0956eb1726700c6"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":535,"sha256":"f6d6786ab788678af9ab40b98a8dad362e30021e25fe7102ce90a6c8d9278d4c"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist.cpython-36.opt-1.pyc","mode":33188,"size":3781,"sha256":"6e6f33ac05f9145d0d7e456861cdcccf9493e1cec6258a6b4db56d4005b4b0fe"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist.cpython-36.opt-2.pyc","mode":33188,"size":3587,"sha256":"9f6172a51c6ebbaf93bf121cda78c4f64607ad100867a033ca62e7d019ad3ed4"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist.cpython-36.pyc","mode":33188,"size":3781,"sha256":"6e6f33ac05f9145d0d7e456861cdcccf9493e1cec6258a6b4db56d4005b4b0fe"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_dumb.cpython-36.opt-1.pyc","mode":33188,"size":3743,"sha256":"a241b8e01a5c5b44b3ba4b0ac5467028e5a5faffa0489e263683c25cc4378e3d"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_dumb.cpython-36.opt-2.pyc","mode":33188,"size":3543,"sha256":"e84eef144b57e6315fdd995ed4732e4f6920028efc529502bf32937b9f8287c4"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_dumb.cpython-36.pyc","mode":33188,"size":3743,"sha256":"a241b8e01a5c5b44b3ba4b0ac5467028e5a5faffa0489e263683c25cc4378e3d"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_msi.cpython-36.opt-1.pyc","mode":33188,"size":19679,"sha256":"9b28375d072eb388c57d621ca3ed4afe04455be45ab52c0f312cdcc882d31ecc"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_msi.cpython-36.opt-2.pyc","mode":33188,"size":18138,"sha256":"58d972b48ea531b32d2572f5a1d21a0964950155cfc1af75f067feb095efa616"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_msi.cpython-36.pyc","mode":33188,"size":19767,"sha256":"ec2001cf6f322a8c3ee29347f04b1f3696fbdcf997a5f75d1a8f4fbfe0fcbd3e"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_rpm.cpython-36.opt-1.pyc","mode":33188,"size":13004,"sha256":"1ce7aafeb5627948e77e7fd70198a00cb953710f32a4eb17019172539c97e970"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_rpm.cpython-36.opt-2.pyc","mode":33188,"size":12685,"sha256":"c17197943f28a0499e6750b49e2c70a73fa5028b4de640c4cbd56d130607b5d4"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_rpm.cpython-36.pyc","mode":33188,"size":13070,"sha256":"2692c5699364cecb981a351fb541d5efc899d22845ec75b09944fe08e7cdefbe"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_wininst.cpython-36.opt-1.pyc","mode":33188,"size":8303,"sha256":"bd5780434b9bef6a6b356b0c3cc2543eb52baf5db258352b5d157f1a59a5e066"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_wininst.cpython-36.opt-2.pyc","mode":33188,"size":8164,"sha256":"b75cb9f973cf337244a7fc26324967517dd7294417510064afdc76ba78362687"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/bdist_wininst.cpython-36.pyc","mode":33188,"size":8371,"sha256":"b2c813ad93f6b345f253ae93757a160c97353d39af5d73d7e60fca471cf9dc4a"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build.cpython-36.opt-1.pyc","mode":33188,"size":4065,"sha256":"15cd71e4a085b378469b8832c68f026f2b637707738fad328c88e6e289ba8ec3"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build.cpython-36.opt-2.pyc","mode":33188,"size":3982,"sha256":"d14349d153664302d3bd2d774aab6bc1c59087eb533fcd0a6745135d8f26e25d"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build.cpython-36.pyc","mode":33188,"size":4065,"sha256":"15cd71e4a085b378469b8832c68f026f2b637707738fad328c88e6e289ba8ec3"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_clib.cpython-36.opt-1.pyc","mode":33188,"size":4971,"sha256":"bbcce7895b0a40f894c2cfe1b197632bf412a0f5431d4539f26e54eb15e66ff1"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_clib.cpython-36.opt-2.pyc","mode":33188,"size":4417,"sha256":"75602eb10e5669e5dac45820a9da625f82ddc27be1baada03314133c8a216440"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_clib.cpython-36.pyc","mode":33188,"size":4971,"sha256":"bbcce7895b0a40f894c2cfe1b197632bf412a0f5431d4539f26e54eb15e66ff1"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_ext.cpython-36.opt-1.pyc","mode":33188,"size":16558,"sha256":"783a95bdf7a0fa22b7000a76d4d689f0863a61d2005744c25ea576d9bb6c3933"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_ext.cpython-36.opt-2.pyc","mode":33188,"size":14600,"sha256":"1c16c6cfea2b8b9ce699b34ecdf3ea53c0b18c9a17f4a74d1d9a5935a9ad267f"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_ext.cpython-36.pyc","mode":33188,"size":16558,"sha256":"783a95bdf7a0fa22b7000a76d4d689f0863a61d2005744c25ea576d9bb6c3933"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_py.cpython-36.opt-1.pyc","mode":33188,"size":10459,"sha256":"06ee2cc25eec9e16d30fe0e3e7b07c20f5e0267bc205cbd64477ed4ae10711dc"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_py.cpython-36.opt-2.pyc","mode":33188,"size":9250,"sha256":"05ec1806bb03ac02b00ed7f7f5ffe13b3de381deaf0f5bf854224c4ebeb3ea2a"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_py.cpython-36.pyc","mode":33188,"size":10518,"sha256":"163d1deb251f257770a668ebdcc8365fe6a187dce7e65881e681515b43728ae6"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_scripts.cpython-36.opt-1.pyc","mode":33188,"size":4334,"sha256":"369275babb5ac75e8ad7fb09ce1672d723b4b3c5eb8af4409f9b6a95edc4fc9d"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_scripts.cpython-36.opt-2.pyc","mode":33188,"size":3940,"sha256":"80a6fc3cc1051caa4cd02b3deea3f08077156b383ed8a0658f00c020bbfe7c20"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/build_scripts.cpython-36.pyc","mode":33188,"size":4334,"sha256":"369275babb5ac75e8ad7fb09ce1672d723b4b3c5eb8af4409f9b6a95edc4fc9d"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/check.cpython-36.opt-1.pyc","mode":33188,"size":5225,"sha256":"ec5cbe627ad90b9926b6bc8f2aa7fceeae889b67e78dfb18f0dbba90bbd1fc2a"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/check.cpython-36.opt-2.pyc","mode":33188,"size":4657,"sha256":"d65362e5bc222c637d64511945b219eca41fdcbc54dade45fdcdf74fa930eac4"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/check.cpython-36.pyc","mode":33188,"size":5225,"sha256":"ec5cbe627ad90b9926b6bc8f2aa7fceeae889b67e78dfb18f0dbba90bbd1fc2a"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/clean.cpython-36.opt-1.pyc","mode":33188,"size":2179,"sha256":"c3ede3a4f126038cf1e47e9959722db1d5002435bfda9a04491f11c539cba9fa"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/clean.cpython-36.opt-2.pyc","mode":33188,"size":2096,"sha256":"90cdb2044e3e35895c6542921893e9325bde26da71afdd07ef6a5b5c22845c34"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/clean.cpython-36.pyc","mode":33188,"size":2179,"sha256":"c3ede3a4f126038cf1e47e9959722db1d5002435bfda9a04491f11c539cba9fa"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/config.cpython-36.opt-1.pyc","mode":33188,"size":10314,"sha256":"28e83896dca901903b1e28795ec039ccc4b7361ee2107ae1257d9c83a52a1e2e"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/config.cpython-36.opt-2.pyc","mode":33188,"size":6998,"sha256":"dfdeda16ca847cac7c3cee3064373ac9cf223a068161dfeb400ad5ce38de0e5c"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/config.cpython-36.pyc","mode":33188,"size":10314,"sha256":"28e83896dca901903b1e28795ec039ccc4b7361ee2107ae1257d9c83a52a1e2e"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install.cpython-36.opt-1.pyc","mode":33188,"size":14237,"sha256":"3e5c823e07779176ab34329c7d2a3e145261507831ce5aaaac4a2175bf396cbd"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install.cpython-36.opt-2.pyc","mode":33188,"size":13180,"sha256":"5f6bf4e98f9292cbee1cf717ba92c50a0389f21688213b6336e3b3db7e4a3e12"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install.cpython-36.pyc","mode":33188,"size":14237,"sha256":"3e5c823e07779176ab34329c7d2a3e145261507831ce5aaaac4a2175bf396cbd"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_data.cpython-36.opt-1.pyc","mode":33188,"size":2324,"sha256":"3c76d5d08ca4b1bc85df2c07a93e55bae8a1b6f975bcd839f88a4b7eda677496"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_data.cpython-36.opt-2.pyc","mode":33188,"size":2179,"sha256":"e06b3eb84605bef37c6fa892bae3e1334b8d168608fb97b0f67eae4bfffab4fc"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_data.cpython-36.pyc","mode":33188,"size":2324,"sha256":"3c76d5d08ca4b1bc85df2c07a93e55bae8a1b6f975bcd839f88a4b7eda677496"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_egg_info.cpython-36.opt-1.pyc","mode":33188,"size":2985,"sha256":"951beaa578d4496cb1fc3f92fd8937779b1a41ba0a4f01095c9461b81f24dcb9"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_egg_info.cpython-36.opt-2.pyc","mode":33188,"size":2306,"sha256":"bbfe0c793524b9022397df4f7f17cd9aacdfe1a69c0c386d99b6ad770da85f35"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_egg_info.cpython-36.pyc","mode":33188,"size":2985,"sha256":"951beaa578d4496cb1fc3f92fd8937779b1a41ba0a4f01095c9461b81f24dcb9"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_headers.cpython-36.opt-1.pyc","mode":33188,"size":1724,"sha256":"092d35b3086a3aa6d23ce836fe204e7225386d0d4989bf2bef11f20503d5b2c9"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_headers.cpython-36.opt-2.pyc","mode":33188,"size":1558,"sha256":"9722bfc646b5919fc9749da5ebef07d78365559fcf5dcf7de0a9ee0967090c67"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_headers.cpython-36.pyc","mode":33188,"size":1724,"sha256":"092d35b3086a3aa6d23ce836fe204e7225386d0d4989bf2bef11f20503d5b2c9"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_lib.cpython-36.opt-1.pyc","mode":33188,"size":5176,"sha256":"2b121a5aa777e04fa7b36077ec41e139137da426c4b0efc39418a6ee1e330f3f"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_lib.cpython-36.opt-2.pyc","mode":33188,"size":4603,"sha256":"83492d5b68b80a8ba7053302ce6b0d4c06ea171a14ab2bbe21594b9d48e1d692"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_lib.cpython-36.pyc","mode":33188,"size":5176,"sha256":"2b121a5aa777e04fa7b36077ec41e139137da426c4b0efc39418a6ee1e330f3f"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_scripts.cpython-36.opt-1.pyc","mode":33188,"size":2190,"sha256":"a26fa98e841e7ae341143c923a3236c457e3607bce87dd743c4a6ac35f1104d4"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_scripts.cpython-36.opt-2.pyc","mode":33188,"size":2056,"sha256":"155ecc1dd39c7ed26dcec1474c16732eeeb4d54623089f34098ec002894601a2"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/install_scripts.cpython-36.pyc","mode":33188,"size":2190,"sha256":"a26fa98e841e7ae341143c923a3236c457e3607bce87dd743c4a6ac35f1104d4"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/register.cpython-36.opt-1.pyc","mode":33188,"size":8412,"sha256":"071fa621e0e19b834e83eb7ff13dc111e42dc438fb1c17a57176337eb525ddf0"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/register.cpython-36.opt-2.pyc","mode":33188,"size":7147,"sha256":"665c6fd585bca32dd9a2a0bfc71a1b6e3bd522b35d36dec2c1273b1bb8afdb35"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/register.cpython-36.pyc","mode":33188,"size":8412,"sha256":"071fa621e0e19b834e83eb7ff13dc111e42dc438fb1c17a57176337eb525ddf0"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/sdist.cpython-36.opt-1.pyc","mode":33188,"size":13109,"sha256":"7b6ef53413305c78fc17ffa87c1f9a8f2f7b44431f38a97419b149024e554ad1"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/sdist.cpython-36.opt-2.pyc","mode":33188,"size":9922,"sha256":"139de865d32471cc0c8a9b2ce07ebbeed75a332cd3b018630095ddccc6b47acf"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/sdist.cpython-36.pyc","mode":33188,"size":13109,"sha256":"7b6ef53413305c78fc17ffa87c1f9a8f2f7b44431f38a97419b149024e554ad1"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/upload.cpython-36.opt-1.pyc","mode":33188,"size":5293,"sha256":"936a7465eb4f1e5699742b63a264d667cc142c69a4760c462c944201752bbe8f"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/upload.cpython-36.opt-2.pyc","mode":33188,"size":5167,"sha256":"0fa34d8a6920aa55342116ac678a1a321f5dcb2a02697a4a3a23805c17c8f1ab"},{"path":"/usr/lib64/python3.6/distutils/command/__pycache__/upload.cpython-36.pyc","mode":33188,"size":5293,"sha256":"936a7465eb4f1e5699742b63a264d667cc142c69a4760c462c944201752bbe8f"},{"path":"/usr/lib64/python3.6/distutils/command/bdist.py","mode":33188,"size":5562,"sha256":"db3e1eb9d465fe7ee6de51bd95e2f4218a9eb386ec9bc7347f17d9ba269f8cc8"},{"path":"/usr/lib64/python3.6/distutils/command/bdist_dumb.py","mode":33188,"size":4913,"sha256":"053babf63708a69c8fecf89abe37ec93b623125aafc5e60eda7a54c8f3ce7a47"},{"path":"/usr/lib64/python3.6/distutils/command/bdist_msi.py","mode":33188,"size":35233,"sha256":"e556f496b600b3247186209d966e5313671eee17e5f6ec5eacb97e6b21fd083a"},{"path":"/usr/lib64/python3.6/distutils/command/bdist_rpm.py","mode":33188,"size":21671,"sha256":"27088277103866d6cb6eff58368385c64f2f22a6e5d8d93230df2178ea66a62e"},{"path":"/usr/lib64/python3.6/distutils/command/bdist_wininst.py","mode":33188,"size":15560,"sha256":"7f83b54409b82154a715ebb09450cc24794300fa6851d9edde6b32c50f739732"},{"path":"/usr/lib64/python3.6/distutils/command/build.py","mode":33188,"size":5748,"sha256":"bd834b44e54db72e3357404c1835ac1767fb9bce1cb112482649a961adf58d87"},{"path":"/usr/lib64/python3.6/distutils/command/build_clib.py","mode":33188,"size":8022,"sha256":"6e05531e1dbc78b400d86930ebc6a602977f8fba90057e0c4c8fb34ef00afc9e"},{"path":"/usr/lib64/python3.6/distutils/command/build_ext.py","mode":33188,"size":31486,"sha256":"01bf18ac03772f1188832b0e6e5c853336f44784c8e125c8cf77208cb70c0113"},{"path":"/usr/lib64/python3.6/distutils/command/build_py.py","mode":33188,"size":17164,"sha256":"9198159d5de5bcf1621301d548ab1168a78574b67b7c334d2621ee4d1d19a6d7"},{"path":"/usr/lib64/python3.6/distutils/command/build_scripts.py","mode":33188,"size":6232,"sha256":"68ac9c2493f1dcb7d9d5cbd981225ac670f62e7bd1339589fbcc64a5d81c2ec2"},{"path":"/usr/lib64/python3.6/distutils/command/check.py","mode":33188,"size":5496,"sha256":"62ff4b331d77020b7e0ccaf5d8fb96fb164216a00db36f484578c5df948dd1e4"},{"path":"/usr/lib64/python3.6/distutils/command/clean.py","mode":33188,"size":2776,"sha256":"d930ade3baeee2165933445f55f5188f96dba6272918b3f8421c398c1b6fa7d9"},{"path":"/usr/lib64/python3.6/distutils/command/command_template","mode":33188,"size":633,"sha256":"7c1c707cd6ad3872515cf3fc9d8dd1a3f7cc08e3eb71813ed427499b256a8751"},{"path":"/usr/lib64/python3.6/distutils/command/config.py","mode":33188,"size":13086,"sha256":"5e39704e9e173b6fa81f646990a29f3051cecb1cc98e02b029cf57b0d5aa6642"},{"path":"/usr/lib64/python3.6/distutils/command/install.py","mode":33188,"size":27271,"sha256":"24400336e7448526a8bd0c99c43aa210cb61cd7480b1e133d93754adc657ea5f"},{"path":"/usr/lib64/python3.6/distutils/command/install_data.py","mode":33188,"size":2822,"sha256":"62118e0308778093ea17b7a6e57034ae6a51e36cf56cb87cd28a049730f252f9"},{"path":"/usr/lib64/python3.6/distutils/command/install_egg_info.py","mode":33188,"size":2603,"sha256":"d245b496254c79a7648d7d197117cca6d2857a7d3b1b0ea0cb0d551d3e4a2307"},{"path":"/usr/lib64/python3.6/distutils/command/install_headers.py","mode":33188,"size":1298,"sha256":"5d0ea27646c80dfaf59635c23b39ee55432f385a47067e9c2b45b3f6020cd9be"},{"path":"/usr/lib64/python3.6/distutils/command/install_lib.py","mode":33188,"size":8397,"sha256":"f40a1f47e30ef6502d8f0c2eba40a9b5ea4e68910a3195b65478b2479854ec70"},{"path":"/usr/lib64/python3.6/distutils/command/install_scripts.py","mode":33188,"size":2017,"sha256":"fc22d4790c06251718da48a4edaccf327e4876d0c2ae359d52f675921946e9c9"},{"path":"/usr/lib64/python3.6/distutils/command/register.py","mode":33188,"size":11712,"sha256":"da36aaf7debcaedda9b91543071d476cd897bf6eee3a4f22744ff894f7ffdd53"},{"path":"/usr/lib64/python3.6/distutils/command/sdist.py","mode":33188,"size":17826,"sha256":"045c17be9555b3c07f07af2f740645c8ce53bed1dbd386d485490926b651e94b"},{"path":"/usr/lib64/python3.6/distutils/command/upload.py","mode":33188,"size":7671,"sha256":"2c7eab9f5695ead0cb2b27a54e1671ecb1eaf4316def4862e3132ba9c7bdf4d0"},{"path":"/usr/lib64/python3.6/distutils/config.py","mode":33188,"size":4880,"sha256":"5f9fc724465879be474505c7b32b53cefdb08c93c5509162866af919b2c77f08"},{"path":"/usr/lib64/python3.6/distutils/core.py","mode":33188,"size":8876,"sha256":"8db74e92938ad3dc62fb9eaf861c2f9f77d87612dbe4324ef2adcad5f9d0cf44"},{"path":"/usr/lib64/python3.6/distutils/cygwinccompiler.py","mode":33188,"size":16475,"sha256":"124163dd246c65c3b1d1d12abd99bd7173148d125f4191f2d68199728475c0b4"},{"path":"/usr/lib64/python3.6/distutils/debug.py","mode":33188,"size":139,"sha256":"37a32b4c0a8aea5f52564ead5b0791d74f0f33c3a5eea3657f257e9c770b86c6"},{"path":"/usr/lib64/python3.6/distutils/dep_util.py","mode":33188,"size":3491,"sha256":"1ae47d230fe3cd9464c9e989e475fcac1ff0446c642017019b5aa1e78afbce19"},{"path":"/usr/lib64/python3.6/distutils/dir_util.py","mode":33188,"size":7778,"sha256":"5308413944dc57ae464f071ee123ee4d747c67cab72d811c9adb6a7066f46d8a"},{"path":"/usr/lib64/python3.6/distutils/dist.py","mode":33188,"size":49690,"sha256":"05dfc78f8ac34fcdcbe7c61baea225d7ce9fbc0dff5c94b19c3fce0c7e0c3cee"},{"path":"/usr/lib64/python3.6/distutils/errors.py","mode":33188,"size":3577,"sha256":"62bead29919dcc1a0d8b9def06d8aad1427ffd7d390a6c5275026a3966b0e926"},{"path":"/usr/lib64/python3.6/distutils/extension.py","mode":33188,"size":10515,"sha256":"6d36f74340a87af18a62fe5d5f596cfbe2e7f2d941d3e5043ac8bd070ce567eb"},{"path":"/usr/lib64/python3.6/distutils/fancy_getopt.py","mode":33188,"size":17784,"sha256":"38fc69d82c478b5629fddd43f09c56e147aaf5f0bbd6d7a040569a7e1e7c1865"},{"path":"/usr/lib64/python3.6/distutils/file_util.py","mode":33188,"size":8148,"sha256":"d2152a7c8b4dff1d83562851d0c1dd03828231508e3bc568072685a7f6ba3038"},{"path":"/usr/lib64/python3.6/distutils/filelist.py","mode":33188,"size":12832,"sha256":"f1b471873a7616c6a81d3ed3b8a0f842372e87f07d3b0ff14edfe1b5926f3764"},{"path":"/usr/lib64/python3.6/distutils/log.py","mode":33188,"size":1969,"sha256":"8560667540b62bddbb41c56fdd110c5b71cc3dc97171c3d09e0c4b4ae517425d"},{"path":"/usr/lib64/python3.6/distutils/msvc9compiler.py","mode":33188,"size":30612,"sha256":"1a41326806de0869ed0b49c67b67dc885f23efb9c38eee309c44c46ddb805be1"},{"path":"/usr/lib64/python3.6/distutils/msvccompiler.py","mode":33188,"size":23576,"sha256":"54143f78adc11b1c839112624776a6bd9a1a82c57792498eb005575f3d58a480"},{"path":"/usr/lib64/python3.6/distutils/spawn.py","mode":33188,"size":7427,"sha256":"754f393f757f23175557642f4dde08030ce348ad127be7b4062a670b76051e2a"},{"path":"/usr/lib64/python3.6/distutils/sysconfig.py","mode":33188,"size":20276,"sha256":"4aa971ebd99f09d64dd3acdc6db654a252913e96bbe008e70992683c76d839e4"},{"path":"/usr/lib64/python3.6/distutils/text_file.py","mode":33188,"size":12483,"sha256":"3ecb8025e59d289a0b495ffa37a229079fb43daf382b32d4b9c24c1516b3c372"},{"path":"/usr/lib64/python3.6/distutils/unixccompiler.py","mode":33188,"size":14984,"sha256":"e0c1e3d2249780ddf0160b334e1b1fe548f8f1ea9524917b417bb33c2de0894e"},{"path":"/usr/lib64/python3.6/distutils/util.py","mode":33188,"size":20789,"sha256":"adf97e817fa2a53479dbd2dbe5738f9cbf85d85d232ee6689aa638cda09c547e"},{"path":"/usr/lib64/python3.6/distutils/version.py","mode":33188,"size":12345,"sha256":"2f35b834b27fa7d0b61bec6550e1a16133f6482b1431875ee93acbce4118987f"},{"path":"/usr/lib64/python3.6/distutils/versionpredicate.py","mode":33188,"size":5133,"sha256":"671a4403e4d0bfcf2651673a85eb543b8a92a80dac6bb8a98d9dd010ae5ebc39"},{"path":"/usr/lib64/python3.6/doctest.py","mode":33188,"size":104391,"sha256":"6ebaa1a027690f38aedc109284a95fcd58268f042b215f7e4d66d5163ac9e7fe"},{"path":"/usr/lib64/python3.6/dummy_threading.py","mode":33188,"size":2815,"sha256":"73abb5d5b4fd70329da6acc0f18df055c2cbb677228f9fab78172e9162cff243"},{"path":"/usr/lib64/python3.6/email/__init__.py","mode":33188,"size":1766,"sha256":"14eeb17ae40c6cc19b48a9bd5e2a0340ee3dd86a8d64bd1d5c4df8fcfa726c8a"},{"path":"/usr/lib64/python3.6/email/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":1671,"sha256":"4bcc17d53100b9f210a8225adf890eedec926634a10861300726e65bd4c72ab9"},{"path":"/usr/lib64/python3.6/email/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":1062,"sha256":"8aabeea0b8b24990e0b09d2cf18c974dbc651baa217d5199c8eb3587cd2c42d6"},{"path":"/usr/lib64/python3.6/email/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":1671,"sha256":"4bcc17d53100b9f210a8225adf890eedec926634a10861300726e65bd4c72ab9"},{"path":"/usr/lib64/python3.6/email/__pycache__/_encoded_words.cpython-36.opt-1.pyc","mode":33188,"size":5586,"sha256":"7726e897d0af300cec62e2a199a9a19eac2c6bb75e6300b3d0687ba7cfd9e740"},{"path":"/usr/lib64/python3.6/email/__pycache__/_encoded_words.cpython-36.opt-2.pyc","mode":33188,"size":3700,"sha256":"f3a0b9356dabc1e1ed2d3fb8607c4cfc183e21bb51afdc5ec56ff0c4a64950e0"},{"path":"/usr/lib64/python3.6/email/__pycache__/_encoded_words.cpython-36.pyc","mode":33188,"size":5586,"sha256":"7726e897d0af300cec62e2a199a9a19eac2c6bb75e6300b3d0687ba7cfd9e740"},{"path":"/usr/lib64/python3.6/email/__pycache__/_header_value_parser.cpython-36.opt-1.pyc","mode":33188,"size":75995,"sha256":"bc76e65aba9e5e7bb75a1933035ba7d1b67ec25e46b0f5438d6aa36c4a2af508"},{"path":"/usr/lib64/python3.6/email/__pycache__/_header_value_parser.cpython-36.opt-2.pyc","mode":33188,"size":59504,"sha256":"15ff1825508203c671bd5574dbd518f41de1dc43b3127aec93dca98d81e45de1"},{"path":"/usr/lib64/python3.6/email/__pycache__/_header_value_parser.cpython-36.pyc","mode":33188,"size":76047,"sha256":"502958c3d0b0358937a2507edf42b8a9d35f597f5ffb01fd9aed9da3bf60c6dc"},{"path":"/usr/lib64/python3.6/email/__pycache__/_parseaddr.cpython-36.opt-1.pyc","mode":33188,"size":12499,"sha256":"5f431a43c94b522b74bb2cfdffbcfa97850de6f819d2afa878d5b53f7eab4f75"},{"path":"/usr/lib64/python3.6/email/__pycache__/_parseaddr.cpython-36.opt-2.pyc","mode":33188,"size":9539,"sha256":"c787a7ad1cb2d7bb8e255c6dbc3404eea5592d53c41fa91072be0c071235307c"},{"path":"/usr/lib64/python3.6/email/__pycache__/_parseaddr.cpython-36.pyc","mode":33188,"size":12499,"sha256":"5f431a43c94b522b74bb2cfdffbcfa97850de6f819d2afa878d5b53f7eab4f75"},{"path":"/usr/lib64/python3.6/email/__pycache__/_policybase.cpython-36.opt-1.pyc","mode":33188,"size":14830,"sha256":"35566d3ca65befb602efe227c8ed1fd1e4b0026f867df3a066a1aef1b6a60c0d"},{"path":"/usr/lib64/python3.6/email/__pycache__/_policybase.cpython-36.opt-2.pyc","mode":33188,"size":5983,"sha256":"90d55e045e4592c156636d2b689c6113236010824dadfdaa16ad63e342e6bc1c"},{"path":"/usr/lib64/python3.6/email/__pycache__/_policybase.cpython-36.pyc","mode":33188,"size":14830,"sha256":"35566d3ca65befb602efe227c8ed1fd1e4b0026f867df3a066a1aef1b6a60c0d"},{"path":"/usr/lib64/python3.6/email/__pycache__/base64mime.cpython-36.opt-1.pyc","mode":33188,"size":3220,"sha256":"b7e0d2bb5ee0ad0da45a21207add55b873c9978755d2e267d744d28178c47aa0"},{"path":"/usr/lib64/python3.6/email/__pycache__/base64mime.cpython-36.opt-2.pyc","mode":33188,"size":1443,"sha256":"8a8ccad6c31d3c7876176ecdce1ae10375bd374c5faf9a891dd2948484a48114"},{"path":"/usr/lib64/python3.6/email/__pycache__/base64mime.cpython-36.pyc","mode":33188,"size":3220,"sha256":"b7e0d2bb5ee0ad0da45a21207add55b873c9978755d2e267d744d28178c47aa0"},{"path":"/usr/lib64/python3.6/email/__pycache__/charset.cpython-36.opt-1.pyc","mode":33188,"size":11476,"sha256":"9aa615fbfea457f17ff157f7f8280bef6a8844d2859a7e4d180c67728f9e60f2"},{"path":"/usr/lib64/python3.6/email/__pycache__/charset.cpython-36.opt-2.pyc","mode":33188,"size":5141,"sha256":"7fca82c768c7e2853160dd86d1ca6fee0e425dcdf97fa8b40fd4be3865e98414"},{"path":"/usr/lib64/python3.6/email/__pycache__/charset.cpython-36.pyc","mode":33188,"size":11513,"sha256":"8ef79f57727458136a753484be53e5c548a9f419e016c0e15f62af3c4b722a02"},{"path":"/usr/lib64/python3.6/email/__pycache__/contentmanager.cpython-36.opt-1.pyc","mode":33188,"size":7290,"sha256":"eca9c0b58dfacaca681911ea163229b61407ed2c60f0252c9482e9a34e4f6cb8"},{"path":"/usr/lib64/python3.6/email/__pycache__/contentmanager.cpython-36.opt-2.pyc","mode":33188,"size":7290,"sha256":"eca9c0b58dfacaca681911ea163229b61407ed2c60f0252c9482e9a34e4f6cb8"},{"path":"/usr/lib64/python3.6/email/__pycache__/contentmanager.cpython-36.pyc","mode":33188,"size":7290,"sha256":"eca9c0b58dfacaca681911ea163229b61407ed2c60f0252c9482e9a34e4f6cb8"},{"path":"/usr/lib64/python3.6/email/__pycache__/encoders.cpython-36.opt-1.pyc","mode":33188,"size":1642,"sha256":"0881b7467e5974a4342331df2dfd17f9d59e0d91682a713d0ac99a39244fa730"},{"path":"/usr/lib64/python3.6/email/__pycache__/encoders.cpython-36.opt-2.pyc","mode":33188,"size":1291,"sha256":"bba4bd20ef7b0225c4afb5987cec7e8e670bf7917f8de7365efa54bbb07ba751"},{"path":"/usr/lib64/python3.6/email/__pycache__/encoders.cpython-36.pyc","mode":33188,"size":1642,"sha256":"0881b7467e5974a4342331df2dfd17f9d59e0d91682a713d0ac99a39244fa730"},{"path":"/usr/lib64/python3.6/email/__pycache__/errors.cpython-36.opt-1.pyc","mode":33188,"size":6171,"sha256":"316586a7176ef4345f8f67fd41a26d7bd6c939d933ba7dfceac2c5003fa268fa"},{"path":"/usr/lib64/python3.6/email/__pycache__/errors.cpython-36.opt-2.pyc","mode":33188,"size":4629,"sha256":"df7bb1b593beef039c85adc3b4119ea2942f0806f87000a5f639c0a31f43f513"},{"path":"/usr/lib64/python3.6/email/__pycache__/errors.cpython-36.pyc","mode":33188,"size":6171,"sha256":"316586a7176ef4345f8f67fd41a26d7bd6c939d933ba7dfceac2c5003fa268fa"},{"path":"/usr/lib64/python3.6/email/__pycache__/feedparser.cpython-36.opt-1.pyc","mode":33188,"size":10492,"sha256":"85547a4830bb969090b61c34220a7ec4fe0353cd91494be3b0d5b158904f0d50"},{"path":"/usr/lib64/python3.6/email/__pycache__/feedparser.cpython-36.opt-2.pyc","mode":33188,"size":8827,"sha256":"d714f430eb7e60367518fe73db2ff26672424030892e8e2cdd16e50c107a30c2"},{"path":"/usr/lib64/python3.6/email/__pycache__/feedparser.cpython-36.pyc","mode":33188,"size":10646,"sha256":"49d7fddf8096520baa5cb415a21f659dceb3a5ddecf27949cf70492c2f2087ac"},{"path":"/usr/lib64/python3.6/email/__pycache__/generator.cpython-36.opt-1.pyc","mode":33188,"size":12515,"sha256":"a3da870f581db28d5b4b419eb2cebc338891464e4125376a01cc7daab0da590c"},{"path":"/usr/lib64/python3.6/email/__pycache__/generator.cpython-36.opt-2.pyc","mode":33188,"size":8819,"sha256":"8e6f3ebebb079fb0ecc985dd89a10fdabb3d93e0d78a099f95aab98fe452fcd4"},{"path":"/usr/lib64/python3.6/email/__pycache__/generator.cpython-36.pyc","mode":33188,"size":12515,"sha256":"a3da870f581db28d5b4b419eb2cebc338891464e4125376a01cc7daab0da590c"},{"path":"/usr/lib64/python3.6/email/__pycache__/header.cpython-36.opt-1.pyc","mode":33188,"size":16482,"sha256":"a191cd09c217341bc7c73adb9612965b69737ec7c62bd0a535fad06422c561d5"},{"path":"/usr/lib64/python3.6/email/__pycache__/header.cpython-36.opt-2.pyc","mode":33188,"size":10858,"sha256":"6c59fa82a1bacc5bb36c437d592f053507bcf6cbb0e420513be7c76b93002ac1"},{"path":"/usr/lib64/python3.6/email/__pycache__/header.cpython-36.pyc","mode":33188,"size":16482,"sha256":"a191cd09c217341bc7c73adb9612965b69737ec7c62bd0a535fad06422c561d5"},{"path":"/usr/lib64/python3.6/email/__pycache__/headerregistry.cpython-36.opt-1.pyc","mode":33188,"size":21224,"sha256":"e26a1c1a9317aab35764f427bc4fedf0d7f127ca789558a0a7e2f4b90690f78b"},{"path":"/usr/lib64/python3.6/email/__pycache__/headerregistry.cpython-36.opt-2.pyc","mode":33188,"size":15453,"sha256":"422c9d9f1cc7f115b794c237af88cc1adbd4a914e7dc7b534e0fef4966bcc6ba"},{"path":"/usr/lib64/python3.6/email/__pycache__/headerregistry.cpython-36.pyc","mode":33188,"size":21280,"sha256":"cad2071a67e70c43eb9cf00f603afba4637008f366adb6ecb52f0f9e1549fb11"},{"path":"/usr/lib64/python3.6/email/__pycache__/iterators.cpython-36.opt-1.pyc","mode":33188,"size":1912,"sha256":"9992153f52579fad43fa3bb352717a443a03979505325e05e7ad0a8e361bd4e6"},{"path":"/usr/lib64/python3.6/email/__pycache__/iterators.cpython-36.opt-2.pyc","mode":33188,"size":1290,"sha256":"c5301217a3f67f26ca1241473c05778a073b0b1edd053f1366565c438788350b"},{"path":"/usr/lib64/python3.6/email/__pycache__/iterators.cpython-36.pyc","mode":33188,"size":1912,"sha256":"9992153f52579fad43fa3bb352717a443a03979505325e05e7ad0a8e361bd4e6"},{"path":"/usr/lib64/python3.6/email/__pycache__/message.cpython-36.opt-1.pyc","mode":33188,"size":37994,"sha256":"958518d248c712651faab63d58daf949431fdfa96b8e0262c92ea70c126c67c3"},{"path":"/usr/lib64/python3.6/email/__pycache__/message.cpython-36.opt-2.pyc","mode":33188,"size":21402,"sha256":"a2668cce840b04faddc201943a3cf99d5185ff8abbbf818006bc6587cd70c82f"},{"path":"/usr/lib64/python3.6/email/__pycache__/message.cpython-36.pyc","mode":33188,"size":37994,"sha256":"958518d248c712651faab63d58daf949431fdfa96b8e0262c92ea70c126c67c3"},{"path":"/usr/lib64/python3.6/email/__pycache__/parser.cpython-36.opt-1.pyc","mode":33188,"size":5727,"sha256":"661b8317ebf67c7a72b182cf331e2020b0f9241a54be48596587f1b578ce263c"},{"path":"/usr/lib64/python3.6/email/__pycache__/parser.cpython-36.opt-2.pyc","mode":33188,"size":2707,"sha256":"f8bc83f4b65d151c76b414b1e9d1bb12971634b7cf49547604ee504de2f9215f"},{"path":"/usr/lib64/python3.6/email/__pycache__/parser.cpython-36.pyc","mode":33188,"size":5727,"sha256":"661b8317ebf67c7a72b182cf331e2020b0f9241a54be48596587f1b578ce263c"},{"path":"/usr/lib64/python3.6/email/__pycache__/policy.cpython-36.opt-1.pyc","mode":33188,"size":9620,"sha256":"90f44577c0440f574a94a0dfe48caa61a364e45fa33700bb011be32320ea9d13"},{"path":"/usr/lib64/python3.6/email/__pycache__/policy.cpython-36.opt-2.pyc","mode":33188,"size":3403,"sha256":"af7e9e5e6e48f56a3f7b43d715b3ba597596598d20fe66ae6741f33234457815"},{"path":"/usr/lib64/python3.6/email/__pycache__/policy.cpython-36.pyc","mode":33188,"size":9620,"sha256":"90f44577c0440f574a94a0dfe48caa61a364e45fa33700bb011be32320ea9d13"},{"path":"/usr/lib64/python3.6/email/__pycache__/quoprimime.cpython-36.opt-1.pyc","mode":33188,"size":7682,"sha256":"7be852af3c389894bf81ac07a60146c9c6c2dc2fad9c7c9ce51e4df86e95f8ee"},{"path":"/usr/lib64/python3.6/email/__pycache__/quoprimime.cpython-36.opt-2.pyc","mode":33188,"size":4205,"sha256":"1690bbe7cc33084b47c6e5d843ba1e8cbb750a8719febeec70735c0d1b214e13"},{"path":"/usr/lib64/python3.6/email/__pycache__/quoprimime.cpython-36.pyc","mode":33188,"size":7682,"sha256":"7be852af3c389894bf81ac07a60146c9c6c2dc2fad9c7c9ce51e4df86e95f8ee"},{"path":"/usr/lib64/python3.6/email/__pycache__/utils.cpython-36.opt-1.pyc","mode":33188,"size":9876,"sha256":"d4c75a14eca2cc6591205d6b3cc7d54817ff726445dba5a2aef0541311f427c2"},{"path":"/usr/lib64/python3.6/email/__pycache__/utils.cpython-36.opt-2.pyc","mode":33188,"size":6547,"sha256":"57b32c58e8232dc1caaef80d60e38b11834d74692a341a60455d0de6983f3ef5"},{"path":"/usr/lib64/python3.6/email/__pycache__/utils.cpython-36.pyc","mode":33188,"size":9876,"sha256":"d4c75a14eca2cc6591205d6b3cc7d54817ff726445dba5a2aef0541311f427c2"},{"path":"/usr/lib64/python3.6/email/_encoded_words.py","mode":33188,"size":8518,"sha256":"4a897f2e5aca1a0d0966a43d56ed4c84be447f0f2f4ff49696f4add6d82b8a19"},{"path":"/usr/lib64/python3.6/email/_header_value_parser.py","mode":33188,"size":99848,"sha256":"19a18e836b5d8942459da077de628021d00fa45a508e6cb21e2e8a7e95fe4a3b"},{"path":"/usr/lib64/python3.6/email/_parseaddr.py","mode":33188,"size":17604,"sha256":"4ddb953e2b35969fc9d86285a13ed7fdd09c607c306aa5c781d535f4847975f7"},{"path":"/usr/lib64/python3.6/email/_policybase.py","mode":33188,"size":15073,"sha256":"967a41672b54f3443eac096968ad189d75c77be7eb42611b4d81d12a41605be9"},{"path":"/usr/lib64/python3.6/email/base64mime.py","mode":33188,"size":3558,"sha256":"1a1bd2d536c77b735892ddf4c6cc6c741184d93c58c11e8f191b5ea29beb753a"},{"path":"/usr/lib64/python3.6/email/charset.py","mode":33188,"size":17151,"sha256":"c26d64eac3a675fa035d831851c93624a73490739246c091e5e44101370b4065"},{"path":"/usr/lib64/python3.6/email/contentmanager.py","mode":33188,"size":10672,"sha256":"05b0a6b7f92969dde00b9bc492d3abc3ed6f63647f8a556561e420d60b5290b5"},{"path":"/usr/lib64/python3.6/email/encoders.py","mode":33188,"size":1786,"sha256":"1e05b3ee30c62c605077e7770b5b3249f5060d968b0fee8d5cf9cad9450b89cd"},{"path":"/usr/lib64/python3.6/email/errors.py","mode":33188,"size":3647,"sha256":"0cb3199868ed5b0a5b0a3bdc8434f99e0b6fef1296f7ed05263397092fce3ad7"},{"path":"/usr/lib64/python3.6/email/feedparser.py","mode":33188,"size":22775,"sha256":"428f21a0ca2817b8b733f3e5074dbdcce3b3b687ee83d0cbc1361fc122c09780"},{"path":"/usr/lib64/python3.6/email/generator.py","mode":33188,"size":19975,"sha256":"829d2918c382d14cec063f9ecb582c97caeab5ad8da0bdb288050549a9c2b109"},{"path":"/usr/lib64/python3.6/email/header.py","mode":33188,"size":24102,"sha256":"304c8c0ec80022672f44343677f034a8a356bf8021156bf88d70fbec8adc0761"},{"path":"/usr/lib64/python3.6/email/headerregistry.py","mode":33188,"size":20227,"sha256":"74bc853507aa2a45312adeb94983dabca92a84d6ac04c4e0beefaaf84c5f1237"},{"path":"/usr/lib64/python3.6/email/iterators.py","mode":33188,"size":2135,"sha256":"7ebca15c9f5889b9551727303666a7bd80c5e4ebdf6bc7ec4d0c46938a1378e1"},{"path":"/usr/lib64/python3.6/email/message.py","mode":33188,"size":46719,"sha256":"e4ae2da9fbc7e42d7333235873b4f82ff15e25f16b5ad62c3896d38fe6c9cd99"},{"path":"/usr/lib64/python3.6/email/mime/__init__.py","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":126,"sha256":"919f960d2cf159ff07b7b2d16823eff90e52bcaf50e4b83fe4757f6d327e4a83"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":126,"sha256":"919f960d2cf159ff07b7b2d16823eff90e52bcaf50e4b83fe4757f6d327e4a83"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":126,"sha256":"919f960d2cf159ff07b7b2d16823eff90e52bcaf50e4b83fe4757f6d327e4a83"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/application.cpython-36.opt-1.pyc","mode":33188,"size":1437,"sha256":"4453d823cebaf915ea8bc1e48b448862c34171edb39687b7bba31e5253c4bf42"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/application.cpython-36.opt-2.pyc","mode":33188,"size":783,"sha256":"ed845ae381dbf16a73e76ff37c3f5d9d2e0b8b4f32c1b74bb2de6f1aba24647a"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/application.cpython-36.pyc","mode":33188,"size":1437,"sha256":"4453d823cebaf915ea8bc1e48b448862c34171edb39687b7bba31e5253c4bf42"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/audio.cpython-36.opt-1.pyc","mode":33188,"size":2596,"sha256":"b6c85f804735fba5db866044a5ba59a97553e982a0269bcea1c8759eee11541f"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/audio.cpython-36.opt-2.pyc","mode":33188,"size":1156,"sha256":"dcea78b60a0c53413ff28ed3b671a4c4a376df377edf78f5a9fbf2f18c7a75f5"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/audio.cpython-36.pyc","mode":33188,"size":2596,"sha256":"b6c85f804735fba5db866044a5ba59a97553e982a0269bcea1c8759eee11541f"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/base.cpython-36.opt-1.pyc","mode":33188,"size":1062,"sha256":"e510d5513cdf3870490befb70a075bedc3ac22e04b4c70f6cb37258077f21199"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/base.cpython-36.opt-2.pyc","mode":33188,"size":705,"sha256":"aea0393685ad2799db748a04f5c23730c95a687368772ac06f39cdb5502bea81"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/base.cpython-36.pyc","mode":33188,"size":1062,"sha256":"e510d5513cdf3870490befb70a075bedc3ac22e04b4c70f6cb37258077f21199"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/image.cpython-36.opt-1.pyc","mode":33188,"size":1882,"sha256":"f49a866cc267b405ebeecf43115a3b7e7b0041767bb39735c08a9d1f47a5a655"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/image.cpython-36.opt-2.pyc","mode":33188,"size":805,"sha256":"eca452f25a77cbd9f95dac78a262e9ebcf56a6f8135e5ad73d2d9d4e77113ce1"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/image.cpython-36.pyc","mode":33188,"size":1882,"sha256":"f49a866cc267b405ebeecf43115a3b7e7b0041767bb39735c08a9d1f47a5a655"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/message.cpython-36.opt-1.pyc","mode":33188,"size":1311,"sha256":"fe71c3ab2c1ddc7ef4d77ef83d72ca02b784dc105aedbadfbf5fae0cee512169"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/message.cpython-36.opt-2.pyc","mode":33188,"size":778,"sha256":"37b5ee5bb35f401b4135f5398f4e115c2c8ad2794e5db7f7d505e0656a4c5c75"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/message.cpython-36.pyc","mode":33188,"size":1311,"sha256":"fe71c3ab2c1ddc7ef4d77ef83d72ca02b784dc105aedbadfbf5fae0cee512169"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/multipart.cpython-36.opt-1.pyc","mode":33188,"size":1533,"sha256":"90635fe65825d34bfa7180e8ff67d768cfd2b27bf06ca7c47347fcfb2e8ed295"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/multipart.cpython-36.opt-2.pyc","mode":33188,"size":694,"sha256":"a1c16d52890009ea822a23a1c978c9bd400afd4f6948a751878ef6dd395ae634"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/multipart.cpython-36.pyc","mode":33188,"size":1533,"sha256":"90635fe65825d34bfa7180e8ff67d768cfd2b27bf06ca7c47347fcfb2e8ed295"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/nonmultipart.cpython-36.opt-1.pyc","mode":33188,"size":748,"sha256":"eb810c387cf8e50305fb3bb58433cfc263ab84703ecf59d14f934da2b48d05a7"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/nonmultipart.cpython-36.opt-2.pyc","mode":33188,"size":613,"sha256":"2664e8d0efbcb19010b7e0319de5cc08e1f13c2635b0c315677abef876fd6128"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/nonmultipart.cpython-36.pyc","mode":33188,"size":748,"sha256":"eb810c387cf8e50305fb3bb58433cfc263ab84703ecf59d14f934da2b48d05a7"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/text.cpython-36.opt-1.pyc","mode":33188,"size":1295,"sha256":"82ad0dac3293a5c23fe13c80ac3d1dd743cd2993388c0e889485fc0a193b683a"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/text.cpython-36.opt-2.pyc","mode":33188,"size":784,"sha256":"6ca45db9c46d0eac07a7cf246b0d7d8f59b9711c4ead1ff6aefdd7016700a95a"},{"path":"/usr/lib64/python3.6/email/mime/__pycache__/text.cpython-36.pyc","mode":33188,"size":1295,"sha256":"82ad0dac3293a5c23fe13c80ac3d1dd743cd2993388c0e889485fc0a193b683a"},{"path":"/usr/lib64/python3.6/email/mime/application.py","mode":33188,"size":1321,"sha256":"5cd0255a621e87867c3c7f5130e0f3468eff99278e859320fcd07619cb5a35d8"},{"path":"/usr/lib64/python3.6/email/mime/audio.py","mode":33188,"size":2739,"sha256":"427778cece4effa17e21ea53e9946b146c9d70d7252473a0745cafb621fbafb5"},{"path":"/usr/lib64/python3.6/email/mime/base.py","mode":33188,"size":916,"sha256":"8e1014770d0d5e9fe6207ae0919b572033e4acc75e961ea0a3f760547716e3ee"},{"path":"/usr/lib64/python3.6/email/mime/image.py","mode":33188,"size":1829,"sha256":"a7aa3adaa32627323d5aa9d07228665a5d6492d2b392eb7bb36de752cd0972ee"},{"path":"/usr/lib64/python3.6/email/mime/message.py","mode":33188,"size":1317,"sha256":"0553e0365eb7e58ba8dcd5f4d416af8ab331b5d6d920b6fb16481ed172fa7d79"},{"path":"/usr/lib64/python3.6/email/mime/multipart.py","mode":33188,"size":1621,"sha256":"53730a1a7807d8af12b88665d8f474f48bf39ed1ef4c47433267a44ef54b0ba7"},{"path":"/usr/lib64/python3.6/email/mime/nonmultipart.py","mode":33188,"size":691,"sha256":"1f6fdedb5ba3e0a698bf33d77e329fc4cf2ab4305474b6ae23c1bc0f99daaf7a"},{"path":"/usr/lib64/python3.6/email/mime/text.py","mode":33188,"size":1437,"sha256":"aa903b8248020e9211e88f2c3a5e3a05f6969b6aab2b6f01ea1ddff776b870de"},{"path":"/usr/lib64/python3.6/email/parser.py","mode":33188,"size":5043,"sha256":"5010aca740bd1671aca4487d334ed298a1ba42c1b8d534e4bc627581cc07073f"},{"path":"/usr/lib64/python3.6/email/policy.py","mode":33188,"size":10373,"sha256":"fd8ad84b8a570b05062a3b6252a40c3353c0e111a18b07bfd05801a53f64a04e"},{"path":"/usr/lib64/python3.6/email/quoprimime.py","mode":33188,"size":9858,"sha256":"3b892900fd55b57d3be22f7bc9696feb905545adb81d37f4b77166753473a4b4"},{"path":"/usr/lib64/python3.6/email/utils.py","mode":33188,"size":13897,"sha256":"7c241bdb1ce6f09bb21045a05f32670d7f700cb50918a386c8b7f0b82432bff5"},{"path":"/usr/lib64/python3.6/encodings/__init__.py","mode":33188,"size":5642,"sha256":"5efd2b6cd7e54996e2f17909a4e19dd4787be8ff17d8de5f867741e2cef53830"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3932,"sha256":"a1d0a1028bea8f196518da5d5604a69968217737170bf4a440083d92e5352c30"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":2397,"sha256":"1cefd995ceb566bc15c20197ea2dd4aac7a8ef9b5a9d84b0102ada71270adc04"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3932,"sha256":"a1d0a1028bea8f196518da5d5604a69968217737170bf4a440083d92e5352c30"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/aliases.cpython-36.opt-1.pyc","mode":33188,"size":6276,"sha256":"5ba83a9a505a38e8eb3ad2c544fc9978843eeff72a40a0324fc6ce3f4da28523"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/aliases.cpython-36.opt-2.pyc","mode":33188,"size":5684,"sha256":"c6538701206c2d5bc94d888c438f06f51d986f9614e66060dc16aa6209c3bb8c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/aliases.cpython-36.pyc","mode":33188,"size":6276,"sha256":"5ba83a9a505a38e8eb3ad2c544fc9978843eeff72a40a0324fc6ce3f4da28523"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/ascii.cpython-36.opt-1.pyc","mode":33188,"size":1864,"sha256":"74396d2a36308aa71f8b39a600843c1e2cbbc9d316687b55a3532fae409d5114"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/ascii.cpython-36.opt-2.pyc","mode":33188,"size":1718,"sha256":"125dde25ccd36c942c8dc53f80d52aa55e2462ff70525e091dc597769a7d6796"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/ascii.cpython-36.pyc","mode":33188,"size":1864,"sha256":"74396d2a36308aa71f8b39a600843c1e2cbbc9d316687b55a3532fae409d5114"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/base64_codec.cpython-36.opt-1.pyc","mode":33188,"size":2282,"sha256":"eb62e99631995556184281497916ed7807a24a74a61b7bcc1b66f97ad501bf79"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/base64_codec.cpython-36.opt-2.pyc","mode":33188,"size":2107,"sha256":"a73a812c0df313dfc60458c81f57040a9a07b0e35e763c3429e83bbb6c192a31"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/base64_codec.cpython-36.pyc","mode":33188,"size":2403,"sha256":"1e06e1bb8b1e2a42c76fd31f98801c29e4887e3bceb36eecbc2c63a52be9224e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/big5.cpython-36.opt-1.pyc","mode":33188,"size":1424,"sha256":"14af61f517c23f084522b7d8fd803b5fae5b6e52f403d5c7798790e2a3a3e502"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/big5.cpython-36.opt-2.pyc","mode":33188,"size":1424,"sha256":"14af61f517c23f084522b7d8fd803b5fae5b6e52f403d5c7798790e2a3a3e502"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/big5.cpython-36.pyc","mode":33188,"size":1424,"sha256":"14af61f517c23f084522b7d8fd803b5fae5b6e52f403d5c7798790e2a3a3e502"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/big5hkscs.cpython-36.opt-1.pyc","mode":33188,"size":1434,"sha256":"d0878e1ca9104b504974c13876272bdde0f58d47df7e263acd60a1a939644165"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/big5hkscs.cpython-36.opt-2.pyc","mode":33188,"size":1434,"sha256":"d0878e1ca9104b504974c13876272bdde0f58d47df7e263acd60a1a939644165"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/big5hkscs.cpython-36.pyc","mode":33188,"size":1434,"sha256":"d0878e1ca9104b504974c13876272bdde0f58d47df7e263acd60a1a939644165"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/bz2_codec.cpython-36.opt-1.pyc","mode":33188,"size":3158,"sha256":"2adf1dc83c838b7e09263271a383d057eed37c857333e0b6b76f9d1464fe1f6f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/bz2_codec.cpython-36.opt-2.pyc","mode":33188,"size":2862,"sha256":"32eaf78b47e99b65e174d3037cd97c45187b5830b619ae4c5efa775b483c57e4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/bz2_codec.cpython-36.pyc","mode":33188,"size":3265,"sha256":"14285104e02b85396318e40e4952319c288dc5577cc4685e1711a0dae7f78c84"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/charmap.cpython-36.opt-1.pyc","mode":33188,"size":2917,"sha256":"d4d7457f50d28e2671b293ef3678dcaf9a90830ff4068dc9ea10d21c559120f6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/charmap.cpython-36.opt-2.pyc","mode":33188,"size":2623,"sha256":"5a0021dca4b48bff0aa75ff3750dc8ebe5ab2c57b59a6014cca195699ad28695"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/charmap.cpython-36.pyc","mode":33188,"size":2917,"sha256":"d4d7457f50d28e2671b293ef3678dcaf9a90830ff4068dc9ea10d21c559120f6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp037.cpython-36.opt-1.pyc","mode":33188,"size":2409,"sha256":"14ed75348a82754783ce5eff0171bde4b7fcdc5f7595b77ad76049bec8c50d80"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp037.cpython-36.opt-2.pyc","mode":33188,"size":2277,"sha256":"3ac7096ce987b0479b109f6437c57ab6017e2080aa184d146d601366d2f4935a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp037.cpython-36.pyc","mode":33188,"size":2409,"sha256":"14ed75348a82754783ce5eff0171bde4b7fcdc5f7595b77ad76049bec8c50d80"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1006.cpython-36.opt-1.pyc","mode":33188,"size":2485,"sha256":"d2ed5c9cde296b9004ac1b8ffb376d87cafea808e5fb0f0493faf4cc2235040a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1006.cpython-36.opt-2.pyc","mode":33188,"size":2360,"sha256":"a97f82e1a68a026a13e3e33fe2c13f8f0c8c5c809ea9af50f43f2ca37099bebf"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1006.cpython-36.pyc","mode":33188,"size":2485,"sha256":"d2ed5c9cde296b9004ac1b8ffb376d87cafea808e5fb0f0493faf4cc2235040a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1026.cpython-36.opt-1.pyc","mode":33188,"size":2413,"sha256":"05e179d375825b34dcae4220fb6f729ed3b272041eab1d2eeab6cd582140492d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1026.cpython-36.opt-2.pyc","mode":33188,"size":2279,"sha256":"8c7253b0d948d690d7fa3652556ebfd6a07d841ec7ec16b089c194282eb99182"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1026.cpython-36.pyc","mode":33188,"size":2413,"sha256":"05e179d375825b34dcae4220fb6f729ed3b272041eab1d2eeab6cd582140492d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1125.cpython-36.opt-1.pyc","mode":33188,"size":8106,"sha256":"6e5bc0a2f39c2efb845c99bec5d7bd1734eae5120a8a24eaf2995678f2a0f1bb"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1125.cpython-36.opt-2.pyc","mode":33188,"size":8043,"sha256":"bcb4846f474ea1d5f9d348373158532901d64a27deb25c822f59887e03677861"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1125.cpython-36.pyc","mode":33188,"size":8106,"sha256":"6e5bc0a2f39c2efb845c99bec5d7bd1734eae5120a8a24eaf2995678f2a0f1bb"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1140.cpython-36.opt-1.pyc","mode":33188,"size":2399,"sha256":"e6e8ea43e1f6d4f4480b12c39303d7ee6facec2bbf64979d98e39d92151915d7"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1140.cpython-36.opt-2.pyc","mode":33188,"size":2280,"sha256":"05ad225f21f3daf06d1ffbfa0d831ecb58c93a0c7699ae934c32c18aa0640460"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1140.cpython-36.pyc","mode":33188,"size":2399,"sha256":"e6e8ea43e1f6d4f4480b12c39303d7ee6facec2bbf64979d98e39d92151915d7"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1250.cpython-36.opt-1.pyc","mode":33188,"size":2436,"sha256":"ca000f76f626756239a16535308b5247df06d556bc434eae5b9abada6ca4aac2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1250.cpython-36.opt-2.pyc","mode":33188,"size":2301,"sha256":"856431706d51c847f69eadc6ccee84f04b57a81f6e590bddc3dfcd98bb04d95c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1250.cpython-36.pyc","mode":33188,"size":2436,"sha256":"ca000f76f626756239a16535308b5247df06d556bc434eae5b9abada6ca4aac2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1251.cpython-36.opt-1.pyc","mode":33188,"size":2433,"sha256":"20a85c07e48db2a6831faf937971a70f8b88851fdf02be686c7067e18855af17"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1251.cpython-36.opt-2.pyc","mode":33188,"size":2298,"sha256":"f1ae9152ff3500c2a10822cc44976455f1eb573d6818808ff293e667cc68a5d9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1251.cpython-36.pyc","mode":33188,"size":2433,"sha256":"20a85c07e48db2a6831faf937971a70f8b88851fdf02be686c7067e18855af17"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1252.cpython-36.opt-1.pyc","mode":33188,"size":2436,"sha256":"240c37d394c4f4a4145b578632b8abaa6eff69ea789b3f3fbefdf3e485458017"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1252.cpython-36.opt-2.pyc","mode":33188,"size":2301,"sha256":"4bd89cf9a0a27f5463fc02cc891ee78d8f1d706cf95b99f8f3f12f1da88beb85"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1252.cpython-36.pyc","mode":33188,"size":2436,"sha256":"240c37d394c4f4a4145b578632b8abaa6eff69ea789b3f3fbefdf3e485458017"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1253.cpython-36.opt-1.pyc","mode":33188,"size":2449,"sha256":"fa877e3fed2b328dccee6951336d06bd31e725662eab6c2b980b979dde4baf7f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1253.cpython-36.opt-2.pyc","mode":33188,"size":2314,"sha256":"d70d762d701b7bf4347849ac7cf4fa0c722cd18a64b0cc0b4ff0031fd659343b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1253.cpython-36.pyc","mode":33188,"size":2449,"sha256":"fa877e3fed2b328dccee6951336d06bd31e725662eab6c2b980b979dde4baf7f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1254.cpython-36.opt-1.pyc","mode":33188,"size":2438,"sha256":"3088717c1d7f727b1b3db97cbd4b321308ff455eaffd01886635f829223f563e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1254.cpython-36.opt-2.pyc","mode":33188,"size":2303,"sha256":"15f68ff2cba79f16208021f6c02edaa99f04065107dcd7963a217161b22e9ed9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1254.cpython-36.pyc","mode":33188,"size":2438,"sha256":"3088717c1d7f727b1b3db97cbd4b321308ff455eaffd01886635f829223f563e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1255.cpython-36.opt-1.pyc","mode":33188,"size":2457,"sha256":"19280a757935342da9a33750ea261864a3f4e7229901257f2658e6ab1c9e39fd"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1255.cpython-36.opt-2.pyc","mode":33188,"size":2322,"sha256":"e1957e52601d51f898df0e5bc9abef8c5df255728e04c5f595b3613aa3b42e19"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1255.cpython-36.pyc","mode":33188,"size":2457,"sha256":"19280a757935342da9a33750ea261864a3f4e7229901257f2658e6ab1c9e39fd"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1256.cpython-36.opt-1.pyc","mode":33188,"size":2435,"sha256":"ebbe257fa6bf667dbf4736392115a20f15863edfd087884bd140c196c2316854"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1256.cpython-36.opt-2.pyc","mode":33188,"size":2300,"sha256":"f9374fb6001c08683478387f98ca60aa93f21e865e288a5411d99ec40b449706"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1256.cpython-36.pyc","mode":33188,"size":2435,"sha256":"ebbe257fa6bf667dbf4736392115a20f15863edfd087884bd140c196c2316854"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1257.cpython-36.opt-1.pyc","mode":33188,"size":2443,"sha256":"dc5787422423a71961159ce00f767939188f8d1c7e8cf7bb812b7b89859a2062"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1257.cpython-36.opt-2.pyc","mode":33188,"size":2308,"sha256":"358bf85db3f89ce1132e54fb7ef32d0b80067689c00945f6ed26789e489a2c24"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1257.cpython-36.pyc","mode":33188,"size":2443,"sha256":"dc5787422423a71961159ce00f767939188f8d1c7e8cf7bb812b7b89859a2062"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1258.cpython-36.opt-1.pyc","mode":33188,"size":2441,"sha256":"4f986abc786f156e4d7df81a5941334a68fe8eaa004581bdf39f623c288d4740"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1258.cpython-36.opt-2.pyc","mode":33188,"size":2306,"sha256":"474a5a388741db47eb1c654590c622bf9a456a9320dd246f43f438f600d3dd0b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp1258.cpython-36.pyc","mode":33188,"size":2441,"sha256":"4f986abc786f156e4d7df81a5941334a68fe8eaa004581bdf39f623c288d4740"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp273.cpython-36.opt-1.pyc","mode":33188,"size":2395,"sha256":"4b631fd70008ca8192fe5bac4b518aae1dd241afda7afebad190792732384340"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp273.cpython-36.opt-2.pyc","mode":33188,"size":2278,"sha256":"ee195590b75210c304b96f5813ae0b3eed30585a15a7d6657a61210d124f91bd"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp273.cpython-36.pyc","mode":33188,"size":2395,"sha256":"4b631fd70008ca8192fe5bac4b518aae1dd241afda7afebad190792732384340"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp424.cpython-36.opt-1.pyc","mode":33188,"size":2439,"sha256":"4f4dbf7f023f95ce9a537bcc4d0f7237bff1968a85acafe395ce81df66e6537c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp424.cpython-36.opt-2.pyc","mode":33188,"size":2316,"sha256":"323256519f3061617f0429a4d902611a9dcc664f807aed558330d1596b02b792"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp424.cpython-36.pyc","mode":33188,"size":2439,"sha256":"4f4dbf7f023f95ce9a537bcc4d0f7237bff1968a85acafe395ce81df66e6537c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp437.cpython-36.opt-1.pyc","mode":33188,"size":7823,"sha256":"ca43933fab2bc7b29b93940f24423aa9a35f87930a36bba04dd3b8bf2d212073"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp437.cpython-36.opt-2.pyc","mode":33188,"size":7702,"sha256":"b431f2c4edc3329c5cb5d90492fca76177ec8c5fe1e449e0cda0b113164681f6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp437.cpython-36.pyc","mode":33188,"size":7823,"sha256":"ca43933fab2bc7b29b93940f24423aa9a35f87930a36bba04dd3b8bf2d212073"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp500.cpython-36.opt-1.pyc","mode":33188,"size":2409,"sha256":"3902a1f9a8a1be3207187cb36609719e991bb4e32d75c12cf6b234af7c6ba84b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp500.cpython-36.opt-2.pyc","mode":33188,"size":2277,"sha256":"0aa18581b5e8336fa7165b1059e73c6172acef58b351d264473edff0ff840365"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp500.cpython-36.pyc","mode":33188,"size":2409,"sha256":"3902a1f9a8a1be3207187cb36609719e991bb4e32d75c12cf6b234af7c6ba84b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp65001.cpython-36.opt-1.pyc","mode":33188,"size":1663,"sha256":"79320dfd8d3efd73f72a4b963953780307cf3ccc8b393997a9b258d8fd8622b0"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp65001.cpython-36.opt-2.pyc","mode":33188,"size":1603,"sha256":"897396ce49845bc1e2a11c06d8f7d94c449eee0fa63ea81e0348f8a2f107fc4c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp65001.cpython-36.pyc","mode":33188,"size":1663,"sha256":"79320dfd8d3efd73f72a4b963953780307cf3ccc8b393997a9b258d8fd8622b0"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp720.cpython-36.opt-1.pyc","mode":33188,"size":2506,"sha256":"1ac47a0f708fbbed0db7a2eaaeb4077ec66a1b9804839608fe46956c3614536f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp720.cpython-36.opt-2.pyc","mode":33188,"size":2331,"sha256":"84016fa1737d358148f228a615f03eeefa69f1fcadab107f772dd99388e5205b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp720.cpython-36.pyc","mode":33188,"size":2506,"sha256":"1ac47a0f708fbbed0db7a2eaaeb4077ec66a1b9804839608fe46956c3614536f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp737.cpython-36.opt-1.pyc","mode":33188,"size":8145,"sha256":"a384b445e70dcba26f540895e68a7e8c6fb3806112b9d344bbd4e993d5fa63ca"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp737.cpython-36.opt-2.pyc","mode":33188,"size":8024,"sha256":"46ca914e6ba8fb04857fc47b4082925882d86dd1344b070fb8d5b9c2741d02af"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp737.cpython-36.pyc","mode":33188,"size":8145,"sha256":"a384b445e70dcba26f540895e68a7e8c6fb3806112b9d344bbd4e993d5fa63ca"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp775.cpython-36.opt-1.pyc","mode":33188,"size":7853,"sha256":"b4d93c3dd6202698a2f7196f52a2c3de59df23e6a16478716c515d352ab2897a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp775.cpython-36.opt-2.pyc","mode":33188,"size":7732,"sha256":"3846f4e374e28df96973a325f3d4abaae4f986d62fb6079c5638aae7b1672f30"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp775.cpython-36.pyc","mode":33188,"size":7853,"sha256":"b4d93c3dd6202698a2f7196f52a2c3de59df23e6a16478716c515d352ab2897a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp850.cpython-36.opt-1.pyc","mode":33188,"size":7484,"sha256":"22921746e0190d725f3a6dd6233eabdaeeebdd0f8307fad8b2ee6b720628e6e7"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp850.cpython-36.opt-2.pyc","mode":33188,"size":7369,"sha256":"f4f4cd4756bcf693d0d495e6e45c2280d14e1818b0de52c14a52a70d301292c9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp850.cpython-36.pyc","mode":33188,"size":7484,"sha256":"22921746e0190d725f3a6dd6233eabdaeeebdd0f8307fad8b2ee6b720628e6e7"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp852.cpython-36.opt-1.pyc","mode":33188,"size":7861,"sha256":"1e356c9e3b81d75e6fc79676e1d81ce9063a28b27bc42867d6216f836d63df15"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp852.cpython-36.opt-2.pyc","mode":33188,"size":7746,"sha256":"8f4d0f6b608f2933a3193dda0268ec92839e55bf80fb27abdeb35d2b630df5f9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp852.cpython-36.pyc","mode":33188,"size":7861,"sha256":"1e356c9e3b81d75e6fc79676e1d81ce9063a28b27bc42867d6216f836d63df15"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp855.cpython-36.opt-1.pyc","mode":33188,"size":8114,"sha256":"3a5c3cd39f66447ccc1e69b9741a9ea07b53bca6e44eaa8e97c2da73146b2546"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp855.cpython-36.opt-2.pyc","mode":33188,"size":7999,"sha256":"d23a91d83bb547015f262ecf65a416d3bd10d268b5e9e4e641921188c3a69e9a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp855.cpython-36.pyc","mode":33188,"size":8114,"sha256":"3a5c3cd39f66447ccc1e69b9741a9ea07b53bca6e44eaa8e97c2da73146b2546"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp856.cpython-36.opt-1.pyc","mode":33188,"size":2471,"sha256":"7674a489f22cae96edcac7db951b816a3684c50e684a25380268152e40c0a339"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp856.cpython-36.opt-2.pyc","mode":33188,"size":2348,"sha256":"68f5fc7badf4c5b3b5ad51db9cfd194a3204aa439e4d85e4d2eb63dc53a890f1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp856.cpython-36.pyc","mode":33188,"size":2471,"sha256":"7674a489f22cae96edcac7db951b816a3684c50e684a25380268152e40c0a339"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp857.cpython-36.opt-1.pyc","mode":33188,"size":7466,"sha256":"2a149db0b91a663b55501e25425d4a798b3389ec66fd2b30981e09a0c1f98bc5"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp857.cpython-36.opt-2.pyc","mode":33188,"size":7351,"sha256":"c343d58b37a08e7abe901a3f3baa4194125503521d7aff398a959ce18d82bd7b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp857.cpython-36.pyc","mode":33188,"size":7466,"sha256":"2a149db0b91a663b55501e25425d4a798b3389ec66fd2b30981e09a0c1f98bc5"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp858.cpython-36.opt-1.pyc","mode":33188,"size":7454,"sha256":"6ac05d0ac8bab00637b8b5d78bb78bd24c85403d6aaebfdf399b509d0d845477"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp858.cpython-36.opt-2.pyc","mode":33188,"size":7370,"sha256":"3cfccc1aa6ba098fe07dc7c092dc13f71b49800a106050f997c9e93a7e907e30"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp858.cpython-36.pyc","mode":33188,"size":7454,"sha256":"6ac05d0ac8bab00637b8b5d78bb78bd24c85403d6aaebfdf399b509d0d845477"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp860.cpython-36.opt-1.pyc","mode":33188,"size":7802,"sha256":"6328a0af3e0dc64f1de8a533d7d238f3d08cac9d10c4e0bdbd601faf909e2740"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp860.cpython-36.opt-2.pyc","mode":33188,"size":7687,"sha256":"7d4b0c07726f15905191efb55d59c8708c6a5ca1e425dd7c82d87cf4c2ea41c8"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp860.cpython-36.pyc","mode":33188,"size":7802,"sha256":"6328a0af3e0dc64f1de8a533d7d238f3d08cac9d10c4e0bdbd601faf909e2740"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp861.cpython-36.opt-1.pyc","mode":33188,"size":7817,"sha256":"1203c4b3ad084261b507df7c729b1d064209d0cfadc00a4dbfa0101c07c1f65e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp861.cpython-36.opt-2.pyc","mode":33188,"size":7702,"sha256":"a513adff06030af288143d688cb46dbb6b0650ee90293e914da5ba0f9952ff6c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp861.cpython-36.pyc","mode":33188,"size":7817,"sha256":"1203c4b3ad084261b507df7c729b1d064209d0cfadc00a4dbfa0101c07c1f65e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp862.cpython-36.opt-1.pyc","mode":33188,"size":8006,"sha256":"10677b33e74897124bb1bd1221ec40edf408912fa73344f7d32fcd3e189c4189"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp862.cpython-36.opt-2.pyc","mode":33188,"size":7891,"sha256":"4ae8aef9d9f7787276fadcb5a1413803ba73c990c5a9cc12b7be65bbd57b9aa1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp862.cpython-36.pyc","mode":33188,"size":8006,"sha256":"10677b33e74897124bb1bd1221ec40edf408912fa73344f7d32fcd3e189c4189"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp863.cpython-36.opt-1.pyc","mode":33188,"size":7817,"sha256":"ca4791025fd6bd07d5647affdde44f1f742b7a2802512f69dfef88d5201ec56b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp863.cpython-36.opt-2.pyc","mode":33188,"size":7702,"sha256":"19a3b4ef35de7f89623413b56e0c70a11a857a8bbf8654b86fab418055e0c97b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp863.cpython-36.pyc","mode":33188,"size":7817,"sha256":"ca4791025fd6bd07d5647affdde44f1f742b7a2802512f69dfef88d5201ec56b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp864.cpython-36.opt-1.pyc","mode":33188,"size":7963,"sha256":"8d078828f1affae55847c4bc423e559500404a6cad11b7bbd450e117976aa98d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp864.cpython-36.opt-2.pyc","mode":33188,"size":7848,"sha256":"c2fae539be152c9f7d92819ae2f2cfd312fb709759abe9eb8a898abe82d73d96"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp864.cpython-36.pyc","mode":33188,"size":7963,"sha256":"8d078828f1affae55847c4bc423e559500404a6cad11b7bbd450e117976aa98d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp865.cpython-36.opt-1.pyc","mode":33188,"size":7817,"sha256":"3ed5ef84837d95ff135c12cf0d8602f11eaf5f70e0a02a1f8ed7345d60b06599"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp865.cpython-36.opt-2.pyc","mode":33188,"size":7702,"sha256":"f559d7f08110e1eba8e91037215821aabe7b87b6bb0c9fbd60a06348c47596fa"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp865.cpython-36.pyc","mode":33188,"size":7817,"sha256":"3ed5ef84837d95ff135c12cf0d8602f11eaf5f70e0a02a1f8ed7345d60b06599"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp866.cpython-36.opt-1.pyc","mode":33188,"size":8150,"sha256":"49d42e51e8e689ffc1e0bba51614ba0a2cba8a4fa27ea0ae2b11130551bac0c9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp866.cpython-36.opt-2.pyc","mode":33188,"size":8035,"sha256":"e762ea641a752e70653d3ff958959e6ae3a187d3332b20a9090823371e1048b8"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp866.cpython-36.pyc","mode":33188,"size":8150,"sha256":"49d42e51e8e689ffc1e0bba51614ba0a2cba8a4fa27ea0ae2b11130551bac0c9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp869.cpython-36.opt-1.pyc","mode":33188,"size":7843,"sha256":"17d9bc3c5805306b6421505d818aaaa39e2f9b3fb06a012c17a77068cb2f8d62"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp869.cpython-36.opt-2.pyc","mode":33188,"size":7728,"sha256":"667da51ab2f47eb0b7191f4fe55d3ecf4a3ecf0a2d762d183cfca3298558e415"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp869.cpython-36.pyc","mode":33188,"size":7843,"sha256":"17d9bc3c5805306b6421505d818aaaa39e2f9b3fb06a012c17a77068cb2f8d62"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp874.cpython-36.opt-1.pyc","mode":33188,"size":2537,"sha256":"13f36a5f53853deb860a7c576e58cf48df2fe8266791f60c96f2858a0c222d65"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp874.cpython-36.opt-2.pyc","mode":33188,"size":2404,"sha256":"c05c2b39243b9b069450458925d8d88101c1ffc0eda457d2750bdc437f5327e1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp874.cpython-36.pyc","mode":33188,"size":2537,"sha256":"13f36a5f53853deb860a7c576e58cf48df2fe8266791f60c96f2858a0c222d65"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp875.cpython-36.opt-1.pyc","mode":33188,"size":2406,"sha256":"f55f0e88bfa041b1de536714144cebb0e6697e6fd634c9be41b726371ba367d7"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp875.cpython-36.opt-2.pyc","mode":33188,"size":2274,"sha256":"e89c30074d4cb23bfe50f9c6c021bbe9985a6034d9e45c4b529c2d9bde7c1334"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp875.cpython-36.pyc","mode":33188,"size":2406,"sha256":"f55f0e88bfa041b1de536714144cebb0e6697e6fd634c9be41b726371ba367d7"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp932.cpython-36.opt-1.pyc","mode":33188,"size":1426,"sha256":"56147ed3f9ccd697f02abca4666b2e688c9134c3cef628f10982209e59fd7eee"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp932.cpython-36.opt-2.pyc","mode":33188,"size":1426,"sha256":"56147ed3f9ccd697f02abca4666b2e688c9134c3cef628f10982209e59fd7eee"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp932.cpython-36.pyc","mode":33188,"size":1426,"sha256":"56147ed3f9ccd697f02abca4666b2e688c9134c3cef628f10982209e59fd7eee"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp949.cpython-36.opt-1.pyc","mode":33188,"size":1426,"sha256":"2c3e30bd314ad8b031f330e32ccc72016d3cdc06834e1991857d3855b94103b1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp949.cpython-36.opt-2.pyc","mode":33188,"size":1426,"sha256":"2c3e30bd314ad8b031f330e32ccc72016d3cdc06834e1991857d3855b94103b1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp949.cpython-36.pyc","mode":33188,"size":1426,"sha256":"2c3e30bd314ad8b031f330e32ccc72016d3cdc06834e1991857d3855b94103b1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp950.cpython-36.opt-1.pyc","mode":33188,"size":1426,"sha256":"55196f1f847802cd8b6e8d93e568839306de2a7073798433318f513912aa35b3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp950.cpython-36.opt-2.pyc","mode":33188,"size":1426,"sha256":"55196f1f847802cd8b6e8d93e568839306de2a7073798433318f513912aa35b3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/cp950.cpython-36.pyc","mode":33188,"size":1426,"sha256":"55196f1f847802cd8b6e8d93e568839306de2a7073798433318f513912aa35b3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jis_2004.cpython-36.opt-1.pyc","mode":33188,"size":1440,"sha256":"0d1e6048dad099cdfd1c6d84ae2d9086c21a0652910edfc53ed9b9b7f311fe10"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jis_2004.cpython-36.opt-2.pyc","mode":33188,"size":1440,"sha256":"0d1e6048dad099cdfd1c6d84ae2d9086c21a0652910edfc53ed9b9b7f311fe10"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jis_2004.cpython-36.pyc","mode":33188,"size":1440,"sha256":"0d1e6048dad099cdfd1c6d84ae2d9086c21a0652910edfc53ed9b9b7f311fe10"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jisx0213.cpython-36.opt-1.pyc","mode":33188,"size":1440,"sha256":"d9bcb0322401faebc6279ff8e18745904145b224cbdb6af61179fb0cba56b267"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jisx0213.cpython-36.opt-2.pyc","mode":33188,"size":1440,"sha256":"d9bcb0322401faebc6279ff8e18745904145b224cbdb6af61179fb0cba56b267"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jisx0213.cpython-36.pyc","mode":33188,"size":1440,"sha256":"d9bcb0322401faebc6279ff8e18745904145b224cbdb6af61179fb0cba56b267"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jp.cpython-36.opt-1.pyc","mode":33188,"size":1428,"sha256":"959c15faef867ad4be122da19017bf7540ecfdb8cc2a0e206524c41869e4cd91"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jp.cpython-36.opt-2.pyc","mode":33188,"size":1428,"sha256":"959c15faef867ad4be122da19017bf7540ecfdb8cc2a0e206524c41869e4cd91"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_jp.cpython-36.pyc","mode":33188,"size":1428,"sha256":"959c15faef867ad4be122da19017bf7540ecfdb8cc2a0e206524c41869e4cd91"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_kr.cpython-36.opt-1.pyc","mode":33188,"size":1428,"sha256":"beb31a76a3c2192304fa9282b9c9f5f0de79e26c5134499b2fc555eee961bf1a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_kr.cpython-36.opt-2.pyc","mode":33188,"size":1428,"sha256":"beb31a76a3c2192304fa9282b9c9f5f0de79e26c5134499b2fc555eee961bf1a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/euc_kr.cpython-36.pyc","mode":33188,"size":1428,"sha256":"beb31a76a3c2192304fa9282b9c9f5f0de79e26c5134499b2fc555eee961bf1a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gb18030.cpython-36.opt-1.pyc","mode":33188,"size":1430,"sha256":"01de7fb65fa1d65b9d30b7c93d338812530c91b6eb68f63a93507b235e203d54"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gb18030.cpython-36.opt-2.pyc","mode":33188,"size":1430,"sha256":"01de7fb65fa1d65b9d30b7c93d338812530c91b6eb68f63a93507b235e203d54"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gb18030.cpython-36.pyc","mode":33188,"size":1430,"sha256":"01de7fb65fa1d65b9d30b7c93d338812530c91b6eb68f63a93507b235e203d54"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gb2312.cpython-36.opt-1.pyc","mode":33188,"size":1428,"sha256":"05d1cd76064fe22e05230ace9ddaa441f7d675b2b76a28af6a3867fa25fdf291"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gb2312.cpython-36.opt-2.pyc","mode":33188,"size":1428,"sha256":"05d1cd76064fe22e05230ace9ddaa441f7d675b2b76a28af6a3867fa25fdf291"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gb2312.cpython-36.pyc","mode":33188,"size":1428,"sha256":"05d1cd76064fe22e05230ace9ddaa441f7d675b2b76a28af6a3867fa25fdf291"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gbk.cpython-36.opt-1.pyc","mode":33188,"size":1422,"sha256":"082747ad39a4697301137eac36a87960b8a316304ee1d27b1cecc01458aac551"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gbk.cpython-36.opt-2.pyc","mode":33188,"size":1422,"sha256":"082747ad39a4697301137eac36a87960b8a316304ee1d27b1cecc01458aac551"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/gbk.cpython-36.pyc","mode":33188,"size":1422,"sha256":"082747ad39a4697301137eac36a87960b8a316304ee1d27b1cecc01458aac551"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hex_codec.cpython-36.opt-1.pyc","mode":33188,"size":2269,"sha256":"ad948ad3e994c3086560e6c1cc0e24da3b4f6c15baef19d572d5b6426911f835"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hex_codec.cpython-36.opt-2.pyc","mode":33188,"size":2092,"sha256":"e26b7d080ff750878aed036464fdf0d32dc73285128faa88e09522df6da40c6c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hex_codec.cpython-36.pyc","mode":33188,"size":2390,"sha256":"b69b1e508e81ce702b2a2c3d16cf43ddfd54b49f5bfd895b58126926a97ddfdb"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hp_roman8.cpython-36.opt-1.pyc","mode":33188,"size":2610,"sha256":"2c556082b71a4c387e74d897b929eb6a4aa8fb06fcc89ffd2f05d26e346fac52"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hp_roman8.cpython-36.opt-2.pyc","mode":33188,"size":2289,"sha256":"2c86a71774993bf86302ee98564568845f19f48c8fbd9d3fbecce672a4af5329"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hp_roman8.cpython-36.pyc","mode":33188,"size":2610,"sha256":"2c556082b71a4c387e74d897b929eb6a4aa8fb06fcc89ffd2f05d26e346fac52"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hz.cpython-36.opt-1.pyc","mode":33188,"size":1420,"sha256":"85f9f3385bd041836add8c1d094da966ee840164431e0c57a57370e91f23cd1b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hz.cpython-36.opt-2.pyc","mode":33188,"size":1420,"sha256":"85f9f3385bd041836add8c1d094da966ee840164431e0c57a57370e91f23cd1b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/hz.cpython-36.pyc","mode":33188,"size":1420,"sha256":"85f9f3385bd041836add8c1d094da966ee840164431e0c57a57370e91f23cd1b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/idna.cpython-36.opt-1.pyc","mode":33188,"size":5767,"sha256":"e1fc74030fe94a7bf9537db98a9a62f323646c9604fd87617724f17be2ef95f9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/idna.cpython-36.opt-2.pyc","mode":33188,"size":5767,"sha256":"e1fc74030fe94a7bf9537db98a9a62f323646c9604fd87617724f17be2ef95f9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/idna.cpython-36.pyc","mode":33188,"size":5767,"sha256":"e1fc74030fe94a7bf9537db98a9a62f323646c9604fd87617724f17be2ef95f9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp.cpython-36.opt-1.pyc","mode":33188,"size":1441,"sha256":"fc69a5b52ad3679d76a685b447b69bb05427df3f5fe490ccba6d0e838a4369ee"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp.cpython-36.opt-2.pyc","mode":33188,"size":1441,"sha256":"fc69a5b52ad3679d76a685b447b69bb05427df3f5fe490ccba6d0e838a4369ee"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp.cpython-36.pyc","mode":33188,"size":1441,"sha256":"fc69a5b52ad3679d76a685b447b69bb05427df3f5fe490ccba6d0e838a4369ee"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_1.cpython-36.opt-1.pyc","mode":33188,"size":1445,"sha256":"6c6ebdd19a681a66dcd0a83605018e310d7d465752096efc2bb964376b7c3ea1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_1.cpython-36.opt-2.pyc","mode":33188,"size":1445,"sha256":"6c6ebdd19a681a66dcd0a83605018e310d7d465752096efc2bb964376b7c3ea1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_1.cpython-36.pyc","mode":33188,"size":1445,"sha256":"6c6ebdd19a681a66dcd0a83605018e310d7d465752096efc2bb964376b7c3ea1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_2.cpython-36.opt-1.pyc","mode":33188,"size":1445,"sha256":"2c6440357427ac716b9229a64eafd1a78a65be58e078a35e13d8dc35b0d3d7ab"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_2.cpython-36.opt-2.pyc","mode":33188,"size":1445,"sha256":"2c6440357427ac716b9229a64eafd1a78a65be58e078a35e13d8dc35b0d3d7ab"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_2.cpython-36.pyc","mode":33188,"size":1445,"sha256":"2c6440357427ac716b9229a64eafd1a78a65be58e078a35e13d8dc35b0d3d7ab"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_2004.cpython-36.opt-1.pyc","mode":33188,"size":1451,"sha256":"abbcf35fb385010d4547594437c73215b74814837bf800688deda144abcab20f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_2004.cpython-36.opt-2.pyc","mode":33188,"size":1451,"sha256":"abbcf35fb385010d4547594437c73215b74814837bf800688deda144abcab20f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_2004.cpython-36.pyc","mode":33188,"size":1451,"sha256":"abbcf35fb385010d4547594437c73215b74814837bf800688deda144abcab20f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_3.cpython-36.opt-1.pyc","mode":33188,"size":1445,"sha256":"cd44578a65620264685741c9d4cf2a9f8cd8bc55e8aac36ff3a80f4912302786"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_3.cpython-36.opt-2.pyc","mode":33188,"size":1445,"sha256":"cd44578a65620264685741c9d4cf2a9f8cd8bc55e8aac36ff3a80f4912302786"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_3.cpython-36.pyc","mode":33188,"size":1445,"sha256":"cd44578a65620264685741c9d4cf2a9f8cd8bc55e8aac36ff3a80f4912302786"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_ext.cpython-36.opt-1.pyc","mode":33188,"size":1449,"sha256":"1a6751e5dfbe2175804da84a6502e51a7895c526d71f4ccb04b56a624b927d75"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_ext.cpython-36.opt-2.pyc","mode":33188,"size":1449,"sha256":"1a6751e5dfbe2175804da84a6502e51a7895c526d71f4ccb04b56a624b927d75"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_jp_ext.cpython-36.pyc","mode":33188,"size":1449,"sha256":"1a6751e5dfbe2175804da84a6502e51a7895c526d71f4ccb04b56a624b927d75"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_kr.cpython-36.opt-1.pyc","mode":33188,"size":1441,"sha256":"6032473ee267f1bbe10b2cff9f8894c0424edfe92326571872d735d5f817be80"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_kr.cpython-36.opt-2.pyc","mode":33188,"size":1441,"sha256":"6032473ee267f1bbe10b2cff9f8894c0424edfe92326571872d735d5f817be80"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso2022_kr.cpython-36.pyc","mode":33188,"size":1441,"sha256":"6032473ee267f1bbe10b2cff9f8894c0424edfe92326571872d735d5f817be80"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_1.cpython-36.opt-1.pyc","mode":33188,"size":2408,"sha256":"96d9740f6342b96199c78934814bb711bda3c6ac367ab7b9f3d3c4203a3b2bc9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_1.cpython-36.opt-2.pyc","mode":33188,"size":2285,"sha256":"efef2e35cbbf9344e9a40d84bba3d725c52e34d0b5bdf30efc2694702dac043e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_1.cpython-36.pyc","mode":33188,"size":2408,"sha256":"96d9740f6342b96199c78934814bb711bda3c6ac367ab7b9f3d3c4203a3b2bc9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_10.cpython-36.opt-1.pyc","mode":33188,"size":2413,"sha256":"38ed3ed9556429d5ac446336c934872e5b1d4c65684f491672eff43d419f75f2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_10.cpython-36.opt-2.pyc","mode":33188,"size":2288,"sha256":"08249d9a177905d6cba8d0eadb3c6dbba141245e102d37750bfb0bf47b4d81c6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_10.cpython-36.pyc","mode":33188,"size":2413,"sha256":"38ed3ed9556429d5ac446336c934872e5b1d4c65684f491672eff43d419f75f2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_11.cpython-36.opt-1.pyc","mode":33188,"size":2507,"sha256":"28906aea43ef7ee6963b258aed11685c0a6f367225ef80fef6df28d6d132759b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_11.cpython-36.opt-2.pyc","mode":33188,"size":2382,"sha256":"0bdada7fecb7f6b508b67d9aef62ae891ccbc441fe92e4066a6b349266b1691f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_11.cpython-36.pyc","mode":33188,"size":2507,"sha256":"28906aea43ef7ee6963b258aed11685c0a6f367225ef80fef6df28d6d132759b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_13.cpython-36.opt-1.pyc","mode":33188,"size":2416,"sha256":"167df343721172bb1a13c786f46bbecb9612a8992fd40000c5949a0cc2ea723e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_13.cpython-36.opt-2.pyc","mode":33188,"size":2291,"sha256":"9c1407a536525d54815b421662369e85edb8d6ae71cdc3679f4125546180c815"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_13.cpython-36.pyc","mode":33188,"size":2416,"sha256":"167df343721172bb1a13c786f46bbecb9612a8992fd40000c5949a0cc2ea723e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_14.cpython-36.opt-1.pyc","mode":33188,"size":2434,"sha256":"a99b2f2199456396a999c42b1d5bcd1148c61102959161ef472b7bc7b87811b4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_14.cpython-36.opt-2.pyc","mode":33188,"size":2309,"sha256":"2d2f5b4534ada44d795f5d2ada58ee56e6c8a8224cde8fda7b8376fefe4d8904"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_14.cpython-36.pyc","mode":33188,"size":2434,"sha256":"a99b2f2199456396a999c42b1d5bcd1148c61102959161ef472b7bc7b87811b4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_15.cpython-36.opt-1.pyc","mode":33188,"size":2413,"sha256":"177749ade4a048bb8450d464c50a9db36a9bf815d3d5fced67ca8c738621985e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_15.cpython-36.opt-2.pyc","mode":33188,"size":2288,"sha256":"e3fd2adae5ac2645f71653be3cb629c4e9f5a55f07e8387ea05b09a97fad070d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_15.cpython-36.pyc","mode":33188,"size":2413,"sha256":"177749ade4a048bb8450d464c50a9db36a9bf815d3d5fced67ca8c738621985e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_16.cpython-36.opt-1.pyc","mode":33188,"size":2415,"sha256":"99360839ffd6f3d79524c751143d627cbd832ed348d5ff23ccee20928793f6df"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_16.cpython-36.opt-2.pyc","mode":33188,"size":2290,"sha256":"70b7bd182005b90351ef146349cd33dbfd9cc66b515bfe9e0df38fe1f4a8fc52"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_16.cpython-36.pyc","mode":33188,"size":2415,"sha256":"99360839ffd6f3d79524c751143d627cbd832ed348d5ff23ccee20928793f6df"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_2.cpython-36.opt-1.pyc","mode":33188,"size":2408,"sha256":"a86d80569b1b5b15b00a1481d877b7bafa8945015a0c7d1dd4539a6070c0e48c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_2.cpython-36.opt-2.pyc","mode":33188,"size":2285,"sha256":"f09f27e23afb82fb3436b39420ecc7980376b79a07205feb082bed6eda05546f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_2.cpython-36.pyc","mode":33188,"size":2408,"sha256":"a86d80569b1b5b15b00a1481d877b7bafa8945015a0c7d1dd4539a6070c0e48c"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_3.cpython-36.opt-1.pyc","mode":33188,"size":2415,"sha256":"eeb7f139b27a9c7075b9aeb313a3496610699c3cbdd07f84e903903f77dfa390"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_3.cpython-36.opt-2.pyc","mode":33188,"size":2292,"sha256":"f3edc2b244d64d58d1ab93f2e48337b44439534740ab22614776f0326d3f4222"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_3.cpython-36.pyc","mode":33188,"size":2415,"sha256":"eeb7f139b27a9c7075b9aeb313a3496610699c3cbdd07f84e903903f77dfa390"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_4.cpython-36.opt-1.pyc","mode":33188,"size":2408,"sha256":"e5b1adde0aa7e590266047ab4b1bafd061b1403aeef3d08f517096f407783aef"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_4.cpython-36.opt-2.pyc","mode":33188,"size":2285,"sha256":"76eba3b099d6913255760ac1fc738218e75e60f8dceacedabd1ddffc8e496dc1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_4.cpython-36.pyc","mode":33188,"size":2408,"sha256":"e5b1adde0aa7e590266047ab4b1bafd061b1403aeef3d08f517096f407783aef"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_5.cpython-36.opt-1.pyc","mode":33188,"size":2409,"sha256":"62ecc13aefefd9b96f9878d5138b4250edbec712ee09a84a2d8d4c2e30d43620"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_5.cpython-36.opt-2.pyc","mode":33188,"size":2286,"sha256":"4c0eb3da99c5cdffd87c286ee822f56adb4b5a09b41d2c3e2deda702f075c3df"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_5.cpython-36.pyc","mode":33188,"size":2409,"sha256":"62ecc13aefefd9b96f9878d5138b4250edbec712ee09a84a2d8d4c2e30d43620"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_6.cpython-36.opt-1.pyc","mode":33188,"size":2453,"sha256":"a5eb31895f4a0238ffc887fa4c92fb43209b70b3862dbe0a0ec492ad8a94cf39"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_6.cpython-36.opt-2.pyc","mode":33188,"size":2330,"sha256":"10a474e8669fbc1f91261b4f3c92ade35a37b9fca3c9e558cbcaeb4428e76ac8"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_6.cpython-36.pyc","mode":33188,"size":2453,"sha256":"a5eb31895f4a0238ffc887fa4c92fb43209b70b3862dbe0a0ec492ad8a94cf39"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_7.cpython-36.opt-1.pyc","mode":33188,"size":2416,"sha256":"63aeb1f02130686f9a7cc09f94603778e72acf75dc46a6a9fb760c90d8cfba70"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_7.cpython-36.opt-2.pyc","mode":33188,"size":2293,"sha256":"2b5f26722badb661c9c3bcda6b3c2004e6b52deb50f50a87c09bd189f6ea2d0d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_7.cpython-36.pyc","mode":33188,"size":2416,"sha256":"63aeb1f02130686f9a7cc09f94603778e72acf75dc46a6a9fb760c90d8cfba70"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_8.cpython-36.opt-1.pyc","mode":33188,"size":2447,"sha256":"a382391ea9cc079282256a20626d4c27c45fec7fa36fa171fd4e36b3f83a42a3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_8.cpython-36.opt-2.pyc","mode":33188,"size":2324,"sha256":"ae0adb7c7a432bc1a8ec23a9fdaf405d1e81fac913f9a9eb396c2fafb6d04a0a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_8.cpython-36.pyc","mode":33188,"size":2447,"sha256":"a382391ea9cc079282256a20626d4c27c45fec7fa36fa171fd4e36b3f83a42a3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_9.cpython-36.opt-1.pyc","mode":33188,"size":2408,"sha256":"0f2b61bf04c8193311a0f25a3f30b1560577c4c724080ee12ac2efcfbd4b736e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_9.cpython-36.opt-2.pyc","mode":33188,"size":2285,"sha256":"a6fdb5cbe6c236c53808888244a029375d2420dc003073acf53ecb08d0097e9d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/iso8859_9.cpython-36.pyc","mode":33188,"size":2408,"sha256":"0f2b61bf04c8193311a0f25a3f30b1560577c4c724080ee12ac2efcfbd4b736e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/johab.cpython-36.opt-1.pyc","mode":33188,"size":1426,"sha256":"ee9838c5e877a344ce46a9e70e4b9ca4387db8eb627344e0df051649843aa98f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/johab.cpython-36.opt-2.pyc","mode":33188,"size":1426,"sha256":"ee9838c5e877a344ce46a9e70e4b9ca4387db8eb627344e0df051649843aa98f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/johab.cpython-36.pyc","mode":33188,"size":1426,"sha256":"ee9838c5e877a344ce46a9e70e4b9ca4387db8eb627344e0df051649843aa98f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_r.cpython-36.opt-1.pyc","mode":33188,"size":2460,"sha256":"389dee411f3ae2dd254e3b29e0b99ef8b89aa69eb69f4dd98a046e5237eeb52f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_r.cpython-36.opt-2.pyc","mode":33188,"size":2335,"sha256":"85688fc2b008a889269da099b9cea0dfa2143e02faa545d660aba073aed7f4e9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_r.cpython-36.pyc","mode":33188,"size":2460,"sha256":"389dee411f3ae2dd254e3b29e0b99ef8b89aa69eb69f4dd98a046e5237eeb52f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_t.cpython-36.opt-1.pyc","mode":33188,"size":2371,"sha256":"a70b455a5b30229ca09f496e12e238cdeda42dfbda4454c6d30fd5f7cf99be7d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_t.cpython-36.opt-2.pyc","mode":33188,"size":2315,"sha256":"19efa8f0d516a5f124bdbbfbdd7be0b08e87121769f2808010fe147110e98ab6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_t.cpython-36.pyc","mode":33188,"size":2371,"sha256":"a70b455a5b30229ca09f496e12e238cdeda42dfbda4454c6d30fd5f7cf99be7d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_u.cpython-36.opt-1.pyc","mode":33188,"size":2446,"sha256":"58515596a8fc89989278d29c3c8d935a38347d6c05faaeb6a795d8fdf7967d03"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_u.cpython-36.opt-2.pyc","mode":33188,"size":2327,"sha256":"f9a1c971b37be3c475e37a8638e6014a551e2faee56be363a60e58ce6e6d8919"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/koi8_u.cpython-36.pyc","mode":33188,"size":2446,"sha256":"58515596a8fc89989278d29c3c8d935a38347d6c05faaeb6a795d8fdf7967d03"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/kz1048.cpython-36.opt-1.pyc","mode":33188,"size":2423,"sha256":"9b6640d0ed5cbbccf9e57b2f88a75664034431d0aef7a80ef0bfbf131adf9597"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/kz1048.cpython-36.opt-2.pyc","mode":33188,"size":2298,"sha256":"a09e5d50b876ec738465b5f5363ede1764582d833aa32514700c20ad3524ca43"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/kz1048.cpython-36.pyc","mode":33188,"size":2423,"sha256":"9b6640d0ed5cbbccf9e57b2f88a75664034431d0aef7a80ef0bfbf131adf9597"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/latin_1.cpython-36.opt-1.pyc","mode":33188,"size":1876,"sha256":"726cecc5cf79205f3be2be86f346a8de095075085b32e2f99972be40faa63bcf"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/latin_1.cpython-36.opt-2.pyc","mode":33188,"size":1728,"sha256":"9ea338956e0ac82c22719910cafffdbdefc4bb8451e57736345bf8662d12a32e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/latin_1.cpython-36.pyc","mode":33188,"size":1876,"sha256":"726cecc5cf79205f3be2be86f346a8de095075085b32e2f99972be40faa63bcf"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_arabic.cpython-36.opt-1.pyc","mode":33188,"size":7717,"sha256":"073ca7a0374831db9900eddc723f5a4dc4b3e4a66fb40148f4e10f7c8aa9ff5e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_arabic.cpython-36.opt-2.pyc","mode":33188,"size":7605,"sha256":"3dbc0ba44f4a082f888fe559462db12b0b51e8aba3631a1d5cf4642be7a7fd8d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_arabic.cpython-36.pyc","mode":33188,"size":7717,"sha256":"073ca7a0374831db9900eddc723f5a4dc4b3e4a66fb40148f4e10f7c8aa9ff5e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_centeuro.cpython-36.opt-1.pyc","mode":33188,"size":2447,"sha256":"ca0cbb9862d0d3bdd3712b57b0ea0ab6a3fafd176c8a2383070de0f7ede11f28"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_centeuro.cpython-36.opt-2.pyc","mode":33188,"size":2313,"sha256":"cab9f14f63adedecd23761d147c153aeab2f19389acca30f5a5238f058532a06"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_centeuro.cpython-36.pyc","mode":33188,"size":2447,"sha256":"ca0cbb9862d0d3bdd3712b57b0ea0ab6a3fafd176c8a2383070de0f7ede11f28"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_croatian.cpython-36.opt-1.pyc","mode":33188,"size":2455,"sha256":"bb17da7d9b76a2da8855410dc21b3beba5b558e12cdf6e1636343d237b4175aa"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_croatian.cpython-36.opt-2.pyc","mode":33188,"size":2321,"sha256":"7731a9349dccbc8eceb85a2e8a3e6c3805e989911030a59b98d8188e60c48897"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_croatian.cpython-36.pyc","mode":33188,"size":2455,"sha256":"bb17da7d9b76a2da8855410dc21b3beba5b558e12cdf6e1636343d237b4175aa"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_cyrillic.cpython-36.opt-1.pyc","mode":33188,"size":2445,"sha256":"1e9aed5f2e7db47087105d71f2272d8104e43cfc69412874e443ed011ab2b1a2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_cyrillic.cpython-36.opt-2.pyc","mode":33188,"size":2311,"sha256":"62fb9e31b2949f9fd3a7155e20d335ac6477fc62ea5552b5b344784c1557adf0"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_cyrillic.cpython-36.pyc","mode":33188,"size":2445,"sha256":"1e9aed5f2e7db47087105d71f2272d8104e43cfc69412874e443ed011ab2b1a2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_farsi.cpython-36.opt-1.pyc","mode":33188,"size":2389,"sha256":"7aceefab45bcb3c05e841c3e1feaf1faea93e9172d590d8a148f313420a5b0c3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_farsi.cpython-36.opt-2.pyc","mode":33188,"size":2261,"sha256":"46e222e6a87f186d473dd475edb3ed8561295080474d94889e9b20a598a181b4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_farsi.cpython-36.pyc","mode":33188,"size":2389,"sha256":"7aceefab45bcb3c05e841c3e1feaf1faea93e9172d590d8a148f313420a5b0c3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_greek.cpython-36.opt-1.pyc","mode":33188,"size":2429,"sha256":"dee6119dfb08666f2f4ef87d140b8c5788181da5f71d907a7ece0eb11baf7e97"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_greek.cpython-36.opt-2.pyc","mode":33188,"size":2301,"sha256":"e190f622cfa1186d035a9a419ee394df29703dee02d814a52887fa086dbfab9e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_greek.cpython-36.pyc","mode":33188,"size":2429,"sha256":"dee6119dfb08666f2f4ef87d140b8c5788181da5f71d907a7ece0eb11baf7e97"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_iceland.cpython-36.opt-1.pyc","mode":33188,"size":2448,"sha256":"51bc4cf81d38e6e3bd6a460c502ff52e22f317df9f5e63719bc62b6a4449c974"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_iceland.cpython-36.opt-2.pyc","mode":33188,"size":2316,"sha256":"0c0e23bf9117908ec23278cda421a09412be7da65ef36833d237685a0a4917a3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_iceland.cpython-36.pyc","mode":33188,"size":2448,"sha256":"51bc4cf81d38e6e3bd6a460c502ff52e22f317df9f5e63719bc62b6a4449c974"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_latin2.cpython-36.opt-1.pyc","mode":33188,"size":2589,"sha256":"385a4d8e112da9e7048a73a5bab85ea5c252db31bf90d4b989cc98ec3d79f2f6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_latin2.cpython-36.opt-2.pyc","mode":33188,"size":2309,"sha256":"0d00cab238624e01eaafbbbdc71a5bc2d6ebb928181d843d03e4ab3868ea27bc"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_latin2.cpython-36.pyc","mode":33188,"size":2589,"sha256":"385a4d8e112da9e7048a73a5bab85ea5c252db31bf90d4b989cc98ec3d79f2f6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_roman.cpython-36.opt-1.pyc","mode":33188,"size":2446,"sha256":"b0ea99109016ba2c6586b96724ac990901afb6fb9a6a00f970b6824d11e2d368"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_roman.cpython-36.opt-2.pyc","mode":33188,"size":2318,"sha256":"cd0e68e42d00aba553336270013fbbf6c225519206066def398884d65e2059ad"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_roman.cpython-36.pyc","mode":33188,"size":2446,"sha256":"b0ea99109016ba2c6586b96724ac990901afb6fb9a6a00f970b6824d11e2d368"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_romanian.cpython-36.opt-1.pyc","mode":33188,"size":2456,"sha256":"195647fa9ab76e71ddebfa9aaae63f26627f2227fd779d2488a6acc7fb03f974"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_romanian.cpython-36.opt-2.pyc","mode":33188,"size":2322,"sha256":"c7a2307ebd5dfb98d0345217f9319679a1ddeebc90cc8df32eaf2b13814f98b2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_romanian.cpython-36.pyc","mode":33188,"size":2456,"sha256":"195647fa9ab76e71ddebfa9aaae63f26627f2227fd779d2488a6acc7fb03f974"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_turkish.cpython-36.opt-1.pyc","mode":33188,"size":2449,"sha256":"750ec08c8e9d6985b256e3d4171831c7655d0fa578c326f435879a00c4e8dc10"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_turkish.cpython-36.opt-2.pyc","mode":33188,"size":2317,"sha256":"b24cf779203b106de4e5c4519ac6a116e55f77e63fc6bdd7433a856b43d8591f"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mac_turkish.cpython-36.pyc","mode":33188,"size":2449,"sha256":"750ec08c8e9d6985b256e3d4171831c7655d0fa578c326f435879a00c4e8dc10"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mbcs.cpython-36.opt-1.pyc","mode":33188,"size":1675,"sha256":"be9de87d42138c82361dabad25c69f9bf28f064efa711c73e2e5fcfe78aad423"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mbcs.cpython-36.opt-2.pyc","mode":33188,"size":1442,"sha256":"c3d1f7cdd6efd53dd840cb418c9431ceba9f1e255004b8273da05163550d4f4e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/mbcs.cpython-36.pyc","mode":33188,"size":1675,"sha256":"be9de87d42138c82361dabad25c69f9bf28f064efa711c73e2e5fcfe78aad423"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/oem.cpython-36.opt-1.pyc","mode":33188,"size":1488,"sha256":"bd0ba6666a068447fdb73699c635b53f99e85a99ac06d1d0b6e1f3f6c2b1d632"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/oem.cpython-36.opt-2.pyc","mode":33188,"size":1438,"sha256":"fcf0e8e5296c3feeb9a929efa4ebffb52ca18c69cf8dbc17534e6c53723ab6d2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/oem.cpython-36.pyc","mode":33188,"size":1488,"sha256":"bd0ba6666a068447fdb73699c635b53f99e85a99ac06d1d0b6e1f3f6c2b1d632"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/palmos.cpython-36.opt-1.pyc","mode":33188,"size":2436,"sha256":"d6f793e95dfc313e154e479b033d52db3e9ff06a5ee6fc05b111f8692ee68753"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/palmos.cpython-36.opt-2.pyc","mode":33188,"size":2299,"sha256":"00424c0384d1b0549ccb69d85d46f628b4ac3f429b80fc8c6119a9d1ea56056b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/palmos.cpython-36.pyc","mode":33188,"size":2436,"sha256":"d6f793e95dfc313e154e479b033d52db3e9ff06a5ee6fc05b111f8692ee68753"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/ptcp154.cpython-36.opt-1.pyc","mode":33188,"size":2530,"sha256":"aa30ea10037a8c77f20b623f6c7b3a8f979349f97ad9a436ef6405aeca48ec7e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/ptcp154.cpython-36.opt-2.pyc","mode":33188,"size":2291,"sha256":"6e5ae6a450bf3dfd585ebc70979a7c3d189c932b8ecf6e83cacee2bf693aeda4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/ptcp154.cpython-36.pyc","mode":33188,"size":2530,"sha256":"aa30ea10037a8c77f20b623f6c7b3a8f979349f97ad9a436ef6405aeca48ec7e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/punycode.cpython-36.opt-1.pyc","mode":33188,"size":6447,"sha256":"4ee3dd75e64cff20984403d38eac61982892e5ee45beb239aaee690a43c59984"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/punycode.cpython-36.opt-2.pyc","mode":33188,"size":5794,"sha256":"1899c55d7c68aa7c205ace9879c584b1eac939649edd065f262d67af2f90ad20"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/punycode.cpython-36.pyc","mode":33188,"size":6447,"sha256":"4ee3dd75e64cff20984403d38eac61982892e5ee45beb239aaee690a43c59984"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/quopri_codec.cpython-36.opt-1.pyc","mode":33188,"size":2364,"sha256":"0722e3aae8f6646bafe956df9cde34ea2918214f6e6bc453d3fee293bbb05be6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/quopri_codec.cpython-36.opt-2.pyc","mode":33188,"size":2266,"sha256":"306a94ae43158968313c62d601316edc0a62c05282177c4e45ec8e94a8f3e989"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/quopri_codec.cpython-36.pyc","mode":33188,"size":2423,"sha256":"1f7584ae7d8effcae2863dd7e565142f3ab510f33439d0558d3313feb173b436"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/raw_unicode_escape.cpython-36.opt-1.pyc","mode":33188,"size":1749,"sha256":"9d7e6a6747cb1454a246e6c97526a2370d12a8c41217dea4b67b2268cab2a5d2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/raw_unicode_escape.cpython-36.opt-2.pyc","mode":33188,"size":1590,"sha256":"8335fbf47aef0fe324abcb3d519f83fe7b4c6663d368da0676f00c18e493b9db"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/raw_unicode_escape.cpython-36.pyc","mode":33188,"size":1749,"sha256":"9d7e6a6747cb1454a246e6c97526a2370d12a8c41217dea4b67b2268cab2a5d2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/rot_13.cpython-36.opt-1.pyc","mode":33188,"size":2981,"sha256":"88d3dce3cf1f1e23e46e2825a36f7a5dd7af8312824a7eef59766a889661f387"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/rot_13.cpython-36.opt-2.pyc","mode":33188,"size":2831,"sha256":"75e01434b7edcf8ea0c37aac8aa8e3a8ac948de6d5c817fdd622878c6b179fba"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/rot_13.cpython-36.pyc","mode":33188,"size":2981,"sha256":"88d3dce3cf1f1e23e46e2825a36f7a5dd7af8312824a7eef59766a889661f387"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jis.cpython-36.opt-1.pyc","mode":33188,"size":1434,"sha256":"3305ce669e334d6d02e41101046997036f519137897211ab51b01a337a19e08a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jis.cpython-36.opt-2.pyc","mode":33188,"size":1434,"sha256":"3305ce669e334d6d02e41101046997036f519137897211ab51b01a337a19e08a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jis.cpython-36.pyc","mode":33188,"size":1434,"sha256":"3305ce669e334d6d02e41101046997036f519137897211ab51b01a337a19e08a"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jis_2004.cpython-36.opt-1.pyc","mode":33188,"size":1444,"sha256":"bfc642ffdbd3936688b23afde8eaac0d197f7de036caee6f9234fcf600876a01"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jis_2004.cpython-36.opt-2.pyc","mode":33188,"size":1444,"sha256":"bfc642ffdbd3936688b23afde8eaac0d197f7de036caee6f9234fcf600876a01"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jis_2004.cpython-36.pyc","mode":33188,"size":1444,"sha256":"bfc642ffdbd3936688b23afde8eaac0d197f7de036caee6f9234fcf600876a01"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jisx0213.cpython-36.opt-1.pyc","mode":33188,"size":1444,"sha256":"2d6bbe3ff28929b7ca2cc294509a7635cffcdf92aec1afc3ffa0a4ecb15f0709"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jisx0213.cpython-36.opt-2.pyc","mode":33188,"size":1444,"sha256":"2d6bbe3ff28929b7ca2cc294509a7635cffcdf92aec1afc3ffa0a4ecb15f0709"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/shift_jisx0213.cpython-36.pyc","mode":33188,"size":1444,"sha256":"2d6bbe3ff28929b7ca2cc294509a7635cffcdf92aec1afc3ffa0a4ecb15f0709"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/tis_620.cpython-36.opt-1.pyc","mode":33188,"size":2498,"sha256":"97546028e9decfa8c048c2a9933d6bc3c6fd4756fc76d6d2d6af54c3cfc8e1be"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/tis_620.cpython-36.opt-2.pyc","mode":33188,"size":2377,"sha256":"df34d65054b176452aad80bb674f97848230b0cc9f19c956448d6a45586631de"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/tis_620.cpython-36.pyc","mode":33188,"size":2498,"sha256":"97546028e9decfa8c048c2a9933d6bc3c6fd4756fc76d6d2d6af54c3cfc8e1be"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/undefined.cpython-36.opt-1.pyc","mode":33188,"size":2143,"sha256":"167c3903aa3b3f9a00be48d78992dfd97e39a3390aed09d5e21327e6ad49a685"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/undefined.cpython-36.opt-2.pyc","mode":33188,"size":1814,"sha256":"ebe288eeb0459ee770a901e2b29b519dcf62e345fef24dd407a902a0b7c5bba7"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/undefined.cpython-36.pyc","mode":33188,"size":2143,"sha256":"167c3903aa3b3f9a00be48d78992dfd97e39a3390aed09d5e21327e6ad49a685"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/unicode_escape.cpython-36.opt-1.pyc","mode":33188,"size":1729,"sha256":"32189c4edbd42e45d84b9115e6ffe677e3d2d912af76fd86f4abd8a1ce76e646"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/unicode_escape.cpython-36.opt-2.pyc","mode":33188,"size":1574,"sha256":"581916814cb28f133cbf37c5762a7e156d104d46f97fba23f5df91d6941ce83e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/unicode_escape.cpython-36.pyc","mode":33188,"size":1729,"sha256":"32189c4edbd42e45d84b9115e6ffe677e3d2d912af76fd86f4abd8a1ce76e646"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/unicode_internal.cpython-36.opt-1.pyc","mode":33188,"size":1739,"sha256":"b60da32f8bcbfd17c78b96c7f47f20b158f291836a63474d6974c77085d403b0"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/unicode_internal.cpython-36.opt-2.pyc","mode":33188,"size":1582,"sha256":"d8cc2da2dc3bc1f3007082bc8a6fee087bd6238dd935f53758512313b659ebb6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/unicode_internal.cpython-36.pyc","mode":33188,"size":1739,"sha256":"b60da32f8bcbfd17c78b96c7f47f20b158f291836a63474d6974c77085d403b0"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16.cpython-36.opt-1.pyc","mode":33188,"size":4813,"sha256":"f76cc7b9fb03cda20ea23d7462ca2c5cbc9cb7dd5ae6aa2d60c977ac998a00ad"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16.cpython-36.opt-2.pyc","mode":33188,"size":4666,"sha256":"90dc6d1b1488e7808bc6597df987cd44880eaec0d67f7b932aa168a220c9a217"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16.cpython-36.pyc","mode":33188,"size":4813,"sha256":"f76cc7b9fb03cda20ea23d7462ca2c5cbc9cb7dd5ae6aa2d60c977ac998a00ad"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16_be.cpython-36.opt-1.pyc","mode":33188,"size":1614,"sha256":"268dfa413bc22540b41081eab9743583331cf7038bb6069e97914f04cf82cdd9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16_be.cpython-36.opt-2.pyc","mode":33188,"size":1464,"sha256":"61901a97b7a507b26ec5dd9bdec450db519becea07502824302a7fa4475cd4e4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16_be.cpython-36.pyc","mode":33188,"size":1614,"sha256":"268dfa413bc22540b41081eab9743583331cf7038bb6069e97914f04cf82cdd9"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16_le.cpython-36.opt-1.pyc","mode":33188,"size":1614,"sha256":"c7c3c19be8714856caa99f72e6325a0b12c45bb4ae3871bca24a3c79888152f6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16_le.cpython-36.opt-2.pyc","mode":33188,"size":1464,"sha256":"82ccc1c8d6fbbf40afd59ebd69bc6473aef07ef46670fd6deac2e09216e72dae"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_16_le.cpython-36.pyc","mode":33188,"size":1614,"sha256":"c7c3c19be8714856caa99f72e6325a0b12c45bb4ae3871bca24a3c79888152f6"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32.cpython-36.opt-1.pyc","mode":33188,"size":4706,"sha256":"dcfe347911379cf56e7658da5ea416752b2983396ed22cd9f583a53af72594f2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32.cpython-36.opt-2.pyc","mode":33188,"size":4666,"sha256":"670e2695fc59cabf32797731ea1e819182bd732317d1b117fd6f172fcd0ac9c2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32.cpython-36.pyc","mode":33188,"size":4706,"sha256":"dcfe347911379cf56e7658da5ea416752b2983396ed22cd9f583a53af72594f2"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32_be.cpython-36.opt-1.pyc","mode":33188,"size":1507,"sha256":"b9685c1407066a232a883f1ffd288d36c719786ab54be5f37871276350c52a18"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32_be.cpython-36.opt-2.pyc","mode":33188,"size":1464,"sha256":"bed09f14592e33e96131cb31ef6e866e160f74ffc677fc5a45645d7ba7cde14e"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32_be.cpython-36.pyc","mode":33188,"size":1507,"sha256":"b9685c1407066a232a883f1ffd288d36c719786ab54be5f37871276350c52a18"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32_le.cpython-36.opt-1.pyc","mode":33188,"size":1507,"sha256":"131fbf28638396fdd3e4aae572b998fab4dfedf75f2091c8b07aa9e77d4121e3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32_le.cpython-36.opt-2.pyc","mode":33188,"size":1464,"sha256":"a1f9d50bf455e72bd4a185f24a5257b6849c47fafc917c2ff4a6acd6fa41bcdf"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_32_le.cpython-36.pyc","mode":33188,"size":1507,"sha256":"131fbf28638396fdd3e4aae572b998fab4dfedf75f2091c8b07aa9e77d4121e3"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_7.cpython-36.opt-1.pyc","mode":33188,"size":1535,"sha256":"3137278d060bfed296c33c825358f6b0d4b7ed83cebe46683a596db4457bd1c4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_7.cpython-36.opt-2.pyc","mode":33188,"size":1448,"sha256":"6eade47f63cce15eed602648eb3dc21324a69fcebe144ac29aaa6cde19d900bc"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_7.cpython-36.pyc","mode":33188,"size":1535,"sha256":"3137278d060bfed296c33c825358f6b0d4b7ed83cebe46683a596db4457bd1c4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_8.cpython-36.opt-1.pyc","mode":33188,"size":1594,"sha256":"33a403fb0d00c8ceec9ed6c00cf1b843ef7e19a92a2e1261dfd51b0621859233"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_8.cpython-36.opt-2.pyc","mode":33188,"size":1448,"sha256":"0e6ec628a1b80bde942639bd939d58666ba196c46f075986d76994272fa51ad4"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_8.cpython-36.pyc","mode":33188,"size":1594,"sha256":"33a403fb0d00c8ceec9ed6c00cf1b843ef7e19a92a2e1261dfd51b0621859233"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_8_sig.cpython-36.opt-1.pyc","mode":33188,"size":4511,"sha256":"80abe01d06c669a9d29d7b03a575e3b716210d67164034ddaa082a84f748b5eb"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_8_sig.cpython-36.opt-2.pyc","mode":33188,"size":4209,"sha256":"5bfd36b208cf92951494bf51947bd9874074a5630b74f5e1e087a5889c96f15b"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/utf_8_sig.cpython-36.pyc","mode":33188,"size":4511,"sha256":"80abe01d06c669a9d29d7b03a575e3b716210d67164034ddaa082a84f748b5eb"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/uu_codec.cpython-36.opt-1.pyc","mode":33188,"size":3148,"sha256":"23e028c73cb72909f52b631b70cd37239a20e668685199a2fdcb0a1a3ea36f64"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/uu_codec.cpython-36.opt-2.pyc","mode":33188,"size":2855,"sha256":"00434a67252927e257c1489f84d5c7a6a45d9f2e01337f270f376d661e4e1ad1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/uu_codec.cpython-36.pyc","mode":33188,"size":3207,"sha256":"145c7520207868561cd5de8df27dd48c52daca448d2b8d76cbe955617bd1609d"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/zlib_codec.cpython-36.opt-1.pyc","mode":33188,"size":2996,"sha256":"c720b85857908307b91622bf99c3d1fcdd7116f57202a264a2008bbf9b4d4ea1"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/zlib_codec.cpython-36.opt-2.pyc","mode":33188,"size":2830,"sha256":"3dcfbaa8228123153884da3d4c0ecfcc5f6406309968aaf0b326304bb4abafcf"},{"path":"/usr/lib64/python3.6/encodings/__pycache__/zlib_codec.cpython-36.pyc","mode":33188,"size":3103,"sha256":"2b367b227bbadee46406d55793fb0f99e5ae73c032bb73617af12a54d36f3d41"},{"path":"/usr/lib64/python3.6/encodings/aliases.py","mode":33188,"size":15577,"sha256":"b30d0e742e54d73bd35b26209689611713f105296485ffa97f79f20441c72250"},{"path":"/usr/lib64/python3.6/encodings/ascii.py","mode":33188,"size":1248,"sha256":"578aa1173f7cc60dad2895071287fe6182bd14787b3fbf47a6c7983dfe3675e3"},{"path":"/usr/lib64/python3.6/encodings/base64_codec.py","mode":33188,"size":1533,"sha256":"cf9ac7a464f541492486241d1b4bf33e37b45c6499275cc4d69c5a8e564e5976"},{"path":"/usr/lib64/python3.6/encodings/big5.py","mode":33188,"size":1019,"sha256":"98fac6f86a20dd05da197e2058176ebfd47edee7074c3248f5f48fe0fb672d7c"},{"path":"/usr/lib64/python3.6/encodings/big5hkscs.py","mode":33188,"size":1039,"sha256":"21d051a00fb5c6a86ba187e0c50e811d659ce00991fd5f5b408f71ebb2ef0f16"},{"path":"/usr/lib64/python3.6/encodings/bz2_codec.py","mode":33188,"size":2249,"sha256":"1181a2a89102a2b1d2b2f1f4473236d5d1ececdd0be8fdaa498a3dbe21a185ab"},{"path":"/usr/lib64/python3.6/encodings/charmap.py","mode":33188,"size":2084,"sha256":"1b8b5fdb36ce3becc62a6115ed904a17083949ec8aaef5a80f7078cec232f43b"},{"path":"/usr/lib64/python3.6/encodings/cp037.py","mode":33188,"size":13121,"sha256":"fda6ca994d710e4e0c760e0204c29a4273fc0f14ebe3169306d2eb54c9953f58"},{"path":"/usr/lib64/python3.6/encodings/cp1006.py","mode":33188,"size":13568,"sha256":"eaded38b427841bdf280e878f1e26da506e743eaa9429075332af60cce429473"},{"path":"/usr/lib64/python3.6/encodings/cp1026.py","mode":33188,"size":13113,"sha256":"f5227237dd7ce5005b16a8e4d8342f0d193193c878e3cf35b9305d22b3b1aaf9"},{"path":"/usr/lib64/python3.6/encodings/cp1125.py","mode":33188,"size":34597,"sha256":"f84c7d30ce222e6a50cff1a4c9737173411da108cbd2c9bb57c854480103c470"},{"path":"/usr/lib64/python3.6/encodings/cp1140.py","mode":33188,"size":13105,"sha256":"3379d78b244aa905ffe1171a968caaf41b9a0154d1ddc76c05a2abaca2b289fd"},{"path":"/usr/lib64/python3.6/encodings/cp1250.py","mode":33188,"size":13686,"sha256":"ebcec1adf9167863fb0bab29708c546300c80a77ef07838c9e0437a59e265970"},{"path":"/usr/lib64/python3.6/encodings/cp1251.py","mode":33188,"size":13361,"sha256":"d57f8cfa34494c5acb6692ddb31f616ae2dd89a075d2af6d36b0b7ec2ffe7af1"},{"path":"/usr/lib64/python3.6/encodings/cp1252.py","mode":33188,"size":13511,"sha256":"19aa5bee667f5fb387924a813aec9fa1dda47769d09e8483a748bdb202be6a84"},{"path":"/usr/lib64/python3.6/encodings/cp1253.py","mode":33188,"size":13094,"sha256":"8c27696dcfb6894b378869bc89f113703fbd1e9b13a83934463d5999b055d1e8"},{"path":"/usr/lib64/python3.6/encodings/cp1254.py","mode":33188,"size":13502,"sha256":"06517ec2f74f1c6562d0a1a500c48ba43f2e6e9d0c3d28356d747f274f1a4c8d"},{"path":"/usr/lib64/python3.6/encodings/cp1255.py","mode":33188,"size":12466,"sha256":"54a1b5087578fa78e5bdd0afa6a9e80e8c5467c1e4226cf6e586cfe7a674a653"},{"path":"/usr/lib64/python3.6/encodings/cp1256.py","mode":33188,"size":12814,"sha256":"ad3768ac2fef2a646b3301c20af705f4d4a1544f22fa8a84241bada27ab84133"},{"path":"/usr/lib64/python3.6/encodings/cp1257.py","mode":33188,"size":13374,"sha256":"d9149d2925b3f719809ef2297e541461079f15c658af207a3e498be314ab2c6b"},{"path":"/usr/lib64/python3.6/encodings/cp1258.py","mode":33188,"size":13364,"sha256":"672e05b51952a82c8dbd5603769195fcedf565e457bb86c0d5bae04955d04630"},{"path":"/usr/lib64/python3.6/encodings/cp273.py","mode":33188,"size":14132,"sha256":"6c6aec3b213ea3aebc2c526dd4d121c95d4a25a2fc928a87cd80f8448988185f"},{"path":"/usr/lib64/python3.6/encodings/cp424.py","mode":33188,"size":12055,"sha256":"30414c2186ea0802bbf3db034122ddec1f8a10061b97c50871e14b74ee36d0ca"},{"path":"/usr/lib64/python3.6/encodings/cp437.py","mode":33188,"size":34564,"sha256":"5c2a5015cd36cf7f561269f33dec4c323093d3d88b0673969accdabdcb9ce2cb"},{"path":"/usr/lib64/python3.6/encodings/cp500.py","mode":33188,"size":13121,"sha256":"630f503f9110d98ea3e1529f2f965ebc275a2f78d3de47f8e9b69d35589d764b"},{"path":"/usr/lib64/python3.6/encodings/cp65001.py","mode":33188,"size":1106,"sha256":"3b392c36ef590f40a66bace6eb3d86dcb578c1f8becb6ba0eb9fe116bddbdeb2"},{"path":"/usr/lib64/python3.6/encodings/cp720.py","mode":33188,"size":13686,"sha256":"395496001271b92efe5df07fc0ae7c3410d1dd2bdfebbd3e4d8e806c8166beb0"},{"path":"/usr/lib64/python3.6/encodings/cp737.py","mode":33188,"size":34681,"sha256":"be3ca1785a3970ec62310710eaf7de82932181b04d06fe4528f8adaba9fb8c4b"},{"path":"/usr/lib64/python3.6/encodings/cp775.py","mode":33188,"size":34476,"sha256":"e0dba85b99329d7f16907e620adada06be5216abcb964406c827b569b2cf1aeb"},{"path":"/usr/lib64/python3.6/encodings/cp850.py","mode":33188,"size":34105,"sha256":"257e29f235e2a8790dd68cee45668776648bab809ce8584f893cdd8fd007993c"},{"path":"/usr/lib64/python3.6/encodings/cp852.py","mode":33188,"size":35002,"sha256":"cc6faaa9dc4a933127da0aaacd1dc7a44c09266051af56bfe3215ff228636b6b"},{"path":"/usr/lib64/python3.6/encodings/cp855.py","mode":33188,"size":33850,"sha256":"7b25c61c9e8c47b218d3fbb801541a2861926ac712843d2113fff90e2074f5ba"},{"path":"/usr/lib64/python3.6/encodings/cp856.py","mode":33188,"size":12423,"sha256":"2e52ec5cb1eafa6739b5569b0b98ee89df5f7358b84ccdc8da64e86f017d359f"},{"path":"/usr/lib64/python3.6/encodings/cp857.py","mode":33188,"size":33908,"sha256":"8d1b769058bfccdb3c6c70c49a104f5081a2fcc9fad68f7b5eb3e4f67f0b33da"},{"path":"/usr/lib64/python3.6/encodings/cp858.py","mode":33188,"size":34015,"sha256":"a24930c4a6ad0ff66dde9a69f2027e4b92c2c9c61dcda2992e940654c606577b"},{"path":"/usr/lib64/python3.6/encodings/cp860.py","mode":33188,"size":34681,"sha256":"2dfae7e31d3d9aa3013cff44a4d7ad842f257ac63765a9998436701b629cd86a"},{"path":"/usr/lib64/python3.6/encodings/cp861.py","mode":33188,"size":34633,"sha256":"701930d77a2177497586e99bc3fe60f2d4beffb645608f167c76874a72ff405e"},{"path":"/usr/lib64/python3.6/encodings/cp862.py","mode":33188,"size":33370,"sha256":"15a2844b6ed9544c6400cf7299b42d0c2bef93c9bee70a9e89f66b8610ad6d6d"},{"path":"/usr/lib64/python3.6/encodings/cp863.py","mode":33188,"size":34252,"sha256":"a3d57f61fce1b98fc81ea8e4ebebaf402fae40bbcdd35d4b8297b9bb49a79aa2"},{"path":"/usr/lib64/python3.6/encodings/cp864.py","mode":33188,"size":33663,"sha256":"15ad8f1fdfdd842c7522241372e7eddda7df687e815692a89157c5f256f21a08"},{"path":"/usr/lib64/python3.6/encodings/cp865.py","mode":33188,"size":34618,"sha256":"bdbaded987242ed2a8de7133ec2f61ddcc1c2e9de27816ab7cd0a4c678a3a907"},{"path":"/usr/lib64/python3.6/encodings/cp866.py","mode":33188,"size":34396,"sha256":"9efcc8e85bbd1687272a0991f6d0429a4c06679db2d114b2ac95db27a70f9d13"},{"path":"/usr/lib64/python3.6/encodings/cp869.py","mode":33188,"size":32965,"sha256":"52582d9fb769b24eac7154f18d7dae856588297d6da98f37fb5efd8da883826d"},{"path":"/usr/lib64/python3.6/encodings/cp874.py","mode":33188,"size":12595,"sha256":"fe4752fa2e65741e08a563a31ff914fe71068942ce9c6f4070b1dfd7b25e5e7f"},{"path":"/usr/lib64/python3.6/encodings/cp875.py","mode":33188,"size":12854,"sha256":"2fe72632015db2cba2bb4367055551da6fe22051b96d170c7b96fa271c46b257"},{"path":"/usr/lib64/python3.6/encodings/cp932.py","mode":33188,"size":1023,"sha256":"99748e28113d2d49f5d666b49b78accd2c6e10a7852f7dd6dece9b5b71aa83c4"},{"path":"/usr/lib64/python3.6/encodings/cp949.py","mode":33188,"size":1023,"sha256":"950a7d29467ce0590b4a1137830d43d88d8f20e4035dcaaa8b2a5c3c3f1de962"},{"path":"/usr/lib64/python3.6/encodings/cp950.py","mode":33188,"size":1023,"sha256":"27811178b450731fc955b1247656a605d04e5ee98e0d585e4596b94b703a27f6"},{"path":"/usr/lib64/python3.6/encodings/euc_jis_2004.py","mode":33188,"size":1051,"sha256":"9fa426cd9f17629f6320700ed18baa94839304cf1bcabbee7edb501747dc055d"},{"path":"/usr/lib64/python3.6/encodings/euc_jisx0213.py","mode":33188,"size":1051,"sha256":"e28315910da20218dae8b7d5becd81de1e283dfd8b0415a4980d67065de73a0b"},{"path":"/usr/lib64/python3.6/encodings/euc_jp.py","mode":33188,"size":1027,"sha256":"b453a439787b0efa031e43416a7d852a6be705c985e1200693eb96d87ea79cdc"},{"path":"/usr/lib64/python3.6/encodings/euc_kr.py","mode":33188,"size":1027,"sha256":"633a1a5504bfad04b1ec9c96d44d4ebb3bb99066a218318e7d67d866e20887a6"},{"path":"/usr/lib64/python3.6/encodings/gb18030.py","mode":33188,"size":1031,"sha256":"6c10b4dc49bc63724e539137ede6936304fcca1c97c28d16d89f381e10849521"},{"path":"/usr/lib64/python3.6/encodings/gb2312.py","mode":33188,"size":1027,"sha256":"3d2d567d8d079b78f3f3b566ed52ad2f38af61bf832b7dc28858b0039a032d6b"},{"path":"/usr/lib64/python3.6/encodings/gbk.py","mode":33188,"size":1015,"sha256":"eff9b8cbc9ad2ef2e10e96afa83d3db1f775ea044aed275b7a35574ae0d8645b"},{"path":"/usr/lib64/python3.6/encodings/hex_codec.py","mode":33188,"size":1508,"sha256":"fc5f0a31b59efe990b86efb98936769f33dd91d912ce55b49a5a4cfc516cd047"},{"path":"/usr/lib64/python3.6/encodings/hp_roman8.py","mode":33188,"size":13475,"sha256":"c43cce763d12e8f71a63dbc16641bd87147eaf5f9d9054ea856864b216b2735b"},{"path":"/usr/lib64/python3.6/encodings/hz.py","mode":33188,"size":1011,"sha256":"025a9531e3046e52d3e039c0be04f9a5a74651d7683a13c7c7ebd4c7dfb5996a"},{"path":"/usr/lib64/python3.6/encodings/idna.py","mode":33188,"size":9170,"sha256":"dcce0dd086f2cccd6198458a39af670291786b3a14c003ba5989817f773a7e84"},{"path":"/usr/lib64/python3.6/encodings/iso2022_jp.py","mode":33188,"size":1053,"sha256":"461a0e7f72eccb8b29f351c4e7926cfbda58e0edd6d0770bd82e0b36c5febe77"},{"path":"/usr/lib64/python3.6/encodings/iso2022_jp_1.py","mode":33188,"size":1061,"sha256":"63bacad13a979a5519fcaa4f1e1e07b2c7415005167fac3a689408c7d886fabd"},{"path":"/usr/lib64/python3.6/encodings/iso2022_jp_2.py","mode":33188,"size":1061,"sha256":"5d4248181548b0fc89a9f5ee9cf52ebecb235708ba87d47896ad14130884ef9f"},{"path":"/usr/lib64/python3.6/encodings/iso2022_jp_2004.py","mode":33188,"size":1073,"sha256":"b4d1468bcd608b46f38cb0c6ef115510dcf9aa0f71e590792f407efc6e165164"},{"path":"/usr/lib64/python3.6/encodings/iso2022_jp_3.py","mode":33188,"size":1061,"sha256":"3aceaa5661909de14e2861d864443b8472460ce39b99cce5c6965346d47aa5ac"},{"path":"/usr/lib64/python3.6/encodings/iso2022_jp_ext.py","mode":33188,"size":1069,"sha256":"f4c9ed8f3031995faa224bcb10153d2b6144944477d1f27d1a6cc4a879fac34c"},{"path":"/usr/lib64/python3.6/encodings/iso2022_kr.py","mode":33188,"size":1053,"sha256":"1c86362e17944f0bcf68db02f4995bdeea605867795fff7ab4079073f96705e4"},{"path":"/usr/lib64/python3.6/encodings/iso8859_1.py","mode":33188,"size":13176,"sha256":"b5cebd515e057d670bf54e10b8a6f162ef3daa7f21b146aee3249160caf3c32d"},{"path":"/usr/lib64/python3.6/encodings/iso8859_10.py","mode":33188,"size":13589,"sha256":"54c886b41819ebb7f4fb34b8dbae1c45f4fc0864f019ecd772676ccfac5fae7b"},{"path":"/usr/lib64/python3.6/encodings/iso8859_11.py","mode":33188,"size":12335,"sha256":"ed5a964470a241b4da7a6cfb718e4149d09644933af38f0497602baab6e563ef"},{"path":"/usr/lib64/python3.6/encodings/iso8859_13.py","mode":33188,"size":13271,"sha256":"7312237e8e5d201d920b4130f057cfdf1b0be9baafaa246826e6d93204fcc206"},{"path":"/usr/lib64/python3.6/encodings/iso8859_14.py","mode":33188,"size":13652,"sha256":"82778b995a0ee87c5f1180fcc52900359eee15bd9a6e3a0e25f0d963e0b2a343"},{"path":"/usr/lib64/python3.6/encodings/iso8859_15.py","mode":33188,"size":13212,"sha256":"01976a81811873dc9a0c79db9fc00d1c30103487f3c6bc3a6d81b4043cd48e02"},{"path":"/usr/lib64/python3.6/encodings/iso8859_16.py","mode":33188,"size":13557,"sha256":"b5ac8f5a5d8f84c0f903b2b7c342184758d590d8bcf810d561f942fe5b372d66"},{"path":"/usr/lib64/python3.6/encodings/iso8859_2.py","mode":33188,"size":13404,"sha256":"2b57cab6111cae9021505e3ae1b2adbbfc344ec48165fda322f6b069fbb18adc"},{"path":"/usr/lib64/python3.6/encodings/iso8859_3.py","mode":33188,"size":13089,"sha256":"4ffdf89004bf0c5230caa7079f7ca3142fc112f8b923ddb2c7358369d2d3c242"},{"path":"/usr/lib64/python3.6/encodings/iso8859_4.py","mode":33188,"size":13376,"sha256":"87bd130daa0eaef3e4cb465e10cffb2bcd194ff74097e0c186b4b8eb7be41ac5"},{"path":"/usr/lib64/python3.6/encodings/iso8859_5.py","mode":33188,"size":13015,"sha256":"9961d96cc7b9fdf011ebcaaeaeca7b50b8670fadbd7b75fde66192f8c1f68f30"},{"path":"/usr/lib64/python3.6/encodings/iso8859_6.py","mode":33188,"size":10833,"sha256":"4840e68014346517680f593ca22f67133c39ba7e46f34b9be62c980a728448c6"},{"path":"/usr/lib64/python3.6/encodings/iso8859_7.py","mode":33188,"size":12844,"sha256":"b352eca3b819488f64fb3338fd93f39c1e30f32bb13f2f9c577925e58f2960e4"},{"path":"/usr/lib64/python3.6/encodings/iso8859_8.py","mode":33188,"size":11036,"sha256":"4cf9e8a8bbe04accb1c1a80853efb19ae0772d18f81e270adefc1b2386cb368e"},{"path":"/usr/lib64/python3.6/encodings/iso8859_9.py","mode":33188,"size":13156,"sha256":"84d9b15263e81685f7513c5ab45caf80b2f73c301c68e659f7162c1b1882d359"},{"path":"/usr/lib64/python3.6/encodings/johab.py","mode":33188,"size":1023,"sha256":"9586615917afd3d848c1c4328656603b2834af6115f2aec932fccc935e1a60fb"},{"path":"/usr/lib64/python3.6/encodings/koi8_r.py","mode":33188,"size":13779,"sha256":"4d4e353aee8039bb71e2145a6e68fe1e6833a1b4250b70ee0ac5ec70bbb8c51d"},{"path":"/usr/lib64/python3.6/encodings/koi8_t.py","mode":33188,"size":13193,"sha256":"9c9043814abdbe7dc39ff98f3857d5d110a84c978ad2304158d810a4e9eacef1"},{"path":"/usr/lib64/python3.6/encodings/koi8_u.py","mode":33188,"size":13762,"sha256":"d449f9858e357fa8c2edbd4b9fe739337e9f201cac3ded20f99bfcecd4970ff7"},{"path":"/usr/lib64/python3.6/encodings/kz1048.py","mode":33188,"size":13723,"sha256":"76beb30e98a911f72f97609a2373782573c17c88a5fb3537db338aa382979ffc"},{"path":"/usr/lib64/python3.6/encodings/latin_1.py","mode":33188,"size":1264,"sha256":"b75503e532a27c636477396c855209ff5f3036536d2a4bede0a576c89382b60c"},{"path":"/usr/lib64/python3.6/encodings/mac_arabic.py","mode":33188,"size":36467,"sha256":"5eafd9a3136abfbd8ed52df9c90203c7a283e7429ed60502a87a02511e0fb777"},{"path":"/usr/lib64/python3.6/encodings/mac_centeuro.py","mode":33188,"size":14102,"sha256":"76e90ef586a10ffcfc5991317266f622c65b3ecdd382b51c9e79421e1b32c0f5"},{"path":"/usr/lib64/python3.6/encodings/mac_croatian.py","mode":33188,"size":13633,"sha256":"a880cd05c82a8d11a29c65ee86a396def3344465dd71441b0bb4a73826024953"},{"path":"/usr/lib64/python3.6/encodings/mac_cyrillic.py","mode":33188,"size":13454,"sha256":"83616786a1c6308b03a0dc82536908d24d0974b2248d67393d613fe558cea4bd"},{"path":"/usr/lib64/python3.6/encodings/mac_farsi.py","mode":33188,"size":15170,"sha256":"f5763c38fb4ab0423fafe2fdca34d6f9932ac7f1a74c0cd8109d60234c7dc624"},{"path":"/usr/lib64/python3.6/encodings/mac_greek.py","mode":33188,"size":13721,"sha256":"63016a323ddf98cb3aa9cfa78f3bab4768bedbfe9a5262a36a5aecb13d291f6e"},{"path":"/usr/lib64/python3.6/encodings/mac_iceland.py","mode":33188,"size":13498,"sha256":"753cc1ac635caa7e1b4630fbcebef8db8db332c098154a5b11f652912bf64f37"},{"path":"/usr/lib64/python3.6/encodings/mac_latin2.py","mode":33188,"size":14118,"sha256":"31670da18ce8b5394cd53fe6bf216268e7e8eae4c0247532e420e2e103727d50"},{"path":"/usr/lib64/python3.6/encodings/mac_roman.py","mode":33188,"size":13480,"sha256":"230367d96aef8e8d7f185b4acfb84923714f39ddbcbf9cf38a06bf6f5d621c22"},{"path":"/usr/lib64/python3.6/encodings/mac_romanian.py","mode":33188,"size":13661,"sha256":"49630cf035c19e896a123ed6e5fee18b5e485123daf2f15da38bf727ff387bee"},{"path":"/usr/lib64/python3.6/encodings/mac_turkish.py","mode":33188,"size":13513,"sha256":"99758a5cad2825cb3be3fa5d031e0821e4eba910a46f417fd890207b9b6be77b"},{"path":"/usr/lib64/python3.6/encodings/mbcs.py","mode":33188,"size":1211,"sha256":"f6ed445ed537c9f856d8defe8b56505727737d0dc9348d0a877abedab4bdd864"},{"path":"/usr/lib64/python3.6/encodings/oem.py","mode":33188,"size":1019,"sha256":"481656d3a35f792d0e5109e3f821e6dbfcf097163a19b0cdfcbff3b3db99292f"},{"path":"/usr/lib64/python3.6/encodings/palmos.py","mode":33188,"size":13519,"sha256":"eccf7418adefcc2a59e9a07fc4e34363bd62f7e878d48c8a02730a8ed1c584c8"},{"path":"/usr/lib64/python3.6/encodings/ptcp154.py","mode":33188,"size":14015,"sha256":"0eabcb2c287d335e86b71b0abe5718bd6ddc9aaee234f0f0f2363845d2926d8d"},{"path":"/usr/lib64/python3.6/encodings/punycode.py","mode":33188,"size":6881,"sha256":"0e1b1cae2fd1a76437c0f222490755cacc5f8e55fe21d30635f6588571878215"},{"path":"/usr/lib64/python3.6/encodings/quopri_codec.py","mode":33188,"size":1525,"sha256":"502a213c34c05a94ed063ee03f47680bd6efbb35036e06fb4dc809bf398cfa64"},{"path":"/usr/lib64/python3.6/encodings/raw_unicode_escape.py","mode":33188,"size":1208,"sha256":"d61709ea224423c790d23069fe8ffb8551461e94a787bc5417a263e95f408c68"},{"path":"/usr/lib64/python3.6/encodings/rot_13.py","mode":33261,"size":2438,"sha256":"033609bc1a50a8e1932a2699fd496c0d5f8ab740f215110c924ec35a128e4c67"},{"path":"/usr/lib64/python3.6/encodings/shift_jis.py","mode":33188,"size":1039,"sha256":"ad4ac50ebf58294304e412cc0f1b12980988dd6edc414e4110029c0a1abbe966"},{"path":"/usr/lib64/python3.6/encodings/shift_jis_2004.py","mode":33188,"size":1059,"sha256":"d21c5930f21063ea78fea3b0f76dfb8fd92858d2a4a200064a52126a43dd1a99"},{"path":"/usr/lib64/python3.6/encodings/shift_jisx0213.py","mode":33188,"size":1059,"sha256":"2c8d0b93bb36edf31c1236b1b4d1c0008553868bd2fc9137570115b96b834f2e"},{"path":"/usr/lib64/python3.6/encodings/tis_620.py","mode":33188,"size":12300,"sha256":"647c4719e2c1a7375105e15a89b377c66f6b699977dcabbb71d923a4607b7902"},{"path":"/usr/lib64/python3.6/encodings/undefined.py","mode":33188,"size":1299,"sha256":"85bba5c5e1007cd8c1ade5c0214bcc825396d2bbd02054e62a9f162104748b64"},{"path":"/usr/lib64/python3.6/encodings/unicode_escape.py","mode":33188,"size":1184,"sha256":"17d59827cb8c05405d86b00bc6949316d179395e3556b3de90d1e94cf7d67c93"},{"path":"/usr/lib64/python3.6/encodings/unicode_internal.py","mode":33188,"size":1196,"sha256":"5230e071c3cdd02ed01e12376549e30de0ea9a5b6a1879f549ad24b919b23bfb"},{"path":"/usr/lib64/python3.6/encodings/utf_16.py","mode":33188,"size":5236,"sha256":"6c36257f7b8d214473560d195e71bccef0c69a53e1e52d2800b7a7890aad7e58"},{"path":"/usr/lib64/python3.6/encodings/utf_16_be.py","mode":33188,"size":1037,"sha256":"3357196f3fa52433326a6626880e34964e00c5570aee50e9a0a0a7c6d86f6e4f"},{"path":"/usr/lib64/python3.6/encodings/utf_16_le.py","mode":33188,"size":1037,"sha256":"3aedaf3eb49769282daef1eaedfd4fa1c31fe5eebeff67fe2307c89dc2e2fd80"},{"path":"/usr/lib64/python3.6/encodings/utf_32.py","mode":33188,"size":5129,"sha256":"2072eece5f6026ad2d3549ab193a9e38894ea15ca9d5b3cd408fd6b116acc0c2"},{"path":"/usr/lib64/python3.6/encodings/utf_32_be.py","mode":33188,"size":930,"sha256":"cbba20e1f6d0879c7c4293446c371a9f79e7c90bf3c78a77a9b8fc72b18915dd"},{"path":"/usr/lib64/python3.6/encodings/utf_32_le.py","mode":33188,"size":930,"sha256":"9134b91047d85b442898d59effe23e7e0cf4167ca341ae31119a731dbf880a7b"},{"path":"/usr/lib64/python3.6/encodings/utf_7.py","mode":33188,"size":946,"sha256":"9ff32314f4f1fa074f206bbf7fdb851504e5313128636d73b4bf75b886e4a87d"},{"path":"/usr/lib64/python3.6/encodings/utf_8.py","mode":33188,"size":1005,"sha256":"ba0cac060269583523ca9506473a755203037c57d466a11aa89a30a5f6756f3d"},{"path":"/usr/lib64/python3.6/encodings/utf_8_sig.py","mode":33188,"size":4133,"sha256":"1ef3da8d8aa08149e7f274dc64dbfce2155da812e5258ca8e8f832428d3b5c2d"},{"path":"/usr/lib64/python3.6/encodings/uu_codec.py","mode":33188,"size":2721,"sha256":"991f4d2179008828a759c91fbeb1958cb623e0c993af837b35ab89f48d54cd8a"},{"path":"/usr/lib64/python3.6/encodings/zlib_codec.py","mode":33188,"size":2204,"sha256":"6ef01e8d3a5fe1cc52f7b5ae008df12f1dbce7304111bf8d4758f1bfc0115759"},{"path":"/usr/lib64/python3.6/ensurepip/__init__.py","mode":33188,"size":6992,"sha256":"ee794108085eff250132cfd99a386e7d6db53c44b0fe61f2b5d39ccd97c023a5"},{"path":"/usr/lib64/python3.6/ensurepip/__main__.py","mode":33188,"size":88,"sha256":"ee735f518d0fc4dfec81f7aa3da1e052372ed4202c0da4eddd2587840beaecd7"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":5585,"sha256":"9738bcb7e29d7253972eaaef61ea5f212998a29e7c4988df6886ffb81ee74b3a"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":5008,"sha256":"b3faf4510ba53513eb2fdd7a3e8f1a8c5f3e8b652b1b2e87272c9c6c63994be8"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":5585,"sha256":"9738bcb7e29d7253972eaaef61ea5f212998a29e7c4988df6886ffb81ee74b3a"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/__main__.cpython-36.opt-1.pyc","mode":33188,"size":220,"sha256":"f67c9b88edc4b572a0d2d97753dc2abd61d05ef834b5125eacb56e380bac953a"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/__main__.cpython-36.opt-2.pyc","mode":33188,"size":220,"sha256":"f67c9b88edc4b572a0d2d97753dc2abd61d05ef834b5125eacb56e380bac953a"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/__main__.cpython-36.pyc","mode":33188,"size":220,"sha256":"f67c9b88edc4b572a0d2d97753dc2abd61d05ef834b5125eacb56e380bac953a"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/_uninstall.cpython-36.opt-1.pyc","mode":33188,"size":918,"sha256":"e4d1449d13c00bf69dee9f82c980912530767b4831032a60df0cb3845b9a0046"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/_uninstall.cpython-36.opt-2.pyc","mode":33188,"size":833,"sha256":"f6fda595bd12c032184e575ae32284dace6ff492aae41c08061ab35072626837"},{"path":"/usr/lib64/python3.6/ensurepip/__pycache__/_uninstall.cpython-36.pyc","mode":33188,"size":918,"sha256":"e4d1449d13c00bf69dee9f82c980912530767b4831032a60df0cb3845b9a0046"},{"path":"/usr/lib64/python3.6/ensurepip/_uninstall.py","mode":33188,"size":808,"sha256":"3a6e95d01c45e2e47c05df3c81073b895c97c1eb0e5b90ab175d6d9263fc81f2"},{"path":"/usr/lib64/python3.6/enum.py","mode":33188,"size":33606,"sha256":"30c38fd06f6c03608525e8b350ec8bf1455b9ee15079ef3cb660a3da4f5268d8"},{"path":"/usr/lib64/python3.6/filecmp.py","mode":33188,"size":9830,"sha256":"71e084dbe941f20a098654135d4f3cf722f7ae08b436d20ab7f68219ee6b5e6d"},{"path":"/usr/lib64/python3.6/fileinput.py","mode":33188,"size":14471,"sha256":"09830fe5b4fa1536c09bd8649982df305333749b29bf0c29330ea6649a3f721f"},{"path":"/usr/lib64/python3.6/fnmatch.py","mode":33188,"size":3166,"sha256":"571ee522073062992aa4b01fba2c729b0bab37ae6c3d81106c264a00e743977a"},{"path":"/usr/lib64/python3.6/formatter.py","mode":33188,"size":15143,"sha256":"46f7d6271031b4716badb318ca47e29b99447cad7770e3922ba48091b9c898f8"},{"path":"/usr/lib64/python3.6/fractions.py","mode":33188,"size":23639,"sha256":"70ce2235812ad1dbe74ee4225a2fb3c4297c5fc02c7df59b90f8de0b34afb8cf"},{"path":"/usr/lib64/python3.6/ftplib.py","mode":33188,"size":35256,"sha256":"23c0c595f0451c928f72fe4be85134d23974b370840e2a2e8248b3a869824058"},{"path":"/usr/lib64/python3.6/functools.py","mode":33188,"size":31346,"sha256":"8e0ffb08ab548e387850abe5a1f11669762b2c80b1f8fc9c908be31315657629"},{"path":"/usr/lib64/python3.6/genericpath.py","mode":33188,"size":4756,"sha256":"fae1f627b5c8408c5f797f9f7170d90fee55faf178b6a65df934ae10e81deca9"},{"path":"/usr/lib64/python3.6/getopt.py","mode":33188,"size":7489,"sha256":"efafb88c7c978e96bd6c232b7fa10bf50cef5e7fb0fb7dc8e5bce44e19f8c92f"},{"path":"/usr/lib64/python3.6/getpass.py","mode":33188,"size":5994,"sha256":"4b42d1f49e0654c5f42dd5f70252be1e3d674f21db97e1bf62d37ef2208198a2"},{"path":"/usr/lib64/python3.6/gettext.py","mode":33188,"size":21530,"sha256":"7e9c44e6a8682903080a6260bd67fe88c653ab3ce33110458b171a42eda3b4f3"},{"path":"/usr/lib64/python3.6/glob.py","mode":33188,"size":5638,"sha256":"917d72296280f492d9e9ce0bb3211a0c12bcf3980f45c5affd516d022d0ea57a"},{"path":"/usr/lib64/python3.6/gzip.py","mode":33188,"size":20334,"sha256":"31ffacfa8347f6b4376c1a484be610c83eef10df24a84c055d8b9a670a9302cf"},{"path":"/usr/lib64/python3.6/hashlib.py","mode":33188,"size":8799,"sha256":"a4a5d754b9b1d6988e8d4337ebe0f00b0191c1f9d7d8154be296aa11ec71eaff"},{"path":"/usr/lib64/python3.6/heapq.py","mode":33188,"size":22929,"sha256":"e4e7381978c763cc8800333f3d62fa34519af7d4ab37d2fbd913146d02d988d9"},{"path":"/usr/lib64/python3.6/hmac.py","mode":33188,"size":6381,"sha256":"38b1cce42ae2f0670adcc9aa6a9ba1fbd52e8a745f0ff68995de8666646fee1f"},{"path":"/usr/lib64/python3.6/html/__init__.py","mode":33188,"size":4756,"sha256":"8d69aeb50f77de6d84c51b9d01e08497983bafe9297cdd1620bf75aa1b1dba1c"},{"path":"/usr/lib64/python3.6/html/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3379,"sha256":"ea1aa5ceab23a007352e81ebed1a3fb542f6c2d00ac0be9cecc45e4990c5f6be"},{"path":"/usr/lib64/python3.6/html/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":2720,"sha256":"d518a62a80864e82391249f278060d43d32a48b227a3dd0130e18937d9aee049"},{"path":"/usr/lib64/python3.6/html/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3379,"sha256":"ea1aa5ceab23a007352e81ebed1a3fb542f6c2d00ac0be9cecc45e4990c5f6be"},{"path":"/usr/lib64/python3.6/html/__pycache__/entities.cpython-36.opt-1.pyc","mode":33188,"size":50449,"sha256":"e84a75fa1956a5364d806f664e362c29a48f5e5b4dd2ef3e09215af3d5033bda"},{"path":"/usr/lib64/python3.6/html/__pycache__/entities.cpython-36.opt-2.pyc","mode":33188,"size":50397,"sha256":"e86cb3168d3ebdadcca18ea1247b8b11f3f3494bb7d4ce48f301e06b9692a444"},{"path":"/usr/lib64/python3.6/html/__pycache__/entities.cpython-36.pyc","mode":33188,"size":50449,"sha256":"e84a75fa1956a5364d806f664e362c29a48f5e5b4dd2ef3e09215af3d5033bda"},{"path":"/usr/lib64/python3.6/html/__pycache__/parser.cpython-36.opt-1.pyc","mode":33188,"size":10747,"sha256":"8685e54caf09d683cd2870bc2ca2006050792a6eb8e5a863a027dbf3f4bbe1db"},{"path":"/usr/lib64/python3.6/html/__pycache__/parser.cpython-36.opt-2.pyc","mode":33188,"size":9382,"sha256":"5c1b02446bd6ea813c363e691a465e507a28aeadd2b62ff56dc98e77885829ce"},{"path":"/usr/lib64/python3.6/html/__pycache__/parser.cpython-36.pyc","mode":33188,"size":11166,"sha256":"09d4c9686b169be3f2e03561aba952363eac34a3f78f300a7e5c833b6c9d71ea"},{"path":"/usr/lib64/python3.6/html/entities.py","mode":33188,"size":75315,"sha256":"fbe69b7c04e3e75eb7b33fefd2d5ad730bff35c4a7b865a8ecfc041075f6f93c"},{"path":"/usr/lib64/python3.6/html/parser.py","mode":33188,"size":17729,"sha256":"9e0b599e7914393330bd86599f9ddcbc6982e9ddd4fd73fa2d66d429d4d04211"},{"path":"/usr/lib64/python3.6/http/__init__.py","mode":33188,"size":5953,"sha256":"272a6739e4c5fd79791e1e1baefb0bfe0a9edb5a53bdadde8c9b7b8741769d76"},{"path":"/usr/lib64/python3.6/http/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":6529,"sha256":"f22b29a9c65f433fd12ca666612a5e2707abd04d0ebc16912e03cd443a6fe3a7"},{"path":"/usr/lib64/python3.6/http/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":5981,"sha256":"f1f0cdceb6345a8778cc747bbe69d16a2d24f6be0233f8641d164f96f1414519"},{"path":"/usr/lib64/python3.6/http/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":6529,"sha256":"f22b29a9c65f433fd12ca666612a5e2707abd04d0ebc16912e03cd443a6fe3a7"},{"path":"/usr/lib64/python3.6/http/__pycache__/client.cpython-36.opt-1.pyc","mode":33188,"size":34507,"sha256":"a3aed13c3febef876e26f10bfe39cedb16da1b7cc126d1f4b7f7176b1590ae9b"},{"path":"/usr/lib64/python3.6/http/__pycache__/client.cpython-36.opt-2.pyc","mode":33188,"size":25293,"sha256":"af91ec2b9ff550f6313d5faeca4e3996fb365db4d48f9243d5a79cf6c7f2ddf1"},{"path":"/usr/lib64/python3.6/http/__pycache__/client.cpython-36.pyc","mode":33188,"size":34606,"sha256":"00f8b5cfcfb7b059d69ec35c75f86fd543c9d0c527846dd7aa711d7a58509f85"},{"path":"/usr/lib64/python3.6/http/__pycache__/cookiejar.cpython-36.opt-1.pyc","mode":33188,"size":53823,"sha256":"3d0bcb95d9ae402b65dc2da392de2a766458c7ffd39faa9ca21826404502477a"},{"path":"/usr/lib64/python3.6/http/__pycache__/cookiejar.cpython-36.opt-2.pyc","mode":33188,"size":38153,"sha256":"f39d11cd44d63f04bebb49d5c5c079faf08b1cebdb8679c0a42610269c491896"},{"path":"/usr/lib64/python3.6/http/__pycache__/cookiejar.cpython-36.pyc","mode":33188,"size":54000,"sha256":"f172fbb64bfdd784c714f82341aa348003ad34cffbcd38a17e15386eed0c14bf"},{"path":"/usr/lib64/python3.6/http/__pycache__/cookies.cpython-36.opt-1.pyc","mode":33188,"size":16106,"sha256":"835e4e3a716089854648daf58678408d59d9156b5161093c35a29748e416dbc6"},{"path":"/usr/lib64/python3.6/http/__pycache__/cookies.cpython-36.opt-2.pyc","mode":33188,"size":11617,"sha256":"136f5359ce412e27076c5d9a67dc04692f249c0ead91bd8be6f90e17153b8cb8"},{"path":"/usr/lib64/python3.6/http/__pycache__/cookies.cpython-36.pyc","mode":33188,"size":16154,"sha256":"24dd9396a1077d175255989ddaec7d318817c311ad4100857a10be60df6fdd2b"},{"path":"/usr/lib64/python3.6/http/__pycache__/server.cpython-36.opt-1.pyc","mode":33188,"size":32220,"sha256":"e32b7833d0390d2f68791b63b7adc7b426015462e9f514e231a15d23868e7c69"},{"path":"/usr/lib64/python3.6/http/__pycache__/server.cpython-36.opt-2.pyc","mode":33188,"size":20305,"sha256":"9dc894ad3c2c792d7abd9110225e20d7444a3c51694c1c89610c9638a95ecb32"},{"path":"/usr/lib64/python3.6/http/__pycache__/server.cpython-36.pyc","mode":33188,"size":32220,"sha256":"e32b7833d0390d2f68791b63b7adc7b426015462e9f514e231a15d23868e7c69"},{"path":"/usr/lib64/python3.6/http/client.py","mode":33188,"size":55701,"sha256":"59ceac92239b0dbbb90dbad2872ccc3f19defe1266106fb333d04423d16d76a0"},{"path":"/usr/lib64/python3.6/http/cookiejar.py","mode":33188,"size":76658,"sha256":"0c9fca387b84ef9fd53021913d87485f0ea724c8f3a9b857b540d9993aaed063"},{"path":"/usr/lib64/python3.6/http/cookies.py","mode":33188,"size":21390,"sha256":"805ea38dd46803da3de55345f950e6d0b56b480e0b96cd10ff3a59054aab908c"},{"path":"/usr/lib64/python3.6/http/server.py","mode":33188,"size":43792,"sha256":"c287dc24b301cb14e7ab806d0fc0412af9df9c8b12e890a14e13c3c9437fb1ac"},{"path":"/usr/lib64/python3.6/imaplib.py","mode":33188,"size":53295,"sha256":"b703f954f81c07ad89f9fe746b3ae1effc14d4011bd60dffc2976e51b3cb62ae"},{"path":"/usr/lib64/python3.6/imghdr.py","mode":33188,"size":3795,"sha256":"2f08102d7d2e0d658bcf9a908913886617db93e9a0282762b2fd688e4fdb4f1d"},{"path":"/usr/lib64/python3.6/imp.py","mode":33188,"size":10669,"sha256":"72ca12b9bebc5cc2f7c36194edf7cff19965504154f2d3b8ddbd768b00834e3c"},{"path":"/usr/lib64/python3.6/importlib/__init__.py","mode":33188,"size":5870,"sha256":"493f457a0ceca5df438908d1daef3affd68c16d12d4d15e4c1c6357d77e56a0f"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3602,"sha256":"27b5166750d354bd2d734c72ea3b7e0d3ad2af59f545de8b6261075b253661ee"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":2923,"sha256":"26504fd294e2a5b3b98f2a973e393194fe3fa336fcbcde59247b5a79420de408"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3602,"sha256":"27b5166750d354bd2d734c72ea3b7e0d3ad2af59f545de8b6261075b253661ee"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/_bootstrap.cpython-36.opt-1.pyc","mode":33188,"size":29084,"sha256":"f2a8e4f44ddaa90fc64c5f1c1900b86fa620fe2b3d68548068be8cf0d817fd60"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/_bootstrap.cpython-36.opt-2.pyc","mode":33188,"size":22249,"sha256":"f4a930c2a35df35d426c8cf95b5109ab0820bfce7d4c4cc5ba8914bad5782f91"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/_bootstrap.cpython-36.pyc","mode":33188,"size":29116,"sha256":"eb759c600c0f08ab0a7b3b14edfd3f52a3d6df659d4eac5da6619d83295ee13e"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/_bootstrap_external.cpython-36.opt-1.pyc","mode":33188,"size":38721,"sha256":"16154cb0b31b4cc54687d27adcd0973953bc80fae249e038830d574c9e1a9f37"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/_bootstrap_external.cpython-36.opt-2.pyc","mode":33188,"size":29099,"sha256":"c473860d62fe786b1da6e4f79569dc6a1cd41e3341cc5dbb1199e22a80cad7fb"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/_bootstrap_external.cpython-36.pyc","mode":33188,"size":38903,"sha256":"a02baf03a366d88e4b5f2e759e231ad7dade54035db08ac26c54b98214599c0e"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/abc.cpython-36.opt-1.pyc","mode":33188,"size":11295,"sha256":"fd11903980503e23f361cec68fed51c6898dd5d99022902b124344120c49f5af"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/abc.cpython-36.opt-2.pyc","mode":33188,"size":5482,"sha256":"de6dff44db84ce35d1e5ec41a28ec6ebaaee5ad084d20aa92660b4efc5961765"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/abc.cpython-36.pyc","mode":33188,"size":11295,"sha256":"fd11903980503e23f361cec68fed51c6898dd5d99022902b124344120c49f5af"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/machinery.cpython-36.opt-1.pyc","mode":33188,"size":952,"sha256":"2438e252385d1d83e80abdbaf919bbd49b0b4b1971d6d1d3c46ef2428d574c3d"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/machinery.cpython-36.opt-2.pyc","mode":33188,"size":812,"sha256":"c4f0d4e1f150fb0e04833e98e89abdd90c565d676bbefed6f0880d25738c9e89"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/machinery.cpython-36.pyc","mode":33188,"size":952,"sha256":"2438e252385d1d83e80abdbaf919bbd49b0b4b1971d6d1d3c46ef2428d574c3d"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/util.cpython-36.opt-1.pyc","mode":33188,"size":8902,"sha256":"d0f63e787d3ccf0a054250e8e857c48e53ae2fb8268aedce0ae4922b10824fc2"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/util.cpython-36.opt-2.pyc","mode":33188,"size":6096,"sha256":"d08790fe28e122f7235d3992de95077c465648f153130df0d783f6f5e6100328"},{"path":"/usr/lib64/python3.6/importlib/__pycache__/util.cpython-36.pyc","mode":33188,"size":8902,"sha256":"d0f63e787d3ccf0a054250e8e857c48e53ae2fb8268aedce0ae4922b10824fc2"},{"path":"/usr/lib64/python3.6/importlib/_bootstrap.py","mode":33188,"size":38843,"sha256":"377e75d3416dd70d6d1cda97982e8a9432a175076cd0651579c2924dbff289ee"},{"path":"/usr/lib64/python3.6/importlib/_bootstrap_external.py","mode":33188,"size":54487,"sha256":"97c86a816e2e543c5b712d432181fe268d8b9e0e947727cdc0fa0ec803dc6892"},{"path":"/usr/lib64/python3.6/importlib/abc.py","mode":33188,"size":10782,"sha256":"30267c1926d1604ffc7eef4a4db65dd2f3bf6ea6d06db08dab860ecde1ae0984"},{"path":"/usr/lib64/python3.6/importlib/machinery.py","mode":33188,"size":844,"sha256":"d8675d9b5553ae4ce0a01005bc47a199b9167ef2c4217a4bbda8f457170aae8b"},{"path":"/usr/lib64/python3.6/importlib/util.py","mode":33188,"size":10883,"sha256":"c89c149b3b76fe889eb04b7bfdff227f12b3e8ac2496e1f23a3fc5069f9a49c1"},{"path":"/usr/lib64/python3.6/inspect.py","mode":33188,"size":116958,"sha256":"9caf37ad1e788851ff4e2bb20647e9ab350177d98bd860b5261502306807012e"},{"path":"/usr/lib64/python3.6/io.py","mode":33188,"size":3517,"sha256":"85761cb75b890461645bb4a3235ee40abd13f4f8d9c80b4078bf261bc7d8128c"},{"path":"/usr/lib64/python3.6/ipaddress.py","mode":33188,"size":74551,"sha256":"d7fb6bebec60583f83c667455c525807956d5739dd180e8db5b95d87c59170f7"},{"path":"/usr/lib64/python3.6/json/__init__.py","mode":33188,"size":14396,"sha256":"07600c60b9b451622c29bc07a0546f7a7cca79c355b13dd869472a97e3f600d6"},{"path":"/usr/lib64/python3.6/json/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":12643,"sha256":"50ae42c9154d2bed564b793db92ddf422e978280d91cf5836ce2ac7cca8737a7"},{"path":"/usr/lib64/python3.6/json/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":2989,"sha256":"bf09894f46ed8392c2ed68f8786ca17a138fdbe84556980280ed8b3b9ef3a766"},{"path":"/usr/lib64/python3.6/json/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":12643,"sha256":"50ae42c9154d2bed564b793db92ddf422e978280d91cf5836ce2ac7cca8737a7"},{"path":"/usr/lib64/python3.6/json/__pycache__/decoder.cpython-36.opt-1.pyc","mode":33188,"size":9957,"sha256":"9cb0a5d494f1b3b76b9b0ed166e203e849e701b8e6f5c56f40c1edda3da8b1cb"},{"path":"/usr/lib64/python3.6/json/__pycache__/decoder.cpython-36.opt-2.pyc","mode":33188,"size":5809,"sha256":"86d501b52748e8b0dcfe4467f01ae57118e4d8249e0b49ab0bdb7d48b798e3bc"},{"path":"/usr/lib64/python3.6/json/__pycache__/decoder.cpython-36.pyc","mode":33188,"size":9957,"sha256":"9cb0a5d494f1b3b76b9b0ed166e203e849e701b8e6f5c56f40c1edda3da8b1cb"},{"path":"/usr/lib64/python3.6/json/__pycache__/encoder.cpython-36.opt-1.pyc","mode":33188,"size":11259,"sha256":"267a96f8ab5292ab576b2de13bc5e73598c9dc1592299d4ca20f67ab9a9a2f35"},{"path":"/usr/lib64/python3.6/json/__pycache__/encoder.cpython-36.opt-2.pyc","mode":33188,"size":6908,"sha256":"1ad9cab390a64e0c92240e75217d34032c2d6395fc16987952d826ed56e84e1c"},{"path":"/usr/lib64/python3.6/json/__pycache__/encoder.cpython-36.pyc","mode":33188,"size":11259,"sha256":"267a96f8ab5292ab576b2de13bc5e73598c9dc1592299d4ca20f67ab9a9a2f35"},{"path":"/usr/lib64/python3.6/json/__pycache__/scanner.cpython-36.opt-1.pyc","mode":33188,"size":1972,"sha256":"cdf62aed727e31983d307312a226ddc8d90cf693031a6c3ba8c5758f1de1cd1a"},{"path":"/usr/lib64/python3.6/json/__pycache__/scanner.cpython-36.opt-2.pyc","mode":33188,"size":1936,"sha256":"d12c415d587a24906822aae4333ce1762d1fd56a74fb0a33070aaec59ac5ae29"},{"path":"/usr/lib64/python3.6/json/__pycache__/scanner.cpython-36.pyc","mode":33188,"size":1972,"sha256":"cdf62aed727e31983d307312a226ddc8d90cf693031a6c3ba8c5758f1de1cd1a"},{"path":"/usr/lib64/python3.6/json/__pycache__/tool.cpython-36.opt-1.pyc","mode":33188,"size":1547,"sha256":"1dab95b03be4141cc1eeb976de2a10883a9d6c89a1ae11386cc30071caf31fce"},{"path":"/usr/lib64/python3.6/json/__pycache__/tool.cpython-36.opt-2.pyc","mode":33188,"size":1254,"sha256":"21fb01a3115ecb721bbef7669ccc1ee13f735389d47fed9117835d626c985e51"},{"path":"/usr/lib64/python3.6/json/__pycache__/tool.cpython-36.pyc","mode":33188,"size":1547,"sha256":"1dab95b03be4141cc1eeb976de2a10883a9d6c89a1ae11386cc30071caf31fce"},{"path":"/usr/lib64/python3.6/json/decoder.py","mode":33188,"size":12585,"sha256":"9acd0914bbc0eaaceeb275e237d8499570bedb1491446968af829517c275b36c"},{"path":"/usr/lib64/python3.6/json/encoder.py","mode":33188,"size":16020,"sha256":"89da4a91a5a672361b7d285154c0efffb704cdd266d7abf27fe12e71799e11e3"},{"path":"/usr/lib64/python3.6/json/scanner.py","mode":33188,"size":2415,"sha256":"012d5cf2a29641ac556f62e21644e37dce77d0ffe3dc0b96123c57ad44aff315"},{"path":"/usr/lib64/python3.6/json/tool.py","mode":33188,"size":1645,"sha256":"d38884439e4ad82b98fb2d8354c0be766b383c6fa73f05b8662343dc0c2913e5"},{"path":"/usr/lib64/python3.6/keyword.py","mode":33261,"size":2219,"sha256":"1441c0c01ed3a4763b796cf2c735b35d355d5dbeb8cf5b901dc0b6b103053807"},{"path":"/usr/lib64/python3.6/lib-dynload/_asyncio.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":55536,"sha256":"15cde316e9292420621ccdc436c20834b450e6574ff77daced601579aa62b26b"},{"path":"/usr/lib64/python3.6/lib-dynload/_bisect.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":13712,"sha256":"cbfff70436c338b09ad8dcccfc46eb6034d754825ccada3975139e4bd8f06d01"},{"path":"/usr/lib64/python3.6/lib-dynload/_blake2.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":92560,"sha256":"e8464f1e81a857b698a8fe7b046194107dbc52c647bde73726db670ed8e83323"},{"path":"/usr/lib64/python3.6/lib-dynload/_bz2.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":23072,"sha256":"fdbaa22663eddf2d6a4860cc2b43344c68c623582d56782041495387ea31332e"},{"path":"/usr/lib64/python3.6/lib-dynload/_codecs_cn.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":155128,"sha256":"4d3afbc6df7dba021ad9b771eacecbb541d1934c32e99bf859d173d7dbc8cab0"},{"path":"/usr/lib64/python3.6/lib-dynload/_codecs_hk.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":159088,"sha256":"9382652d99fcbb88c3126f6ccead7da06c890649d505e6b1c67f7d3868d1de46"},{"path":"/usr/lib64/python3.6/lib-dynload/_codecs_iso2022.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":24272,"sha256":"881ecf66cc144f4c1550c5c2f6c439bb861a286f13fe69606f43973becada07c"},{"path":"/usr/lib64/python3.6/lib-dynload/_codecs_jp.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":269856,"sha256":"a86a059a86a3f792e524da1d549168bf72d4f622e0d4b9a5ad202052c512812d"},{"path":"/usr/lib64/python3.6/lib-dynload/_codecs_kr.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":138664,"sha256":"2c329fb5c4f8a0f5596e983dc0386a2cc3990d6abcecb96cf23a80277a527a62"},{"path":"/usr/lib64/python3.6/lib-dynload/_codecs_tw.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":114040,"sha256":"44179e52d5c74efeb0568ab4ead85988c79bfe1423bacb670abb0c468e18a169"},{"path":"/usr/lib64/python3.6/lib-dynload/_crypt.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":7768,"sha256":"5a48487fd42a38f7be6d38c421974c0055a6ba05f4ddb89348e784d87654471f"},{"path":"/usr/lib64/python3.6/lib-dynload/_csv.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":39512,"sha256":"b450c58119c41ec26bc62655b8bbe49782d4a640abf7fae4cad9b184b5cded6b"},{"path":"/usr/lib64/python3.6/lib-dynload/_ctypes.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":129176,"sha256":"4caf59b9360ebb5270d4c7f3985bd1118f896cea501f676d611285eada2b2ed4"},{"path":"/usr/lib64/python3.6/lib-dynload/_curses.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":96808,"sha256":"5878b1acd398fe7ce1d5c9e259f652a809e64562ee1a100a18183eb71bcd7a37"},{"path":"/usr/lib64/python3.6/lib-dynload/_curses_panel.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":16440,"sha256":"98a1cefb9b650594ddaeee307094dc8435b52bf5f5577414ab8d561bf8b2c59c"},{"path":"/usr/lib64/python3.6/lib-dynload/_datetime.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":115256,"sha256":"d8cef1b79a81cf1f97f11f66775c798ec0e5f01d674412208f5f8c757a8dd6c6"},{"path":"/usr/lib64/python3.6/lib-dynload/_dbm.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":17272,"sha256":"995a2088f53d4fe470c0b324e4080c1227e4c12fc6b6eb8ff68b1f7a36d603ce"},{"path":"/usr/lib64/python3.6/lib-dynload/_decimal.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":311256,"sha256":"4469c04f2eb551548e22111283b12b9499395a47198a4ead2103eb97558527a6"},{"path":"/usr/lib64/python3.6/lib-dynload/_elementtree.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":76104,"sha256":"bb56cd0800418814bda940eee9e5799c1def11bb73e8920b697aa7db58110555"},{"path":"/usr/lib64/python3.6/lib-dynload/_gdbm.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":20432,"sha256":"d44ac03a88af2a9b5f11aa281297d8b8e127ba5f6f886cd9e8d3a1bb16117781"},{"path":"/usr/lib64/python3.6/lib-dynload/_hashlib.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":47968,"sha256":"847e7a7fc4f0e110b3b6535b9c6598c95276b8ff71759da4a63aec1398255908"},{"path":"/usr/lib64/python3.6/lib-dynload/_heapq.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":23064,"sha256":"7b990683bd05f6331a36549791f714503e8c2196dde1d98de330742c11201bd2"},{"path":"/usr/lib64/python3.6/lib-dynload/_hmacopenssl.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":17280,"sha256":"f90db7acece4a4eea55602793d6406f1438af69587587a7a2a2cbb767c50b594"},{"path":"/usr/lib64/python3.6/lib-dynload/_json.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":80136,"sha256":"b3819120254252c1174f87aaca0ecca213a7ef7e598a41b33785cbce6708ecb7"},{"path":"/usr/lib64/python3.6/lib-dynload/_lsprof.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":22448,"sha256":"2ae3610723e7f5bcb8f52b7d2782b2f86a87e5fd7a5d2be8f74fc0be3e507b98"},{"path":"/usr/lib64/python3.6/lib-dynload/_lzma.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":42880,"sha256":"86e558535e10ca0014312039a9b5197f2aade80a5ea09d4256f48b15afe00c03"},{"path":"/usr/lib64/python3.6/lib-dynload/_multibytecodec.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":49648,"sha256":"d2d631c2d517bb76bec4163eeee6d2df980fec197609e41941f063c37a2113a6"},{"path":"/usr/lib64/python3.6/lib-dynload/_multiprocessing.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":16888,"sha256":"fc04d25a5d96c810c44539901f90b10b68a148daa13e9112bba1da980d009321"},{"path":"/usr/lib64/python3.6/lib-dynload/_opcode.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":7520,"sha256":"fb258a371d9c34e6c156d9bd32069f07e4c4620046f154e02dc3b34ac5e81b80"},{"path":"/usr/lib64/python3.6/lib-dynload/_pickle.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":131616,"sha256":"120e17f26285949acd128c2dd7170a1f3bc9d734f0a594d674966a3b31887299"},{"path":"/usr/lib64/python3.6/lib-dynload/_posixsubprocess.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":16616,"sha256":"0c79cbafb8db9c35b9d33f6a7e4b11bd7e70307a0dfafc0526a43aad4a5ed970"},{"path":"/usr/lib64/python3.6/lib-dynload/_random.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":20560,"sha256":"77161159e544941002b3df2a2c4e8140748055b834e7a8972b95792f65a4c99c"},{"path":"/usr/lib64/python3.6/lib-dynload/_sha3.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":102288,"sha256":"c2644345b632e909971abf7badd3c61f1a0badc3d9dd4e9344752f8f8e3624e1"},{"path":"/usr/lib64/python3.6/lib-dynload/_socket.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":88928,"sha256":"4a6eef916d7d57f638f7f1b265c383e47cada0923fedbcdf680f470986761186"},{"path":"/usr/lib64/python3.6/lib-dynload/_sqlite3.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":97600,"sha256":"f27fcc0d1b5bdba9796a96d5b95853fab1cff426515549a49a744c8184ec0fdc"},{"path":"/usr/lib64/python3.6/lib-dynload/_ssl.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":116256,"sha256":"6d65536c65d20998d5f9ad240894626b4cc813f7cbd92f495f002adf1ab27cc3"},{"path":"/usr/lib64/python3.6/lib-dynload/_struct.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":52728,"sha256":"ad656b841ee2ababf36b1d240147ec7a07f5a0e5073229bc6bb30da3dddc1d8d"},{"path":"/usr/lib64/python3.6/lib-dynload/_testmultiphase.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":23480,"sha256":"bfe94d5fe01a078f54b2108e1bbcd53f657d3337fe9546f1cad5eb5eea44547e"},{"path":"/usr/lib64/python3.6/lib-dynload/array.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":66096,"sha256":"e4c3f234157dab738aeedee9583381b03bf22f0c026b3735a1b4b02a76408e8c"},{"path":"/usr/lib64/python3.6/lib-dynload/audioop.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":65144,"sha256":"dcad2080e2d833d6ea4d0724a323b4de48d1b6ca5caeff19b949f36f966a54f5"},{"path":"/usr/lib64/python3.6/lib-dynload/binascii.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":30880,"sha256":"2f7e365b7285c08d583fd6f56473b0de5947d97870ad13818d654e12ac363ef2"},{"path":"/usr/lib64/python3.6/lib-dynload/cmath.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":68840,"sha256":"4764b57ee41f05063c63efd936a9cf1b7a251c36b7b42236bcaf2878b42fcb0c"},{"path":"/usr/lib64/python3.6/lib-dynload/fcntl.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":19480,"sha256":"836305fcc60cb0ade9ee1e6a316746dc3d97f44e421938254a4f2f5d0094e475"},{"path":"/usr/lib64/python3.6/lib-dynload/grp.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":13224,"sha256":"d4d42bacadc4bb3e99f9f38a9c1396042d1fae3f5bcf1e6052c90e3991a2e04e"},{"path":"/usr/lib64/python3.6/lib-dynload/math.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":59392,"sha256":"b56142859db49cd338dfb2bdff5fc039225cf115d7b3e8d950b751262087f258"},{"path":"/usr/lib64/python3.6/lib-dynload/mmap.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":30600,"sha256":"72673c0babbbac7fdb8139de60213bac988fbcb9e40aa8b2d4cfd0945992f189"},{"path":"/usr/lib64/python3.6/lib-dynload/nis.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":16616,"sha256":"554db85979f46bdac69203d0dfd71167836f7b294b7eacba0f03355b12a8970a"},{"path":"/usr/lib64/python3.6/lib-dynload/ossaudiodev.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":34360,"sha256":"ffb901a529c414c07ba90337abcb45184a67bb6b7ec04289b2af53b1e7ce7ad7"},{"path":"/usr/lib64/python3.6/lib-dynload/parser.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":29368,"sha256":"12c921aef1381e5dca01d41dcdf16379eab25fce29d7e3b3a0d2cee1a5580b6e"},{"path":"/usr/lib64/python3.6/lib-dynload/pyexpat.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":66936,"sha256":"b9cb4fda46d263ba1126bb864f5eedce5e43c6a0d0122984929cb9151ad5f30f"},{"path":"/usr/lib64/python3.6/lib-dynload/readline.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":32784,"sha256":"2e4f044a2009232f043266b5f751a0cc9484f8e17b898b0adc8348d32883a8c1"},{"path":"/usr/lib64/python3.6/lib-dynload/resource.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":16440,"sha256":"188a38dc1a56f7b06e46c4007522b9e10b56e94e8454d799dbb04915f0f28ad4"},{"path":"/usr/lib64/python3.6/lib-dynload/select.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":29288,"sha256":"da6ab0a771b0d557d5e5e53a1d8d38e1c715eaf3effcb3bfba9a0d9858b33e9e"},{"path":"/usr/lib64/python3.6/lib-dynload/spwd.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":12976,"sha256":"7272a861f134a6876db5b68f54138fc4049a84041c34260c8caf27d76bf1e8be"},{"path":"/usr/lib64/python3.6/lib-dynload/syslog.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":11808,"sha256":"7b1bd1e518e30e583685ba9ab4b7026115f7a7dd4d6ec2ad0a19d71418a9f7ee"},{"path":"/usr/lib64/python3.6/lib-dynload/termios.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":25928,"sha256":"7d4864c674bae1841da1f4c91b986f1c298ee087f829e3f30005190f547d8a7e"},{"path":"/usr/lib64/python3.6/lib-dynload/unicodedata.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":899608,"sha256":"6257e417e2c19511c11bcb9d6ebb0f300833b1d9da438033cb206d2678a857f5"},{"path":"/usr/lib64/python3.6/lib-dynload/xxlimited.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":12256,"sha256":"dc851877fcb1b623112d1a40efbfbfc928272d99e1f73d206149201d0221fcd8"},{"path":"/usr/lib64/python3.6/lib-dynload/zlib.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":34424,"sha256":"28d401c47f11348a013bc84b93349b925423a7a78ef691128648524886f121d4"},{"path":"/usr/lib64/python3.6/lib2to3/Grammar.txt","mode":33188,"size":6562,"sha256":"1c6b408ed690ac689a2792ca536a6990dfca3ddb3cdca295d90b24850550d380"},{"path":"/usr/lib64/python3.6/lib2to3/Grammar3.6.8.final.0.pickle","mode":33188,"size":32252,"sha256":"ddb14b28bee69da5714b25dbb14550c374d64512fb038ee97ab3fa3ff330637f"},{"path":"/usr/lib64/python3.6/lib2to3/PatternGrammar.txt","mode":33188,"size":793,"sha256":"ee5ba5db3b6722a0e2fbe2560ebc1c883e72328ef9c3b4da1c7c5d1cc649bce3"},{"path":"/usr/lib64/python3.6/lib2to3/PatternGrammar3.6.8.final.0.pickle","mode":33188,"size":2093,"sha256":"edb7f84f6a386161434bf3cdb64db03b29b80717cedd1c492789578454bc3d05"},{"path":"/usr/lib64/python3.6/lib2to3/__init__.py","mode":33188,"size":7,"sha256":"c8204cfd372ee45f79cb744ed0565bc8d486716115a546f48477c0719b8a6bb9"},{"path":"/usr/lib64/python3.6/lib2to3/__main__.py","mode":33188,"size":67,"sha256":"c7b09f90e66dea194ad63dc02c6425dff977d16f1f21a157b7475905c219a707"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":123,"sha256":"47fcb989b09bd481690d51f14e4769ee6c4544627ac7d731ae00e879f7c7fa86"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":123,"sha256":"47fcb989b09bd481690d51f14e4769ee6c4544627ac7d731ae00e879f7c7fa86"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":123,"sha256":"47fcb989b09bd481690d51f14e4769ee6c4544627ac7d731ae00e879f7c7fa86"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/__main__.cpython-36.opt-1.pyc","mode":33188,"size":207,"sha256":"fcdc376e1accd84e66726d2d7266cd9d18461abe734239744ecd5298a3bd0ee7"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/__main__.cpython-36.opt-2.pyc","mode":33188,"size":207,"sha256":"fcdc376e1accd84e66726d2d7266cd9d18461abe734239744ecd5298a3bd0ee7"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/__main__.cpython-36.pyc","mode":33188,"size":207,"sha256":"fcdc376e1accd84e66726d2d7266cd9d18461abe734239744ecd5298a3bd0ee7"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/btm_matcher.cpython-36.opt-1.pyc","mode":33188,"size":4934,"sha256":"22a3244317e2cdcfbd21bdbc00f9b283f78a859ef4966b92483f53759fdd6486"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/btm_matcher.cpython-36.opt-2.pyc","mode":33188,"size":3363,"sha256":"69915fd36bb4a802ee33bba8d0aff18e76652602accdc09feb1e4a9ef549e691"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/btm_matcher.cpython-36.pyc","mode":33188,"size":4934,"sha256":"22a3244317e2cdcfbd21bdbc00f9b283f78a859ef4966b92483f53759fdd6486"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/btm_utils.cpython-36.opt-1.pyc","mode":33188,"size":6133,"sha256":"f422eea43a9fdbb41a0ea8b77e8f3cc15f29c44156059d33e9ebb24d0d45a839"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/btm_utils.cpython-36.opt-2.pyc","mode":33188,"size":4613,"sha256":"715d70e5a69fb418596e3327cfc57da510d22d14930a943d14544035bb2f25f0"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/btm_utils.cpython-36.pyc","mode":33188,"size":6133,"sha256":"f422eea43a9fdbb41a0ea8b77e8f3cc15f29c44156059d33e9ebb24d0d45a839"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/fixer_base.cpython-36.opt-1.pyc","mode":33188,"size":6225,"sha256":"b07a9259ea5197a729e38c0debb7957e76fbd682efdb54ff75e5b4468b2c5def"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/fixer_base.cpython-36.opt-2.pyc","mode":33188,"size":3464,"sha256":"9d81cea93a02a4df179283a4bd4b090ddd1a06ebff3200e173c292fb45b89fd6"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/fixer_base.cpython-36.pyc","mode":33188,"size":6225,"sha256":"b07a9259ea5197a729e38c0debb7957e76fbd682efdb54ff75e5b4468b2c5def"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/fixer_util.cpython-36.opt-1.pyc","mode":33188,"size":12038,"sha256":"280809fd4e6a464f78a286f3c1210b2feca139dc343f9e66ecc0bfa5ad5323cf"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/fixer_util.cpython-36.opt-2.pyc","mode":33188,"size":9870,"sha256":"22fdb7c90d9ff0bdbf5d38bb275def35b84ed331f9c23d29260866eda8414e6e"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/fixer_util.cpython-36.pyc","mode":33188,"size":12038,"sha256":"280809fd4e6a464f78a286f3c1210b2feca139dc343f9e66ecc0bfa5ad5323cf"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/main.cpython-36.opt-1.pyc","mode":33188,"size":8498,"sha256":"e5f1d8f4aa505a43c97ddc530568c5d6560ca2315d0c3c55151994829ca926ba"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/main.cpython-36.opt-2.pyc","mode":33188,"size":6743,"sha256":"d2268eb0a2065e5b95a1f0feaf0836e041a2493d52238e98088af5f279f25917"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/main.cpython-36.pyc","mode":33188,"size":8532,"sha256":"35be8216ecde0e09ad0c0e11779f0625ba7c2ef7a319cf80f648b004cb8b6783"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/patcomp.cpython-36.opt-1.pyc","mode":33188,"size":5357,"sha256":"2de1c7ad2f1e2678c745d84d94dd2ef1861a6f57e9bab53391cc80b74d919fc5"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/patcomp.cpython-36.opt-2.pyc","mode":33188,"size":4847,"sha256":"f4281a1aed460c01a0ecc4b87fff4a7c554dbadb1829f0d191e6e496482624b9"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/patcomp.cpython-36.pyc","mode":33188,"size":5604,"sha256":"c9778217e3c79fc9e5ec5146271abb1f444e0f7715ed65cf527453495ea7c51d"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/pygram.cpython-36.opt-1.pyc","mode":33188,"size":1178,"sha256":"1b72ce30d12d1e84bb197f8ab03ba53f761c72a1792e13ba999bf18e8ace8539"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/pygram.cpython-36.opt-2.pyc","mode":33188,"size":973,"sha256":"01e6d0b19131f399d3f722f526a3e45923b9b3a012ccf5dad5576d32a1f8087a"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/pygram.cpython-36.pyc","mode":33188,"size":1178,"sha256":"1b72ce30d12d1e84bb197f8ab03ba53f761c72a1792e13ba999bf18e8ace8539"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/pytree.cpython-36.opt-1.pyc","mode":33188,"size":24449,"sha256":"8bce260566aa2b9730f5253d12458bf9fda7a64bcdd06223f8f7a0df093f5af4"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/pytree.cpython-36.opt-2.pyc","mode":33188,"size":15055,"sha256":"967998cc0eb2ccfcc97bea76dbcebdf425c0ce446cc17dcbaae5161aa520f2b1"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/pytree.cpython-36.pyc","mode":33188,"size":25136,"sha256":"af7400a7910b8195925be66bbad081d5bbe642f46261414a82e42cd5524fc9dd"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/refactor.cpython-36.opt-1.pyc","mode":33188,"size":20758,"sha256":"169ef6cb1ef4ee7b76e2a828cdbf4ffd99ca1760f29b1a6f5e855c1af1d6a707"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/refactor.cpython-36.opt-2.pyc","mode":33188,"size":16710,"sha256":"2adcbafe5b3abeff1bbee3e5cbafd4febcc55d9908a92566e57c036cd3a90202"},{"path":"/usr/lib64/python3.6/lib2to3/__pycache__/refactor.cpython-36.pyc","mode":33188,"size":20791,"sha256":"256ec82bc3dcd1aabd76929118f5581d8e5e9d6284bbed54c0a3e83f6cc5f4be"},{"path":"/usr/lib64/python3.6/lib2to3/btm_matcher.py","mode":33188,"size":6833,"sha256":"bfe28964af5a713ba25af61d4ff9f9229afb07952aa460501b7f57512a2d9186"},{"path":"/usr/lib64/python3.6/lib2to3/btm_utils.py","mode":33188,"size":9966,"sha256":"79d210510630052adafcc7c4ad8cf16acd2fd8e9adb46deea952cd81bfbea661"},{"path":"/usr/lib64/python3.6/lib2to3/fixer_base.py","mode":33188,"size":6690,"sha256":"c795a53ca849c42212c8ec33a74284e0377df852eb4ea599aba62d5af1df282a"},{"path":"/usr/lib64/python3.6/lib2to3/fixer_util.py","mode":33188,"size":15207,"sha256":"229f893e48aad6afe5d928f00053681b142cc1a1be9be1cc0f1b28e1e00a9361"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__init__.py","mode":33188,"size":47,"sha256":"836cdb388117cf81e78d9fa2a141cca1b14b0179733322e710067749a1b16fe9"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":129,"sha256":"36ee77195811aea038ac0d05b0a45bfc4bd0177bdb46a11931e74814944f7d73"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":129,"sha256":"36ee77195811aea038ac0d05b0a45bfc4bd0177bdb46a11931e74814944f7d73"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":129,"sha256":"36ee77195811aea038ac0d05b0a45bfc4bd0177bdb46a11931e74814944f7d73"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_apply.cpython-36.opt-1.pyc","mode":33188,"size":1651,"sha256":"ff8c3469125c9ecd86256940f9ebf44d4caccbd702162f9f5ab4439143519183"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_apply.cpython-36.opt-2.pyc","mode":33188,"size":1561,"sha256":"b22622d02b475c74e8056442dfdf06870280e9a3c46b24df5586d61aebb38483"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_apply.cpython-36.pyc","mode":33188,"size":1677,"sha256":"a58aee581c098dcfc7d69378c55d07239c0daf50f87201fcebeb26eb61348bbc"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_asserts.cpython-36.opt-1.pyc","mode":33188,"size":1252,"sha256":"ad0f586476a03842b3553af17bedc4152cd0b3f17f8bf17ef9d6fa13f018ae2b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_asserts.cpython-36.opt-2.pyc","mode":33188,"size":1182,"sha256":"3462a395f419079d2c5ad7fd3bc9850e69100f6327eb8177ced5d2c42893ddfb"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_asserts.cpython-36.pyc","mode":33188,"size":1252,"sha256":"ad0f586476a03842b3553af17bedc4152cd0b3f17f8bf17ef9d6fa13f018ae2b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_basestring.cpython-36.opt-1.pyc","mode":33188,"size":642,"sha256":"00d1389df4e431cdaed272a98b01b567d9ce0204c529761ec8e436ee461b5a97"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_basestring.cpython-36.opt-2.pyc","mode":33188,"size":597,"sha256":"dc44af5605154f13b79c1bf020ba65fb226211cb9598d9de661946ea15a6512a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_basestring.cpython-36.pyc","mode":33188,"size":642,"sha256":"00d1389df4e431cdaed272a98b01b567d9ce0204c529761ec8e436ee461b5a97"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_buffer.cpython-36.opt-1.pyc","mode":33188,"size":787,"sha256":"541ed09665cc37c94ed8a6c8be285d4c2f17884e2d78f395dd6c494f068429ee"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_buffer.cpython-36.opt-2.pyc","mode":33188,"size":718,"sha256":"f85a80ddbbc90489d160fd7cd5dbe2d1f574580b94888fdbde68b3f2a8f2712f"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_buffer.cpython-36.pyc","mode":33188,"size":787,"sha256":"541ed09665cc37c94ed8a6c8be285d4c2f17884e2d78f395dd6c494f068429ee"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_dict.cpython-36.opt-1.pyc","mode":33188,"size":3226,"sha256":"a777c14ab3e50ad6c4bb9df8fa049f42abbbd7fda6baa895d7f271ead6cbd017"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_dict.cpython-36.opt-2.pyc","mode":33188,"size":2332,"sha256":"edbee6adb273e465781a0ef14c44c9ade53ab6f5a0c1ec0f86c7fc13a28f17f0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_dict.cpython-36.pyc","mode":33188,"size":3310,"sha256":"2d591b4dfb58e1a580f43e6f7e0d5a51e9ba211062986a3d059a1c17fab62174"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_except.cpython-36.opt-1.pyc","mode":33188,"size":2797,"sha256":"b97363053970465c62e87b535e15dff6be0e935945cd6368caae95f636e5a501"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_except.cpython-36.opt-2.pyc","mode":33188,"size":2351,"sha256":"9b7f57f7717f30ed54450555deae404387e774f7e27fecac16f5d6958611b91d"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_except.cpython-36.pyc","mode":33188,"size":2797,"sha256":"b97363053970465c62e87b535e15dff6be0e935945cd6368caae95f636e5a501"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_exec.cpython-36.opt-1.pyc","mode":33188,"size":1102,"sha256":"7ebd944ab70781032c783fd973d70121984d41994a302acf439d38fda2084d25"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_exec.cpython-36.opt-2.pyc","mode":33188,"size":936,"sha256":"f59078be39db5b2ede3b569220951f6b790f28a6e334dbce36b0797a0091e17a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_exec.cpython-36.pyc","mode":33188,"size":1128,"sha256":"542fb9b9f7698af8913789bd0d4d53bcf4f6e16376d0f7811401de40fa1ca1a0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_execfile.cpython-36.opt-1.pyc","mode":33188,"size":1656,"sha256":"2985f91943f6689dfa0b8fc88512191dde6b1fa2a80985ada18aac524a785d03"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_execfile.cpython-36.opt-2.pyc","mode":33188,"size":1528,"sha256":"60764dae28f07ecc121df51851e78aa335b17a64da3bd43470d6eec3e6225057"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_execfile.cpython-36.pyc","mode":33188,"size":1684,"sha256":"8bf93b601985283f4e95402e714c9ee9009fa0395189306e7bc3a2088b2380ed"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_exitfunc.cpython-36.opt-1.pyc","mode":33188,"size":2275,"sha256":"8e6214667117a3e4c73df699eddc7f693e443a1d29cc069e062eca346cab78e6"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_exitfunc.cpython-36.opt-2.pyc","mode":33188,"size":2203,"sha256":"428e48fb553feba8df03693a363b7b9aa4da6a60bd7561047a6041959297024a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_exitfunc.cpython-36.pyc","mode":33188,"size":2275,"sha256":"8e6214667117a3e4c73df699eddc7f693e443a1d29cc069e062eca346cab78e6"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_filter.cpython-36.opt-1.pyc","mode":33188,"size":2340,"sha256":"aefd3e5569fd1eb7e42880a2561bb444b064d164c95a89526c6d47d30b2e0d17"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_filter.cpython-36.opt-2.pyc","mode":33188,"size":1880,"sha256":"34a509596d7dec699a5ab8b41a89baa9778031c670d201972f235f49f5dd82b3"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_filter.cpython-36.pyc","mode":33188,"size":2340,"sha256":"aefd3e5569fd1eb7e42880a2561bb444b064d164c95a89526c6d47d30b2e0d17"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_funcattrs.cpython-36.opt-1.pyc","mode":33188,"size":953,"sha256":"66767ec41cc8b10f274f5d0f495a6bb524efd4b68149c7b646f4389d0309eabc"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_funcattrs.cpython-36.opt-2.pyc","mode":33188,"size":885,"sha256":"9ac573520913ace04e803dc1b2129c7c4c74626399fad0514731a12768aa51ae"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_funcattrs.cpython-36.pyc","mode":33188,"size":953,"sha256":"66767ec41cc8b10f274f5d0f495a6bb524efd4b68149c7b646f4389d0309eabc"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_future.cpython-36.opt-1.pyc","mode":33188,"size":763,"sha256":"fcdad7089f73409be535e656f7547524d14aed5ad8679f0c272103384bf2ab00"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_future.cpython-36.opt-2.pyc","mode":33188,"size":660,"sha256":"9cad1f54ff24cfe7e21e49a353a6c7bc6223dd4132cb6476a28daafb2e49c4f7"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_future.cpython-36.pyc","mode":33188,"size":763,"sha256":"fcdad7089f73409be535e656f7547524d14aed5ad8679f0c272103384bf2ab00"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_getcwdu.cpython-36.opt-1.pyc","mode":33188,"size":767,"sha256":"cf2e59ffb311a579b1febba13f95d9a0ff4cd95525b4fa9b2b0353ede4d9ffb8"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_getcwdu.cpython-36.opt-2.pyc","mode":33188,"size":701,"sha256":"0a5818ac08ba9788e21a29fb6e13c5960d449dbd8a29a0389ef5eb4cd8dd7e5d"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_getcwdu.cpython-36.pyc","mode":33188,"size":767,"sha256":"cf2e59ffb311a579b1febba13f95d9a0ff4cd95525b4fa9b2b0353ede4d9ffb8"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_has_key.cpython-36.opt-1.pyc","mode":33188,"size":2869,"sha256":"8a26b739a3007868c0668a56a71ac606232d464c61d45c18bd5ef5210e79eb76"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_has_key.cpython-36.opt-2.pyc","mode":33188,"size":2299,"sha256":"357f89047a01b40f823018cd059a7fdc0d8cb020f59e6da26e004472a4cb80e0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_has_key.cpython-36.pyc","mode":33188,"size":2897,"sha256":"9e913dce290d6af9b40b1cd339f5beb70e47196e5f5c5660db58fe983f68b3ef"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_idioms.cpython-36.opt-1.pyc","mode":33188,"size":3806,"sha256":"3163054072e9c0452ad19a375dd4c4fd78ea3a47d037fc3f6a20a1ce2c506729"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_idioms.cpython-36.opt-2.pyc","mode":33188,"size":3310,"sha256":"4fdc683899b85ec841dc56ca8694488007a8dbd667ba1dee1a3b4c7722b8d34c"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_idioms.cpython-36.pyc","mode":33188,"size":3882,"sha256":"731a557cfce2d890edc892964256b8963bd05cd64cf098648c4ba1c348205f60"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_import.cpython-36.opt-1.pyc","mode":33188,"size":2769,"sha256":"a528f494c224246dd83e8ea686f8f25a98ebbb079913dcf7dca46b66158a85b9"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_import.cpython-36.opt-2.pyc","mode":33188,"size":2458,"sha256":"409935717b0e7128e99236793e7a5d6a6d348e03d01853001a9d143194250bb6"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_import.cpython-36.pyc","mode":33188,"size":2769,"sha256":"a528f494c224246dd83e8ea686f8f25a98ebbb079913dcf7dca46b66158a85b9"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_imports.cpython-36.opt-1.pyc","mode":33188,"size":4328,"sha256":"94a6b8a5a76b1ba3bedde39a530b8712873d7c7c0c599c220ae1a93432215ad0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_imports.cpython-36.opt-2.pyc","mode":33188,"size":4264,"sha256":"5386d03292631c98b93bf052403a7e629a7c6ba4f96cc3cd56acb7f0770598e1"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_imports.cpython-36.pyc","mode":33188,"size":4328,"sha256":"94a6b8a5a76b1ba3bedde39a530b8712873d7c7c0c599c220ae1a93432215ad0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_imports2.cpython-36.opt-1.pyc","mode":33188,"size":527,"sha256":"4fcc4125a4cb68c5f402584bcffd10664c96443f65d58ce76d4c99664c513381"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_imports2.cpython-36.opt-2.pyc","mode":33188,"size":426,"sha256":"66809853fb419bb06e361e11c06a600a1172504638cbdf910b885fd01cda57a4"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_imports2.cpython-36.pyc","mode":33188,"size":527,"sha256":"4fcc4125a4cb68c5f402584bcffd10664c96443f65d58ce76d4c99664c513381"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_input.cpython-36.opt-1.pyc","mode":33188,"size":929,"sha256":"881b634d6fd865833335c8ca14d3cde608fda65214dd8cb64b316d532b3eb7c2"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_input.cpython-36.opt-2.pyc","mode":33188,"size":860,"sha256":"93b7e24e00d290e7d5a09d84c57c953ff7ae17f540a83a92f2cb5dec7f24f565"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_input.cpython-36.pyc","mode":33188,"size":929,"sha256":"881b634d6fd865833335c8ca14d3cde608fda65214dd8cb64b316d532b3eb7c2"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_intern.cpython-36.opt-1.pyc","mode":33188,"size":1141,"sha256":"9c8e66b78ed075bffbeaee117a8f0f368874f3d57294c933bd8578db3ee9e8ed"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_intern.cpython-36.opt-2.pyc","mode":33188,"size":1077,"sha256":"23696951f5fda49e2e3df771016dde1d7b08d66585cc0ac8a85f981a0e5ce853"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_intern.cpython-36.pyc","mode":33188,"size":1141,"sha256":"9c8e66b78ed075bffbeaee117a8f0f368874f3d57294c933bd8578db3ee9e8ed"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_isinstance.cpython-36.opt-1.pyc","mode":33188,"size":1539,"sha256":"981c20aebbc8b976e74b490040adef22025397a04397aac2cd8f538b2b71f7ee"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_isinstance.cpython-36.opt-2.pyc","mode":33188,"size":1219,"sha256":"5f02df9b1604558d69768aeb90c9cd2645a11206f785a1de7387057e97f5126d"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_isinstance.cpython-36.pyc","mode":33188,"size":1539,"sha256":"981c20aebbc8b976e74b490040adef22025397a04397aac2cd8f538b2b71f7ee"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_itertools.cpython-36.opt-1.pyc","mode":33188,"size":1533,"sha256":"20cbe17960acc2598742009ee2723a95c1de555553e65a11651b1adf97b38542"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_itertools.cpython-36.opt-2.pyc","mode":33188,"size":1173,"sha256":"16d3ff6c188495922aeb7f440e05c936a4a0de44d0726c42d937baa4beceb57a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_itertools.cpython-36.pyc","mode":33188,"size":1533,"sha256":"20cbe17960acc2598742009ee2723a95c1de555553e65a11651b1adf97b38542"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_itertools_imports.cpython-36.opt-1.pyc","mode":33188,"size":1552,"sha256":"4b0431063e2be669c6bd24902d843c67aaaf328a7fc07a3b86f92c7b47aff9b4"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_itertools_imports.cpython-36.opt-2.pyc","mode":33188,"size":1470,"sha256":"1d30150f197f1df78ebddc4547134ad6a860ef0495918f88fdac83db0f861d3a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_itertools_imports.cpython-36.pyc","mode":33188,"size":1588,"sha256":"73d5e4ce0b6a30e10993100cef15449b20535733769f1e311d96bc0afbddfcbd"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_long.cpython-36.opt-1.pyc","mode":33188,"size":684,"sha256":"36cb255ac4de875c968f35d4dd726614ca46f9b06474d8d379c2b5cbe49efc92"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_long.cpython-36.opt-2.pyc","mode":33188,"size":620,"sha256":"785640fbec7e70008cc2efccfe9eac29170603a5d8d138b8e79e93c0a908c6ef"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_long.cpython-36.pyc","mode":33188,"size":684,"sha256":"36cb255ac4de875c968f35d4dd726614ca46f9b06474d8d379c2b5cbe49efc92"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_map.cpython-36.opt-1.pyc","mode":33188,"size":3072,"sha256":"7280c9e8030510d08f51c0a48b1d10a8ded7d0462dc6b74f278f949b6fbccb87"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_map.cpython-36.opt-2.pyc","mode":33188,"size":2276,"sha256":"56db3298976e001501323763a28c62434d70b1575e31bfe512d8bcd5ba832665"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_map.cpython-36.pyc","mode":33188,"size":3072,"sha256":"7280c9e8030510d08f51c0a48b1d10a8ded7d0462dc6b74f278f949b6fbccb87"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_metaclass.cpython-36.opt-1.pyc","mode":33188,"size":5314,"sha256":"99e0a0a3e1b7d4aab1a684d64801c5bb02e9418fff5f17c4a3fba98e6402613e"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_metaclass.cpython-36.opt-2.pyc","mode":33188,"size":3933,"sha256":"d1468ea0b74a0ab8da270ed7f786ffd6277bbec4aad37dfe322c90947a5362bd"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_metaclass.cpython-36.pyc","mode":33188,"size":5355,"sha256":"5a90d1fc85863293890e6b8d2fa909e759212131bd2c6c2a7ed33c2903beab87"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_methodattrs.cpython-36.opt-1.pyc","mode":33188,"size":915,"sha256":"2ad3190c2b940c74bdd1b1b6f2d1c76d8e926f272070dc0cf7763153a7cf0c7b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_methodattrs.cpython-36.opt-2.pyc","mode":33188,"size":839,"sha256":"c57da36c2e4be9b16c9107f4bc1f3bb200f5bcae6dbc4be829264d846f944703"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_methodattrs.cpython-36.pyc","mode":33188,"size":915,"sha256":"2ad3190c2b940c74bdd1b1b6f2d1c76d8e926f272070dc0cf7763153a7cf0c7b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_ne.cpython-36.opt-1.pyc","mode":33188,"size":786,"sha256":"e11c1fe5cdd467d2fcd40173f3cadf5aeea2df2ecf60a4c1cf8927f65f38f202"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_ne.cpython-36.opt-2.pyc","mode":33188,"size":741,"sha256":"657f7f1df1dc369e06c62e53909a021084ba16152e852200c8ab16a329bc0a64"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_ne.cpython-36.pyc","mode":33188,"size":786,"sha256":"e11c1fe5cdd467d2fcd40173f3cadf5aeea2df2ecf60a4c1cf8927f65f38f202"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_next.cpython-36.opt-1.pyc","mode":33188,"size":3011,"sha256":"4c28b55ea93075e7da9a8aa3895047284d91aabb65cb5796bf5450d005988c61"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_next.cpython-36.opt-2.pyc","mode":33188,"size":2948,"sha256":"80e02a3c8a6065a39cea39f4215c94b30b9b7fd39314684202d30b4877b0b3e0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_next.cpython-36.pyc","mode":33188,"size":3039,"sha256":"56253e119aa1d7af4a711b2a0839d8fdf1acaf9af3e3bd9372cd649453be710d"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_nonzero.cpython-36.opt-1.pyc","mode":33188,"size":902,"sha256":"8d8e97602d667278c76c1febcaabcc1c6d519ab077e71123172a837770707ad9"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_nonzero.cpython-36.opt-2.pyc","mode":33188,"size":843,"sha256":"f075db1250cb684839a3248b32b8289e20fb8b33e065674c1fe618ba924ce4fe"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_nonzero.cpython-36.pyc","mode":33188,"size":902,"sha256":"8d8e97602d667278c76c1febcaabcc1c6d519ab077e71123172a837770707ad9"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_numliterals.cpython-36.opt-1.pyc","mode":33188,"size":1008,"sha256":"ec59db2aec1ef5dc0ec696cc2de938ead6d060820e8ccd13f97fd33c5a59dfff"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_numliterals.cpython-36.opt-2.pyc","mode":33188,"size":946,"sha256":"ee8ae637f7350a19e1f07184fa895f5dd5f8ef251b4ffb6e6c86c7f4e3032244"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_numliterals.cpython-36.pyc","mode":33188,"size":1008,"sha256":"ec59db2aec1ef5dc0ec696cc2de938ead6d060820e8ccd13f97fd33c5a59dfff"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_operator.cpython-36.opt-1.pyc","mode":33188,"size":4216,"sha256":"d0c56164f40abd71a6394f67a8df7938b5a91667469b51580d1a798f01cd0e8b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_operator.cpython-36.opt-2.pyc","mode":33188,"size":3729,"sha256":"21b17758227521f66cadbc57d48760af5be4b47a9774970afee4a9df2b5ca04d"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_operator.cpython-36.pyc","mode":33188,"size":4216,"sha256":"d0c56164f40abd71a6394f67a8df7938b5a91667469b51580d1a798f01cd0e8b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_paren.cpython-36.opt-1.pyc","mode":33188,"size":1369,"sha256":"c0f75bd7892f0d174542e8ca172cf794374735eb8f7eeb4a9e37d25375d98e95"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_paren.cpython-36.opt-2.pyc","mode":33188,"size":1235,"sha256":"3bac645fc4d92a4db259d22735dd44491ec1a4b67f5dcf22cc6697420089875f"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_paren.cpython-36.pyc","mode":33188,"size":1369,"sha256":"c0f75bd7892f0d174542e8ca172cf794374735eb8f7eeb4a9e37d25375d98e95"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_print.cpython-36.opt-1.pyc","mode":33188,"size":2230,"sha256":"5523ea632193e53d6ab6ddfaf165cf72c909054838c0a56bbffb763490d3cb59"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_print.cpython-36.opt-2.pyc","mode":33188,"size":1943,"sha256":"739be2aa7adafc4a5f1f7337d2236d749340cb6f4bbb794216cac915a28208af"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_print.cpython-36.pyc","mode":33188,"size":2309,"sha256":"da2eee13615042c12e14e4da9aeac929cb5c7ffcaffa3c7537b6daa33e54f867"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_raise.cpython-36.opt-1.pyc","mode":33188,"size":2228,"sha256":"c71a2a8070681e5ccfa100dc82b79661ce0d7524b6de3e4c2af9e6f0b7413f42"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_raise.cpython-36.opt-2.pyc","mode":33188,"size":1605,"sha256":"a81f3039260976bcd0654367f8b080bbe7ffda71ea0734d4df328edf68ee0d62"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_raise.cpython-36.pyc","mode":33188,"size":2228,"sha256":"c71a2a8070681e5ccfa100dc82b79661ce0d7524b6de3e4c2af9e6f0b7413f42"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_raw_input.cpython-36.opt-1.pyc","mode":33188,"size":774,"sha256":"c949eb7c4eca510bf5fc90f11045a587cba8ee984de660cdb532e89c1858b36e"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_raw_input.cpython-36.opt-2.pyc","mode":33188,"size":707,"sha256":"9abc17bc9ad4670841b44fc587d797420063f4eeb7411419c19b60ad2f64a9d2"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_raw_input.cpython-36.pyc","mode":33188,"size":774,"sha256":"c949eb7c4eca510bf5fc90f11045a587cba8ee984de660cdb532e89c1858b36e"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_reduce.cpython-36.opt-1.pyc","mode":33188,"size":1109,"sha256":"9375b94ac322db65cfc05a3b20aa929cddc557c328431e8cfffadf6b7432ba18"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_reduce.cpython-36.opt-2.pyc","mode":33188,"size":979,"sha256":"aebdf7bc7ba079b4c9b77c2d214ac26ed06ef51bc1012e7567a00ab45ddcc172"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_reduce.cpython-36.pyc","mode":33188,"size":1109,"sha256":"9375b94ac322db65cfc05a3b20aa929cddc557c328431e8cfffadf6b7432ba18"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_reload.cpython-36.opt-1.pyc","mode":33188,"size":1141,"sha256":"ef806566016b0fed84e144cbcfc0cffbeaefed71f1640754b49f5f08d8cba379"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_reload.cpython-36.opt-2.pyc","mode":33188,"size":1077,"sha256":"03108acaca7ebac198a26514d6a75acb7f2523496232d5ecdbcf47313bf61ab1"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_reload.cpython-36.pyc","mode":33188,"size":1141,"sha256":"ef806566016b0fed84e144cbcfc0cffbeaefed71f1640754b49f5f08d8cba379"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_renames.cpython-36.opt-1.pyc","mode":33188,"size":1972,"sha256":"471e3ddbd3edead9de72531a6f4a23708adff0373796ea1f7cf5b86ea7b57625"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_renames.cpython-36.opt-2.pyc","mode":33188,"size":1892,"sha256":"38cc2c5a38ba4fdbeec786073380eec878976659b5b585024740fcc8aafd4ff2"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_renames.cpython-36.pyc","mode":33188,"size":1972,"sha256":"471e3ddbd3edead9de72531a6f4a23708adff0373796ea1f7cf5b86ea7b57625"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_repr.cpython-36.opt-1.pyc","mode":33188,"size":824,"sha256":"7c7e98804723a6b5345b9e66e94cd8931c6b79db7b13a469acd26bf6503ac466"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_repr.cpython-36.opt-2.pyc","mode":33188,"size":760,"sha256":"905667c274dbfd534b1d9f077e343c82ff5203cd97936c7ca7b634a897745eb5"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_repr.cpython-36.pyc","mode":33188,"size":824,"sha256":"7c7e98804723a6b5345b9e66e94cd8931c6b79db7b13a469acd26bf6503ac466"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_set_literal.cpython-36.opt-1.pyc","mode":33188,"size":1666,"sha256":"fa1112a506d52086c907c29afc695ccab5672159fd813a0c1261931a21c2210a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_set_literal.cpython-36.opt-2.pyc","mode":33188,"size":1591,"sha256":"4716642ab570b70f05eb8ccda2981d901305fe43a4d2942e4da13874d713ac30"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_set_literal.cpython-36.pyc","mode":33188,"size":1666,"sha256":"fa1112a506d52086c907c29afc695ccab5672159fd813a0c1261931a21c2210a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_standarderror.cpython-36.opt-1.pyc","mode":33188,"size":699,"sha256":"2f7343a12db02d5df917b41ca69c0633106f18568de0ce7add337b716501f3f4"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_standarderror.cpython-36.opt-2.pyc","mode":33188,"size":645,"sha256":"e1812f4cf92572332724aba7cefcc9e05cafd93170f62a33752aca1964e3699a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_standarderror.cpython-36.pyc","mode":33188,"size":699,"sha256":"2f7343a12db02d5df917b41ca69c0633106f18568de0ce7add337b716501f3f4"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_sys_exc.cpython-36.opt-1.pyc","mode":33188,"size":1380,"sha256":"6e8613807ac080507bcca4d1ac8f76f33d8e52d221ebbd2962131a3213f94c7b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_sys_exc.cpython-36.opt-2.pyc","mode":33188,"size":1211,"sha256":"7c3189bd1ca8c2a1b1cb4faa9027b09ec40d9b402eb5fc724140386929aac2a0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_sys_exc.cpython-36.pyc","mode":33188,"size":1380,"sha256":"6e8613807ac080507bcca4d1ac8f76f33d8e52d221ebbd2962131a3213f94c7b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_throw.cpython-36.opt-1.pyc","mode":33188,"size":1781,"sha256":"e5aafe5f89d3298d70ef7d6d4ee799b0bcb05092fea870014bce452d5f404394"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_throw.cpython-36.opt-2.pyc","mode":33188,"size":1550,"sha256":"2de107729f776da10d554900889643707dfc12362201ae243511df20b9d11d9b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_throw.cpython-36.pyc","mode":33188,"size":1781,"sha256":"e5aafe5f89d3298d70ef7d6d4ee799b0bcb05092fea870014bce452d5f404394"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_tuple_params.cpython-36.opt-1.pyc","mode":33188,"size":4575,"sha256":"9fcbb002b96f362752abbfeef69b2edabcec5e3453ca936a8dbf9ff672a50c1f"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_tuple_params.cpython-36.opt-2.pyc","mode":33188,"size":4241,"sha256":"806e020efb5adeb43dd5c3011eb9f78bd6dedfc8a767d551728bf40605fb8234"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_tuple_params.cpython-36.pyc","mode":33188,"size":4575,"sha256":"9fcbb002b96f362752abbfeef69b2edabcec5e3453ca936a8dbf9ff672a50c1f"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_types.cpython-36.opt-1.pyc","mode":33188,"size":1808,"sha256":"05732ff12467b48b9cefdaf4699c7f2d91d27fd225786457a62f81befa42ddb6"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_types.cpython-36.opt-2.pyc","mode":33188,"size":1334,"sha256":"52506ec870f739cc489ef2dd6e370ebb2ce0c945994b942858b93a9e5456fd02"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_types.cpython-36.pyc","mode":33188,"size":1808,"sha256":"05732ff12467b48b9cefdaf4699c7f2d91d27fd225786457a62f81befa42ddb6"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_unicode.cpython-36.opt-1.pyc","mode":33188,"size":1522,"sha256":"7e365b278465cdc0c57dc554e596f134ce29ca960f44741c43156d401c885305"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_unicode.cpython-36.opt-2.pyc","mode":33188,"size":1343,"sha256":"bc0245e30db52dfe84d3a783207251a76d27d8eab63814f89220464ff8446798"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_unicode.cpython-36.pyc","mode":33188,"size":1522,"sha256":"7e365b278465cdc0c57dc554e596f134ce29ca960f44741c43156d401c885305"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_urllib.cpython-36.opt-1.pyc","mode":33188,"size":5967,"sha256":"1384a27fcb66fbea3789216d449775b5e1320066bf82dd047a186e0322ff2a0e"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_urllib.cpython-36.opt-2.pyc","mode":33188,"size":5409,"sha256":"9b92387a95fd906456a514f04ee071be593e86983a3dde31fe18d5d76e897174"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_urllib.cpython-36.pyc","mode":33188,"size":5967,"sha256":"1384a27fcb66fbea3789216d449775b5e1320066bf82dd047a186e0322ff2a0e"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_ws_comma.cpython-36.opt-1.pyc","mode":33188,"size":1102,"sha256":"fcbb7f4166fe9d68e255668c660dd01d8e15639b03bc89af9eb9d3ab3734669b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_ws_comma.cpython-36.opt-2.pyc","mode":33188,"size":916,"sha256":"bb655b5c9faf12515c27a901321fc9e0a02d3e49b25499c06e3ab58f6e815bb7"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_ws_comma.cpython-36.pyc","mode":33188,"size":1102,"sha256":"fcbb7f4166fe9d68e255668c660dd01d8e15639b03bc89af9eb9d3ab3734669b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_xrange.cpython-36.opt-1.pyc","mode":33188,"size":2517,"sha256":"4aaa6d44166adc83994da8ff41b7e31db6f09b433e3720bdbccacffe0917eed4"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_xrange.cpython-36.opt-2.pyc","mode":33188,"size":2453,"sha256":"145b2f20d9c89df522355e8d3ca97702fd24aa4eb4338420cab23f821c4cdae0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_xrange.cpython-36.pyc","mode":33188,"size":2517,"sha256":"4aaa6d44166adc83994da8ff41b7e31db6f09b433e3720bdbccacffe0917eed4"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_xreadlines.cpython-36.opt-1.pyc","mode":33188,"size":1096,"sha256":"941f0d77ed2f29c362e07b4bf399d03cfe3860706097e8d188f83a7dfda05fd0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_xreadlines.cpython-36.opt-2.pyc","mode":33188,"size":967,"sha256":"b90f0ab7044ac4cd68e0010cb7e84713309648391caefd1e2f85bbea9c8ecd42"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_xreadlines.cpython-36.pyc","mode":33188,"size":1096,"sha256":"941f0d77ed2f29c362e07b4bf399d03cfe3860706097e8d188f83a7dfda05fd0"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_zip.cpython-36.opt-1.pyc","mode":33188,"size":1560,"sha256":"b26c62eadc02d8d5520fec36fd6ec580c03ed7209e5e93b80cf4f4ee3a28cd9a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_zip.cpython-36.opt-2.pyc","mode":33188,"size":1229,"sha256":"b5e6667b0f966eb1831a0c5efc5fbf89719bed2c4ae57ced1f88a22e6a391fd3"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/__pycache__/fix_zip.cpython-36.pyc","mode":33188,"size":1560,"sha256":"b26c62eadc02d8d5520fec36fd6ec580c03ed7209e5e93b80cf4f4ee3a28cd9a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_apply.py","mode":33188,"size":2430,"sha256":"2bde1a37871cac0ba05b531ff989c2e9433f9f93bcf295551b4acf11ae725e52"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_asserts.py","mode":33188,"size":984,"sha256":"4c77972812cb5ec0a72afbce3e1d618c27ef7b239329c5c952c2bcbe77dba5dd"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_basestring.py","mode":33188,"size":320,"sha256":"d041443d6499a735bb78fec9da1bf33b3d034b5192c98bc273b16a44692fc88f"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_buffer.py","mode":33188,"size":590,"sha256":"2da37b49c30d6a0b4db43146ebb4ac8e5ffcb9814816b4742e464cb856977883"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_dict.py","mode":33188,"size":3760,"sha256":"38f460596ebfb64046aab3d9a65935bd4c76a470118fb7d10a088dc0ecdc53ea"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_except.py","mode":33188,"size":3344,"sha256":"7ff6f560c3c3d7a5d9ceef5ba31c556341f7ce1bc1b52d96b063f6c2c4765651"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_exec.py","mode":33188,"size":979,"sha256":"9e0893327205dea12004e88d18c580286e7977e081b5eda7baf5b7bc93bc6c52"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_execfile.py","mode":33188,"size":2048,"sha256":"6ff65db1192099457cb3d9f2618a893c6ac430028550284f3a34d5c08042b0eb"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_exitfunc.py","mode":33188,"size":2495,"sha256":"ef4f18f651d32410c43644c27590903d41e38e763b0e108e6c685a3412a7d29c"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_filter.py","mode":33188,"size":2651,"sha256":"117f34254fcc12cb492eb9475ad15ddb460a2b1971f066c369e4cf86ce4ef19e"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_funcattrs.py","mode":33188,"size":644,"sha256":"111df53fac6a121d61abe33883a68e731820ddc4864b0a4c1000cf2ac5f019cd"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_future.py","mode":33188,"size":547,"sha256":"baba8cafb48dd9181a0e1f7b0f20b585ce2925e8f347e00b87407a256bb16663"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_getcwdu.py","mode":33188,"size":451,"sha256":"5bc5252f683a401e7d81c5911617c4af1a1bcdf99a51c4bf1cfccb00446ff220"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_has_key.py","mode":33188,"size":3196,"sha256":"32943d3b921c1c3f0d3776d19e5120806990b817bc99a7e22799847abfda1f63"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_idioms.py","mode":33188,"size":4876,"sha256":"600e34faf36e14307e59d55088e3979881d497b8fc9d77659e77709f9e8bafd7"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_import.py","mode":33188,"size":3256,"sha256":"803baf96f9603c957eb974f252b0ad9829c889a293e0ce6829db1bce3da6dd4e"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_imports.py","mode":33188,"size":5684,"sha256":"cdf7ee6d85e2b148230984cfc4ea3f193be458958ea42ef290854a9672a64370"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_imports2.py","mode":33188,"size":289,"sha256":"b6f3c628839ffe7fd72569dd6ca2210e18edae3e180002747ea011b76b7ec0ef"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_input.py","mode":33188,"size":708,"sha256":"10c5ef3b45a4ee7e88af8852181916a788aae2bea52b08f3473815c1c43598d1"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_intern.py","mode":33188,"size":1235,"sha256":"199a203f698769e51e5333afd87772b7cb5449a935deedb31acb509960d75405"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_isinstance.py","mode":33188,"size":1608,"sha256":"8408c92b99f50d8c4978b47a2b2155588e315f2ebbe58c160dcdcdcb89e19914"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_itertools.py","mode":33188,"size":1548,"sha256":"578a51b9935020b03a510de15ece55fcd02c9474f37a54c158fb97ba5fd15af1"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_itertools_imports.py","mode":33188,"size":2086,"sha256":"2e419cfbd7f2a326ae7fa10873aa377112ebec32545238fdf988acb088c3cdb7"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_long.py","mode":33188,"size":476,"sha256":"306b80e0a72c0d16dd934b7d51ab0c9a4224f83be5d6cbad8a7158a0a5d73551"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_map.py","mode":33188,"size":3640,"sha256":"b82c0762c44adf2af7745c030afe291e2badfe360925046c8e58d85340717696"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_metaclass.py","mode":33188,"size":8197,"sha256":"9c876be8ef0bfaa500a9471eb0c13967ede8704f85a2e1804da756128e6c2259"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_methodattrs.py","mode":33188,"size":606,"sha256":"8d60082f98ce52ee4955099bfd447cbadfa0e9b24ccb8d135cecc833168d44e8"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_ne.py","mode":33188,"size":571,"sha256":"4f9cb1388ba86f29422d20979d3423fdf3541ba35a17ed44d6f4a517ff784ecd"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_next.py","mode":33188,"size":3174,"sha256":"5c7d86d9f81b2498486d626c7feced1b92f23171cf9e42881abb78de1a93bccd"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_nonzero.py","mode":33188,"size":591,"sha256":"c2cd7e3ba44508643a20eec4ea4c19f2f1adfd36f6b974d7c143e449571ae736"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_numliterals.py","mode":33188,"size":768,"sha256":"1c4dd0f7881999abde6cf4d232836fa3e55fc41a7d5aa2b9866092f65707db7f"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_operator.py","mode":33188,"size":3471,"sha256":"38bf8fbf1b758382d551f9d8a3ae9b630704b337448f1e2895acfd5b505f3dd4"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_paren.py","mode":33188,"size":1227,"sha256":"158b87396dba4d0d5a1bde3ab008206c155934d53508889398e2ca6b4de3d91b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_print.py","mode":33188,"size":2844,"sha256":"cf2690f1b502249289f52cd544190db0b94d59df5eca139829cd2bf0742e9dba"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_raise.py","mode":33188,"size":2926,"sha256":"c38ffec5862597ee8f9dac50385af943ee312bfc394366be08b2fc12563ca1a5"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_raw_input.py","mode":33188,"size":454,"sha256":"ce04cbaa76d414949afc230360dd9a29ff579bd868cc7f8805230d126ac9ce9b"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_reduce.py","mode":33188,"size":837,"sha256":"9a03910a6c183586e1db01863fcde6417d06745fb3e63032333d71c5e82e7919"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_reload.py","mode":33188,"size":1154,"sha256":"cf8a199092e705aec632a4d27f93bc761e578510cadf27bee7a84d891482e9ef"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_renames.py","mode":33188,"size":2221,"sha256":"8b71472317bf3adabf819e665c725d03e3064baa45f6ffbfd78cca83eaa46e8d"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_repr.py","mode":33188,"size":613,"sha256":"d16930b7ef8577747cfef602aba854c64ce85d4ae1e54a18a456eaa202643e3d"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_set_literal.py","mode":33188,"size":1697,"sha256":"33f2c0b6e16357e083c3a98877e7317abe1578a44c288e5979c9d96fb5aa6727"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_standarderror.py","mode":33188,"size":449,"sha256":"ce7eb37bc7fb29aa138b1cec6656ae8b4886cbfa700e119a1bb8484284cb717a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_sys_exc.py","mode":33188,"size":1034,"sha256":"0143830586d09d702ca3eeaa8f86698e5fd18af69fd28147e71a1a77600d356a"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_throw.py","mode":33188,"size":1582,"sha256":"fec731ed523d5cdfa21893833b52b2844eabfd1549792c1c9f8ceac2d0e8e901"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_tuple_params.py","mode":33188,"size":5565,"sha256":"f3307d4750d0657d9c42b857d5f37bdb5824f9358939da7d16d13f61eb8abc72"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_types.py","mode":33188,"size":1774,"sha256":"a0a133cfc78e82e1f71ce628408e7d10a38552ba3e3228ebd113838c1ce44484"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_unicode.py","mode":33188,"size":1256,"sha256":"01b2a9b1084b6a0424f27eec488c761f75f053a409608ec36a9ee0ede0d38097"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_urllib.py","mode":33188,"size":8353,"sha256":"14fd0b3433db387db33987f1e3071d47c13dc83d1e902aed6b9d7d0ea3189061"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_ws_comma.py","mode":33188,"size":1090,"sha256":"5e7a16daec0b2619110516804bf90cac459a4d0315198fd4eff69c36c54378dd"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_xrange.py","mode":33188,"size":2694,"sha256":"60d8ce92db6f399606d2e40a3c631ba566127e8cd637ebbf35b822672139cab2"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_xreadlines.py","mode":33188,"size":689,"sha256":"e8c2f19f7047bfc7539fd78839929004d8fe0efba1fbcbd9d712d285e43834ba"},{"path":"/usr/lib64/python3.6/lib2to3/fixes/fix_zip.py","mode":33188,"size":1289,"sha256":"55ce115556c7513dd967364dc6a40c39210c874e8168cf090ddd6dc606df34cb"},{"path":"/usr/lib64/python3.6/lib2to3/main.py","mode":33188,"size":11653,"sha256":"bec917f26fe605744cd34e51bf5de3be5baf63ceda573c0cdc4c5fb383390fce"},{"path":"/usr/lib64/python3.6/lib2to3/patcomp.py","mode":33188,"size":7044,"sha256":"7824650a0342c63594ce9cd026b3a15b405729fa9e0e7af77a63d054a6f6818b"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__init__.py","mode":33188,"size":143,"sha256":"858eb0f50533bd3bd16fe32815f77fabfed92ede885070b6cb15827ec66ea500"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":159,"sha256":"4ba986149cad4ee9d2fa03fb6d0270629c823650c6b58a04a9ea2c0509ff844d"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":131,"sha256":"7c4a87698db495b5c4d62c40644de8559b484c2d95b7da4b5bc5c94049104dbb"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":159,"sha256":"4ba986149cad4ee9d2fa03fb6d0270629c823650c6b58a04a9ea2c0509ff844d"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/conv.cpython-36.opt-1.pyc","mode":33188,"size":6148,"sha256":"275ce33b303ba52d27671604bb0a5910ae7d5f34347bbc26435c7aa6e4d19ef5"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/conv.cpython-36.opt-2.pyc","mode":33188,"size":3664,"sha256":"7f5472715a12ef965a70c9b35feca9348c42b6399c0ffca68dbb0ac3289a6b66"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/conv.cpython-36.pyc","mode":33188,"size":7032,"sha256":"ff789b5f1555a5b277da6f223b5750e0b11be3f3ba91ca5920b72cd0da7f4a69"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/driver.cpython-36.opt-1.pyc","mode":33188,"size":5080,"sha256":"10eec6e8053105b39888c9f441893c05775648e5e5ee143b93524f2bfb7c6187"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/driver.cpython-36.opt-2.pyc","mode":33188,"size":4035,"sha256":"893f0f5c322b4e10729c75ac199f090e7be03fe86ef3c86a2d7dcb247e4cf8d9"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/driver.cpython-36.pyc","mode":33188,"size":5128,"sha256":"28961b6cf731efcc389f7578954dfdeced0a7ec98cbdcfa1ef883c4fd4126e5c"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/grammar.cpython-36.opt-1.pyc","mode":33188,"size":7057,"sha256":"a645572ce070330bdff93471d11193aae4722f1a75cdda8d6aa39e4b6416ed49"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/grammar.cpython-36.opt-2.pyc","mode":33188,"size":3243,"sha256":"0ff1ea8d2d41640073d2d140427018033f42a500d9b0fba2d041a22b3965e76d"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/grammar.cpython-36.pyc","mode":33188,"size":7057,"sha256":"a645572ce070330bdff93471d11193aae4722f1a75cdda8d6aa39e4b6416ed49"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/literals.cpython-36.opt-1.pyc","mode":33188,"size":1346,"sha256":"847126b439dae7049ad21830e96c5d5ba79e0355dd50932cdac16d67a86d1223"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/literals.cpython-36.opt-2.pyc","mode":33188,"size":1269,"sha256":"bcfdfca8914ed5e3a3fd6ac1f623ed8510ea9abbd8a7b7de476e3f4c205d1836"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/literals.cpython-36.pyc","mode":33188,"size":1534,"sha256":"c1a8beb75746cead22138ed6224b8767956f950e76d6f0da0816643467a094cc"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/parse.cpython-36.opt-1.pyc","mode":33188,"size":6299,"sha256":"f11fab46ffc948b81c61616ba1e45206ef7c2af3d1238b579e56cb297bd58227"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/parse.cpython-36.opt-2.pyc","mode":33188,"size":3078,"sha256":"943570cdf23547799eb7d89fac0f2cf7dfaa84bb8ec6809ef171bff9daab08dd"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/parse.cpython-36.pyc","mode":33188,"size":6329,"sha256":"d260414e1565523a3058865778db57077a25fb3c58a3bfbb8e698197c8d82b02"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/pgen.cpython-36.opt-1.pyc","mode":33188,"size":9333,"sha256":"d26e753d8ac87c317651c0d8bb7798788c44a4bdb6c55a30c76783e96c1c301a"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/pgen.cpython-36.opt-2.pyc","mode":33188,"size":9333,"sha256":"d26e753d8ac87c317651c0d8bb7798788c44a4bdb6c55a30c76783e96c1c301a"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/pgen.cpython-36.pyc","mode":33188,"size":9785,"sha256":"76ba6fefcfdcdaaa2a9f918b8b1220f1155df765e3c48a044e1c491d62f442c9"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/token.cpython-36.opt-1.pyc","mode":33188,"size":1852,"sha256":"e188fb2536808650d74ccf18cc579b7d4dd216aa143f7c0debf5cb39885b8752"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/token.cpython-36.opt-2.pyc","mode":33188,"size":1802,"sha256":"7f9985b6105adb1774fcdd0e6854af025bff058241b04519a203cef1765e4175"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/token.cpython-36.pyc","mode":33188,"size":1852,"sha256":"e188fb2536808650d74ccf18cc579b7d4dd216aa143f7c0debf5cb39885b8752"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/tokenize.cpython-36.opt-1.pyc","mode":33188,"size":15314,"sha256":"6250c585c47814df554c69b4050c607a128cc4b64cbd1624b63de3746cd5aabe"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/tokenize.cpython-36.opt-2.pyc","mode":33188,"size":11383,"sha256":"9b19d7a5968a1b988dcc9e2c67c7f63a044379594163af20b4e37f28028e03a2"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/__pycache__/tokenize.cpython-36.pyc","mode":33188,"size":15386,"sha256":"84d0e894b03364782740ad564eef930a1cf36685f0031b7bb053f008d526c4be"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/conv.py","mode":33188,"size":9642,"sha256":"e2946a686c12e02248fafb1a57e7514e0c22bdb2b4a66e644215c86fedc37bff"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/driver.py","mode":33188,"size":6028,"sha256":"c1df201c034ed2555ef6aeea9e451c0e64153541dbc4834f28587cb0712412a0"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/grammar.py","mode":33188,"size":6589,"sha256":"9b4dbade76fb732f2994028b0948e283d320d162e95945a1f4df0c46ed4749f9"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/literals.py","mode":33188,"size":1615,"sha256":"cf8f3643226e6dcce993efa0f55e0a9f181ad9c4b366d9d4c8defae3dfdc593d"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/parse.py","mode":33188,"size":8053,"sha256":"ef205d15dd8a2184df48dfcba354037cc7c0f38d939bd5cdc5e56fc05f81cb18"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/pgen.py","mode":33188,"size":13812,"sha256":"2491291537fedb8765dca1c5e2ba34c0a0e3980e4ca3e3bb2b0d3ee293f37861"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/token.py","mode":33261,"size":1294,"sha256":"1260e8f7b14be9d651e9cc912216aacc8dd853c003efa20d9c8e28e9b66b0d7f"},{"path":"/usr/lib64/python3.6/lib2to3/pgen2/tokenize.py","mode":33188,"size":22606,"sha256":"6e3d700e6c984bace27ef59bb10d73498f2a3dec13bc1c5d2064ac6e5ba34e83"},{"path":"/usr/lib64/python3.6/lib2to3/pygram.py","mode":33188,"size":1154,"sha256":"a40f91564f009c169fdb5d3ef0f2011a819b4997c98b2dc496ae03fa6a9e0d3b"},{"path":"/usr/lib64/python3.6/lib2to3/pytree.py","mode":33188,"size":28052,"sha256":"b57195c6daa4f9c88b0913328ba0468e08b5bbe24d4cb685331a3554453163bb"},{"path":"/usr/lib64/python3.6/lib2to3/refactor.py","mode":33188,"size":27965,"sha256":"24a1125b9d68fe19e8f6bd53927d753cc5a4c0952a3c684fbe80f1d55cbb3b3b"},{"path":"/usr/lib64/python3.6/linecache.py","mode":33188,"size":5312,"sha256":"c654a9e19e83d5f826281f0573223d91a60066c572bc6909bc281fa8557f15ef"},{"path":"/usr/lib64/python3.6/locale.py","mode":33188,"size":77300,"sha256":"2578aa6fb9bb65176e9c9608185fa6e1f7628e11564a0e1f03d5af5fbbb2d9e1"},{"path":"/usr/lib64/python3.6/logging/__init__.py","mode":33188,"size":71269,"sha256":"70103f84665c49aa073fd3cd2e76decfe40b74c5a5a2578abc43eeb4cfa55fe2"},{"path":"/usr/lib64/python3.6/logging/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":60365,"sha256":"29bd2ee2e0d1489ad33b414eeb7aa5c021eea785076e39e29d984e05b91a872c"},{"path":"/usr/lib64/python3.6/logging/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":32518,"sha256":"3a10d3a688830f88a14d5c051cc41d310c119fcab4813881d3b081bb5ffeb669"},{"path":"/usr/lib64/python3.6/logging/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":60397,"sha256":"18d691c1e36f00cd82ecf7135a3cc92a9ec5ae2fd9e0dc65b0fa5f1eb41d7a37"},{"path":"/usr/lib64/python3.6/logging/__pycache__/config.cpython-36.opt-1.pyc","mode":33188,"size":23342,"sha256":"5109fed60ecb1c6ae0ced8e34e3f214a89415e5e2269a1a0e0b15fc4e95db0f1"},{"path":"/usr/lib64/python3.6/logging/__pycache__/config.cpython-36.opt-2.pyc","mode":33188,"size":19222,"sha256":"9b74e418b04497f2d208dc9105f547dfbc6febadfefdb2790b31aa8f8a5d8b4a"},{"path":"/usr/lib64/python3.6/logging/__pycache__/config.cpython-36.pyc","mode":33188,"size":23390,"sha256":"0707c9fc0629dfecfb32c97bef6182d884b76e9881b5053733040cc560cc741a"},{"path":"/usr/lib64/python3.6/logging/__pycache__/handlers.cpython-36.opt-1.pyc","mode":33188,"size":43254,"sha256":"1c0c8961cb3ff02f479f68f0f6b0aac46c89ca2d40c5119d211d87cb0e20cf35"},{"path":"/usr/lib64/python3.6/logging/__pycache__/handlers.cpython-36.opt-2.pyc","mode":33188,"size":24275,"sha256":"fa3b2e987d0f1976dfa91ad9ba581d2cedf94f70b1e106f99e68fa45328d472b"},{"path":"/usr/lib64/python3.6/logging/__pycache__/handlers.cpython-36.pyc","mode":33188,"size":43254,"sha256":"1c0c8961cb3ff02f479f68f0f6b0aac46c89ca2d40c5119d211d87cb0e20cf35"},{"path":"/usr/lib64/python3.6/logging/config.py","mode":33188,"size":36048,"sha256":"05808e3b82182bc3010f4e2dc46ecc779e624018b9fc7bc67fed318d7477577c"},{"path":"/usr/lib64/python3.6/logging/handlers.py","mode":33188,"size":58053,"sha256":"b320532d2fa00892f3885d72f4c75b6ab90c83dd9b040c425ad38a7d88f8e09a"},{"path":"/usr/lib64/python3.6/lzma.py","mode":33188,"size":12983,"sha256":"a916f11363a523d3e8ad3dbcec36d38e03118724efa1203c2a6785d3141997fb"},{"path":"/usr/lib64/python3.6/macpath.py","mode":33188,"size":5971,"sha256":"902e6a2be4ce6f5facc1beedc25c73ffedeb6a04b1baaba7d44e13f2f505acd9"},{"path":"/usr/lib64/python3.6/macurl2path.py","mode":33188,"size":2732,"sha256":"4707ad5be6a539bba7eb3eec350ca5414b57d70e8f789c929a28f87e1fba7818"},{"path":"/usr/lib64/python3.6/mailbox.py","mode":33188,"size":78624,"sha256":"c211ee100862a9f1b994692bdeb5395c06b14dde277faf033f51ed1e55b3b0bd"},{"path":"/usr/lib64/python3.6/mailcap.py","mode":33188,"size":8104,"sha256":"2d1c0c8ea35616cca8cec50b1ee7c070672ebd80d2037fc3502b84cff3d1ec3d"},{"path":"/usr/lib64/python3.6/mimetypes.py","mode":33188,"size":21042,"sha256":"3a4a833fca7ec9d6a31422951755b0f1460018bd3168aba84f9f90be471eaf0e"},{"path":"/usr/lib64/python3.6/modulefinder.py","mode":33188,"size":23027,"sha256":"7992c14323e063038b4f9e80ef5b0cc907c04c6a08d86e0a6fae28607afd95c5"},{"path":"/usr/lib64/python3.6/multiprocessing/__init__.py","mode":33188,"size":923,"sha256":"ff3cc56e5007a4f0c3f8eff5327798e4545adec5644efc1bb45d1d4b89e64673"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":507,"sha256":"6d0f0cc4e36fb5d37725b71c510b5c5d8d583c0a61b36b4428edd98a786ac0fc"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":507,"sha256":"6d0f0cc4e36fb5d37725b71c510b5c5d8d583c0a61b36b4428edd98a786ac0fc"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":507,"sha256":"6d0f0cc4e36fb5d37725b71c510b5c5d8d583c0a61b36b4428edd98a786ac0fc"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/connection.cpython-36.opt-1.pyc","mode":33188,"size":24543,"sha256":"d1ccb682aa07b5273542cc1239f44901af56c6126098151c0678512d57459de3"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/connection.cpython-36.opt-2.pyc","mode":33188,"size":22312,"sha256":"b96f0b38648d6d748865876be65afd9fd7e000482bad558e72c3ab4a083919d9"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/connection.cpython-36.pyc","mode":33188,"size":24838,"sha256":"fda826f07afcbf92c1236fe81ff675130478916965b37cdfc6299f4f86644383"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/context.cpython-36.opt-1.pyc","mode":33188,"size":13098,"sha256":"9abe4ae6e497494583cf8da92a0af4343b3a02ed56ca03f1bc064514141dc6e8"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/context.cpython-36.opt-2.pyc","mode":33188,"size":11603,"sha256":"523f4f4ded652f1548f144cca59181384fdacc6132cfe681446083f4cda967e8"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/context.cpython-36.pyc","mode":33188,"size":13098,"sha256":"9abe4ae6e497494583cf8da92a0af4343b3a02ed56ca03f1bc064514141dc6e8"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/forkserver.cpython-36.opt-1.pyc","mode":33188,"size":6742,"sha256":"3b97cd9bd11b2c420eb67fdecadc43859adc038f1ef93e5acbca41b8abf8abab"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/forkserver.cpython-36.opt-2.pyc","mode":33188,"size":5953,"sha256":"d57f7885e9ca553ffc582f5db5a4980e38b6cd2afc253f00a0d6a59a2f00b664"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/forkserver.cpython-36.pyc","mode":33188,"size":6838,"sha256":"a24581ec45031e6c3784e392e6c14fd8d427541fd293f8f5be30e5fe1e36bd75"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/heap.cpython-36.opt-1.pyc","mode":33188,"size":5893,"sha256":"a0d682e032ccb5afe6d4b73cd86e02a06f6974a09001d76a3b931a263a987f92"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/heap.cpython-36.opt-2.pyc","mode":33188,"size":5893,"sha256":"a0d682e032ccb5afe6d4b73cd86e02a06f6974a09001d76a3b931a263a987f92"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/heap.cpython-36.pyc","mode":33188,"size":6079,"sha256":"547af94c4cf271819301ee47d0a861e82b0b7148ad2e8e57be0ce3b9db4982af"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/managers.cpython-36.opt-1.pyc","mode":33188,"size":32812,"sha256":"d222f606862732beda282404b7f429077beaf50bcbaba8acb24d440ec467ef44"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/managers.cpython-36.opt-2.pyc","mode":33188,"size":30370,"sha256":"0c80bf6040723ae48882ff2f7fd64f9aa70a658fa8bb0f76811e5bd648311289"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/managers.cpython-36.pyc","mode":33188,"size":33322,"sha256":"66b41424d8d3ffa11319621718f4cdae66901e53978f93275449acac3754ea87"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/pool.cpython-36.opt-1.pyc","mode":33188,"size":20566,"sha256":"496dfe73e1f97c490643375716c62343641bb8bf00027bc67adce44097553d20"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/pool.cpython-36.opt-2.pyc","mode":33188,"size":18972,"sha256":"4f62f3ae42b94f2afef10ebddc8d52732b573a505e77f01db4588f7067298505"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/pool.cpython-36.pyc","mode":33188,"size":20823,"sha256":"e799d8891a856e64da379818800b2ca2234630c6b224989e956c2f761c486e57"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_fork.cpython-36.opt-1.pyc","mode":33188,"size":2089,"sha256":"03dd04fd3ec688a39e2407f45014a0a3b069087e3628320b11368c50c33c2242"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_fork.cpython-36.opt-2.pyc","mode":33188,"size":2089,"sha256":"03dd04fd3ec688a39e2407f45014a0a3b069087e3628320b11368c50c33c2242"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_fork.cpython-36.pyc","mode":33188,"size":2132,"sha256":"dcbc2df3ab56c7845e44cf010ad12a7222e754c64de6633098b47442461b7a6f"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_forkserver.cpython-36.opt-1.pyc","mode":33188,"size":2328,"sha256":"dbfb0817f1e1e098e6467799785214a7dea1dbaa1f727289952658703d653b73"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_forkserver.cpython-36.opt-2.pyc","mode":33188,"size":2328,"sha256":"dbfb0817f1e1e098e6467799785214a7dea1dbaa1f727289952658703d653b73"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_forkserver.cpython-36.pyc","mode":33188,"size":2328,"sha256":"dbfb0817f1e1e098e6467799785214a7dea1dbaa1f727289952658703d653b73"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_spawn_posix.cpython-36.opt-1.pyc","mode":33188,"size":2108,"sha256":"eb6a1f12cf2598413a62f84933776681a4366d8dca8cec23b7619ff22eedce39"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_spawn_posix.cpython-36.opt-2.pyc","mode":33188,"size":2108,"sha256":"eb6a1f12cf2598413a62f84933776681a4366d8dca8cec23b7619ff22eedce39"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_spawn_posix.cpython-36.pyc","mode":33188,"size":2108,"sha256":"eb6a1f12cf2598413a62f84933776681a4366d8dca8cec23b7619ff22eedce39"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_spawn_win32.cpython-36.opt-1.pyc","mode":33188,"size":2723,"sha256":"498800f6404b3e508d6668d9624fe515587b35cc79f8543b0253df376bfaa6b0"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_spawn_win32.cpython-36.opt-2.pyc","mode":33188,"size":2642,"sha256":"439637586c608bf1f34a8525281d8ea33c8758aa8bcee073eeb297764f5d991e"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/popen_spawn_win32.cpython-36.pyc","mode":33188,"size":2760,"sha256":"15bb38644891d16eb0953a1b7a7b055a2ec2187c13ee62df5f7d26073581d4ca"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/process.cpython-36.opt-1.pyc","mode":33188,"size":7495,"sha256":"5498f43a5135092c239e3320f835e6670987ed4496c7be45236f19b01c15efc0"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/process.cpython-36.opt-2.pyc","mode":33188,"size":6445,"sha256":"134081022e78a96b88686d8d2dc7a91f3a1e859b8ffe2911bd03a00616f1df4c"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/process.cpython-36.pyc","mode":33188,"size":8141,"sha256":"ea34e23e862a1880fe8be1ee41fc88d6e39fb08300b1d6186ef6fa97f67a8d4d"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/queues.cpython-36.opt-1.pyc","mode":33188,"size":8866,"sha256":"5fa36bc17bc8f8df68627704e28c75b1388c44be1824eae5ffba26302f658936"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/queues.cpython-36.opt-2.pyc","mode":33188,"size":8866,"sha256":"5fa36bc17bc8f8df68627704e28c75b1388c44be1824eae5ffba26302f658936"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/queues.cpython-36.pyc","mode":33188,"size":8947,"sha256":"d00e51759e287ef02eb4806f5e4b544fb2eb92d77cbbc82d9de7760130b09fc2"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/reduction.cpython-36.opt-1.pyc","mode":33188,"size":7912,"sha256":"9b78bed443fbb390f6e348a975483ee704222771007e157fe5c14a2b30a1c409"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/reduction.cpython-36.opt-2.pyc","mode":33188,"size":7090,"sha256":"82ebb6ebf3af23d305ee16f08dd733a45d6bec71cd6d41b80e1d2ec212adb0bb"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/reduction.cpython-36.pyc","mode":33188,"size":7959,"sha256":"7e34621c1ec8698a6730092a2200ba8f19061f831ebf9695246a981b5891e5a6"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/resource_sharer.cpython-36.opt-1.pyc","mode":33188,"size":5124,"sha256":"1641bde52a7fe2fd68b37676bc845424e4ae2054fdb668546a31273e045b3436"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/resource_sharer.cpython-36.opt-2.pyc","mode":33188,"size":4696,"sha256":"3a8f607ba950e8aaa5571d0b0e3546cbe2426a1649e1175bbdd42f851010d966"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/resource_sharer.cpython-36.pyc","mode":33188,"size":5156,"sha256":"6d75bf23e75eb8c8bd31746b316ba918a0245347bb941adc0f6894799a5ea15a"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/semaphore_tracker.cpython-36.opt-1.pyc","mode":33188,"size":3637,"sha256":"748d205d41407b58d3747e2742448721bd7e8c50e55561dbea0c159a7e7ba9d8"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/semaphore_tracker.cpython-36.opt-2.pyc","mode":33188,"size":3331,"sha256":"bab912d37730b06eaa76eb4c4ec69a4b23548cacabdc5f79a170b83c0bb7623b"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/semaphore_tracker.cpython-36.pyc","mode":33188,"size":3669,"sha256":"8bcac789ca6cf94b613b56ebe61fc322c20eb2c5a3c43dbaaa2f0f05657323a5"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/sharedctypes.cpython-36.opt-1.pyc","mode":33188,"size":6809,"sha256":"28a23395b9a23493fe52db01237a415511af658642da7c3275be9a801786925d"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/sharedctypes.cpython-36.opt-2.pyc","mode":33188,"size":6568,"sha256":"b161a85e76ecf49d3d0773f4a6c55e37a2f959c46842f44bd0249342bddc36cc"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/sharedctypes.cpython-36.pyc","mode":33188,"size":6876,"sha256":"a4d949480c0ffad2ade64f2306faafd20801d4d86304e37881b00b00138bf4e8"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/spawn.cpython-36.opt-1.pyc","mode":33188,"size":6401,"sha256":"d674c1de322cbf27576aaa7da2ec90c4eb7fe498807fcb608e40854e2bc196c8"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/spawn.cpython-36.opt-2.pyc","mode":33188,"size":5922,"sha256":"de9afb53481044f092989556095336b6ecc90abff7083b52a6fd93413985f6a9"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/spawn.cpython-36.pyc","mode":33188,"size":6443,"sha256":"40ca5c388d4a82910fd0310288e5f2217835b0e867917e7d1dd85966d7f311b6"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/synchronize.cpython-36.opt-1.pyc","mode":33188,"size":11299,"sha256":"938ac58ad561190e98c0654cc2b45beb388edc4f29d5ba9b2a15f828e539376f"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/synchronize.cpython-36.opt-2.pyc","mode":33188,"size":11299,"sha256":"938ac58ad561190e98c0654cc2b45beb388edc4f29d5ba9b2a15f828e539376f"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/synchronize.cpython-36.pyc","mode":33188,"size":11568,"sha256":"4dabadc58b5ac77a6897172cf00675a21ba3e187d78f1175ff840779d9663a09"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/util.cpython-36.opt-1.pyc","mode":33188,"size":9688,"sha256":"85b87dd78614702f74fb75191dab1c6baacfaee49b96f434a00aeee873975aac"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/util.cpython-36.opt-2.pyc","mode":33188,"size":8986,"sha256":"0598af2434b1bfb59f8ef8ff050082c732ae4cabc5503de413e13432330ce461"},{"path":"/usr/lib64/python3.6/multiprocessing/__pycache__/util.cpython-36.pyc","mode":33188,"size":9800,"sha256":"0d8c4ca63fe59f3b1a47a2eaeb2ae19671b06957b91538f4e6a32f3d5cc7dbeb"},{"path":"/usr/lib64/python3.6/multiprocessing/connection.py","mode":33188,"size":31062,"sha256":"04959867937aac623a91251b1c09451dc721767855406339227633f335e08b3c"},{"path":"/usr/lib64/python3.6/multiprocessing/context.py","mode":33188,"size":10917,"sha256":"845d0ee951c86027442840e48ee50b8ef498d1cf98c887855ea1097b2680208a"},{"path":"/usr/lib64/python3.6/multiprocessing/dummy/__init__.py","mode":33188,"size":2896,"sha256":"496561081c3cdec38049e554207461c4c1efbf527b31117b901ef31da84e3c44"},{"path":"/usr/lib64/python3.6/multiprocessing/dummy/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3678,"sha256":"65b3f0d4931b00e251e7a281ba6207aae9b0bbb0a04e5d7364d5337d234c0008"},{"path":"/usr/lib64/python3.6/multiprocessing/dummy/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":3678,"sha256":"65b3f0d4931b00e251e7a281ba6207aae9b0bbb0a04e5d7364d5337d234c0008"},{"path":"/usr/lib64/python3.6/multiprocessing/dummy/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3717,"sha256":"24dc4f66fefb4c9a400d1e060ecd05859150b0d82970dc96be2c01efd2547941"},{"path":"/usr/lib64/python3.6/multiprocessing/dummy/__pycache__/connection.cpython-36.opt-1.pyc","mode":33188,"size":2497,"sha256":"ea0506679be1d4b4e57102a742444c183eed47559ba7c2771ea70a09d3c877f5"},{"path":"/usr/lib64/python3.6/multiprocessing/dummy/__pycache__/connection.cpython-36.opt-2.pyc","mode":33188,"size":2497,"sha256":"ea0506679be1d4b4e57102a742444c183eed47559ba7c2771ea70a09d3c877f5"},{"path":"/usr/lib64/python3.6/multiprocessing/dummy/__pycache__/connection.cpython-36.pyc","mode":33188,"size":2497,"sha256":"ea0506679be1d4b4e57102a742444c183eed47559ba7c2771ea70a09d3c877f5"},{"path":"/usr/lib64/python3.6/multiprocessing/dummy/connection.py","mode":33188,"size":1583,"sha256":"d3cd2a0365b543d8b6c90c9cb196cf61fb92a9385e5bb15d58db463f25b1c040"},{"path":"/usr/lib64/python3.6/multiprocessing/forkserver.py","mode":33188,"size":8694,"sha256":"3590ab6082a847749478e6e68fac253a8cee8c1d7e628409f0ca502c65456619"},{"path":"/usr/lib64/python3.6/multiprocessing/heap.py","mode":33188,"size":8319,"sha256":"c8d0ed58672d43473aa1f4c44ee29c2b659a3467d58dc7ed6dd67d48f3b626e7"},{"path":"/usr/lib64/python3.6/multiprocessing/managers.py","mode":33188,"size":38151,"sha256":"c6b4994beb9b938f88eab8bae25438c5d505cb055bd0f6506a6df8433bc689f2"},{"path":"/usr/lib64/python3.6/multiprocessing/pool.py","mode":33188,"size":26059,"sha256":"089cc9cb423dd5e96e787d81d6ac491f8e11e2834c4c52fb07406d4e36b4211a"},{"path":"/usr/lib64/python3.6/multiprocessing/popen_fork.py","mode":33188,"size":2307,"sha256":"2648444890a3218b1d14321c6eb3019e658a8c1de6213eb81015ca13fd2d051d"},{"path":"/usr/lib64/python3.6/multiprocessing/popen_forkserver.py","mode":33188,"size":1956,"sha256":"3664535e36e49301230e0706332c0daeeb1b623aff3816b62616228167311a93"},{"path":"/usr/lib64/python3.6/multiprocessing/popen_spawn_posix.py","mode":33188,"size":1904,"sha256":"8c4df5fffbb9aab88abeb6ed940e067d5170e4a59231411897eaf418c3a4eef1"},{"path":"/usr/lib64/python3.6/multiprocessing/popen_spawn_win32.py","mode":33188,"size":2999,"sha256":"55d88f7322c73cb72666e9b3f78ff084d640695980d0e912cf39c32eb034800b"},{"path":"/usr/lib64/python3.6/multiprocessing/process.py","mode":33188,"size":9211,"sha256":"bb573686aa2d44ba37564cf08c1efa503a7e2cce12635f1cea1cb042bb1cb938"},{"path":"/usr/lib64/python3.6/multiprocessing/queues.py","mode":33188,"size":10763,"sha256":"4689205112a5e15211586714c1873087a398030e86a89dfeb363ed994d22dd1c"},{"path":"/usr/lib64/python3.6/multiprocessing/reduction.py","mode":33188,"size":9226,"sha256":"3ba388bf75902434a751aee31eca205e4c2e34382629bad8c48c8e8db2e3d778"},{"path":"/usr/lib64/python3.6/multiprocessing/resource_sharer.py","mode":33188,"size":5325,"sha256":"a3047c9b77ba57ef0311654fb9ec80462adb89724019d54860c1cca9df6ad250"},{"path":"/usr/lib64/python3.6/multiprocessing/semaphore_tracker.py","mode":33188,"size":5394,"sha256":"b3b93d9a309dae8cea5278e4bef8fad4da7560c52564fd699ad8a04f8422b7be"},{"path":"/usr/lib64/python3.6/multiprocessing/sharedctypes.py","mode":33188,"size":6245,"sha256":"833a47b2d6a77bc30eb1f75dfd1dc369f9bd1e11bc5227878062528dbd7f6960"},{"path":"/usr/lib64/python3.6/multiprocessing/spawn.py","mode":33188,"size":8863,"sha256":"07bc15a35fbbed293d2b736a0aa374868b4be8ff23230786a83cb61e02b6f6c0"},{"path":"/usr/lib64/python3.6/multiprocessing/synchronize.py","mode":33188,"size":12050,"sha256":"a54562705f9d256596e2dae54920a0ae6ff9f8321d41d6e2289513dd10943d74"},{"path":"/usr/lib64/python3.6/multiprocessing/util.py","mode":33188,"size":11886,"sha256":"5101292432e85fc955cbee20e9ea33fe4b1f1733e2430e2d6e7dd677250bfb28"},{"path":"/usr/lib64/python3.6/netrc.py","mode":33188,"size":5684,"sha256":"24af911c24df43a80a950bb21d4fd6c670e9fd78eb785a69a47334da4ed96e8b"},{"path":"/usr/lib64/python3.6/nntplib.py","mode":33188,"size":43078,"sha256":"83b15cc37deb7ff636cd57ee1af2529a61c536728cba8116bc14d7dc8da8d306"},{"path":"/usr/lib64/python3.6/ntpath.py","mode":33188,"size":23094,"sha256":"efec6e1c06aa4d1452cba91c0a4634e8b32b00761252017f069b5d77940f242b"},{"path":"/usr/lib64/python3.6/nturl2path.py","mode":33188,"size":2444,"sha256":"11b7d0068e78b805e96f0a02d2312119b50a844c6f509ac14013c88f9420b9ae"},{"path":"/usr/lib64/python3.6/numbers.py","mode":33188,"size":10243,"sha256":"f74468478fa32714f0989c9c444e61dabac4b5d8aaff2dcf48795043175eb809"},{"path":"/usr/lib64/python3.6/opcode.py","mode":33188,"size":5822,"sha256":"f08dbb30b5257c7af22447e2dc54ce8b1ba388ea5410d1a551ed72a3a5df162b"},{"path":"/usr/lib64/python3.6/operator.py","mode":33188,"size":10863,"sha256":"6c85f65b08d82802967adbebf12036211293eaec7702449310a962c53e94ce05"},{"path":"/usr/lib64/python3.6/optparse.py","mode":33188,"size":60371,"sha256":"6e931f25b6830a749ddc8e83622d1f55a24a6966f130913e023aa5c89fdcb18d"},{"path":"/usr/lib64/python3.6/os.py","mode":33188,"size":37526,"sha256":"77b51eed2877707deeea1c3cfbe2429206144181cdec2ee68b2ddf9d28038475"},{"path":"/usr/lib64/python3.6/pathlib.py","mode":33188,"size":48982,"sha256":"989dad8b62d089d1820591ace00f5e7e351a9c73a70143509133aa59e2bc3d76"},{"path":"/usr/lib64/python3.6/pdb.py","mode":33261,"size":61320,"sha256":"b5396597e6c0e84ac5eb1faa147a2c121ec45f72fb100b7aea5c044f0a712744"},{"path":"/usr/lib64/python3.6/pickle.py","mode":33188,"size":55691,"sha256":"70805bc3d2a929ab0ee44ebb5b6f2266ba0c25659faf313445c335d3d3142d09"},{"path":"/usr/lib64/python3.6/pickletools.py","mode":33188,"size":91775,"sha256":"1aa5a1b952618ed0d1d49e569389a9a0185bb7ec5913e97e12ce0e3a3ea6f0f2"},{"path":"/usr/lib64/python3.6/pipes.py","mode":33188,"size":8916,"sha256":"b7979ff076f582ab9a6e92bf1aa283abcb2558ec87164f6f2615fe8772de9eda"},{"path":"/usr/lib64/python3.6/pkgutil.py","mode":33188,"size":21315,"sha256":"a8c4cf05981fd4ec719613918d3633d5598cc81f936a01f7895a954e8db7cc9f"},{"path":"/usr/lib64/python3.6/platform.py","mode":33261,"size":47201,"sha256":"200d323cba866e06fc0fba6552ea94b5d3c48ea5f2dde8b7e1bcee26a52d66fc"},{"path":"/usr/lib64/python3.6/plistlib.py","mode":33188,"size":31980,"sha256":"b80fc25ad0f4a34722510c94f2cdb1c3e238316d051499712766f3fc6e729b56"},{"path":"/usr/lib64/python3.6/poplib.py","mode":33188,"size":14964,"sha256":"6fee201bc5b62d161fc78c5fb7324c71603b72ce3c564181bb592ee5b65f20f2"},{"path":"/usr/lib64/python3.6/posixpath.py","mode":33188,"size":15772,"sha256":"881189f1679e8545ddfb54d5d24dff14de20ba30ae65067140821686f32f1bdc"},{"path":"/usr/lib64/python3.6/pprint.py","mode":33188,"size":20860,"sha256":"bebf6bde763f24f4ddc954e6f7e8f2751cc2ab524ad531573b1895b93b6f967e"},{"path":"/usr/lib64/python3.6/profile.py","mode":33261,"size":22029,"sha256":"9e76cb000dc94f7514699f93ef5c02a526223a4a10bdb91ea50621d943adb074"},{"path":"/usr/lib64/python3.6/pstats.py","mode":33188,"size":26564,"sha256":"827507dc44dd24e93270f01e27ba7f236ea27d22e9ab38a10b9198113dcbd480"},{"path":"/usr/lib64/python3.6/pty.py","mode":33188,"size":4763,"sha256":"34c91969a7b78894fd90eecb7ba20d3cf56cd9071741817b502b16fec08101af"},{"path":"/usr/lib64/python3.6/py_compile.py","mode":33188,"size":7181,"sha256":"819c8bc87bba30e447623d994d26c9f865e6cb64d3f744ffe27f22a699c3d443"},{"path":"/usr/lib64/python3.6/pyclbr.py","mode":33188,"size":13558,"sha256":"98724e0a5525660513e08d0df1a2e8fb63da728632cb82d77f4d9c55703dd69d"},{"path":"/usr/lib64/python3.6/pydoc.py","mode":33188,"size":104241,"sha256":"f3a6251ca25b56f8ff64c99c345c0ddae7a8be1f047ac515b253890edf12b833"},{"path":"/usr/lib64/python3.6/pydoc_data/__init__.py","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/lib64/python3.6/pydoc_data/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":126,"sha256":"d03e26605d80678849142707765d27be2d4d543b6f2b50934e6c26f3189daa5e"},{"path":"/usr/lib64/python3.6/pydoc_data/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":126,"sha256":"d03e26605d80678849142707765d27be2d4d543b6f2b50934e6c26f3189daa5e"},{"path":"/usr/lib64/python3.6/pydoc_data/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":126,"sha256":"d03e26605d80678849142707765d27be2d4d543b6f2b50934e6c26f3189daa5e"},{"path":"/usr/lib64/python3.6/pydoc_data/__pycache__/topics.cpython-36.opt-1.pyc","mode":33188,"size":400514,"sha256":"1fcb233219e7999114cc35cc155bf3f546b5cbcb2b784fc8f0b5eaf0f47c53b9"},{"path":"/usr/lib64/python3.6/pydoc_data/__pycache__/topics.cpython-36.opt-2.pyc","mode":33188,"size":400514,"sha256":"1fcb233219e7999114cc35cc155bf3f546b5cbcb2b784fc8f0b5eaf0f47c53b9"},{"path":"/usr/lib64/python3.6/pydoc_data/__pycache__/topics.cpython-36.pyc","mode":33188,"size":400514,"sha256":"1fcb233219e7999114cc35cc155bf3f546b5cbcb2b784fc8f0b5eaf0f47c53b9"},{"path":"/usr/lib64/python3.6/pydoc_data/_pydoc.css","mode":33188,"size":96,"sha256":"7b8cc50cbc204745d38fa3d57b3bd6bb4c3f6ea0d346bef61b3cc423eb15b9d1"},{"path":"/usr/lib64/python3.6/pydoc_data/topics.py","mode":33188,"size":643245,"sha256":"e13ff9d6c72af03e2b7447f66072462289f09c84e864e366fc06812410b0d184"},{"path":"/usr/lib64/python3.6/queue.py","mode":33188,"size":8780,"sha256":"972bf9c668af383b3e629f50875c5a046788816debeab4fd03dd6feb72af0980"},{"path":"/usr/lib64/python3.6/quopri.py","mode":33261,"size":7262,"sha256":"95fc173c5e2df9c3a84b09ebd4dd12baf7726d5f2e3ee0f4f0a0df3e94cbe21a"},{"path":"/usr/lib64/python3.6/random.py","mode":33188,"size":27442,"sha256":"e0b7626813f4ee9c2d85d81d0559ef3a592a0b9869821686ba59606a265a0d1e"},{"path":"/usr/lib64/python3.6/re.py","mode":33188,"size":15552,"sha256":"a25c7e1d517bd22c5647267db5ddc926c56bee63f6e451ed6566dc3538b1d34e"},{"path":"/usr/lib64/python3.6/reprlib.py","mode":33188,"size":5336,"sha256":"a847af1248ddd62ded492a9e06f84260e9cf51c12f78241203542d11abb0484d"},{"path":"/usr/lib64/python3.6/rlcompleter.py","mode":33188,"size":7097,"sha256":"926dbbfdb452592f7a565e20f3d742ce54e89a7cefd0feb6b28a93d091c4a6ac"},{"path":"/usr/lib64/python3.6/runpy.py","mode":33188,"size":11959,"sha256":"ebdf2d98baa73b6ff93935f3f620a3adc36b5c6768e858a91cab94561ea948da"},{"path":"/usr/lib64/python3.6/sched.py","mode":33188,"size":6511,"sha256":"50be204ee818c76012da66de4446c343729f6ccda40c31da8128a4c90578d8b2"},{"path":"/usr/lib64/python3.6/secrets.py","mode":33188,"size":2038,"sha256":"8fe91980080cc3f3d687bfa4078489ebe25fb28005170a8232a3eee75f94d3b4"},{"path":"/usr/lib64/python3.6/selectors.py","mode":33188,"size":19438,"sha256":"2f865269d11d324139e5a9b6eb5a82c1f4ad061ebd6695d4289a179fc1aa3c95"},{"path":"/usr/lib64/python3.6/shelve.py","mode":33188,"size":8515,"sha256":"8d2b7f01ca03c7224350b7f75759d0ed5e9ce8a9b5b6166766e233baaddebbd9"},{"path":"/usr/lib64/python3.6/shlex.py","mode":33188,"size":12956,"sha256":"25149f6da956e635f62f70d7b03a675de6f92e177b349ccd61b8a73bea3a9f31"},{"path":"/usr/lib64/python3.6/shutil.py","mode":33188,"size":40540,"sha256":"71b558e841809470480a3b57a59eb7efa30d58fd46aa45a3b97093c0744d57a4"},{"path":"/usr/lib64/python3.6/signal.py","mode":33188,"size":2123,"sha256":"7c73fc7d2600ccce041d38cbf4d8270851902c33c17eff26c5a6c6a7572c8184"},{"path":"/usr/lib64/python3.6/site-packages/README.txt","mode":33188,"size":119,"sha256":"cba8fece8f62c36306ba27a128f124a257710e41fc619301ee97be93586917cb"},{"path":"/usr/lib64/python3.6/site.py","mode":33188,"size":21268,"sha256":"9caf782ea7ef6261303c3eae8c96ef150396681079fadf7fe5ddf09c9fb61c4a"},{"path":"/usr/lib64/python3.6/smtpd.py","mode":33261,"size":34719,"sha256":"ee78a1f7e0ddf8ccf3ab9d7fe2bb6164aa193d22325ffcf313735e2e3d491324"},{"path":"/usr/lib64/python3.6/smtplib.py","mode":33261,"size":44218,"sha256":"750c43e56637d2b4fadf1cf62ae02a0c74d3fc5950440a0d4b634670f8e8a9a6"},{"path":"/usr/lib64/python3.6/sndhdr.py","mode":33188,"size":7088,"sha256":"16d32bd6d57c61ea12b4c5d059cfac9ec2ce86881439de659327e08429be9ac9"},{"path":"/usr/lib64/python3.6/socket.py","mode":33188,"size":27443,"sha256":"fb568788301152e14ba235dfe574158cbdf78a915a965e9152b117599d0eace4"},{"path":"/usr/lib64/python3.6/socketserver.py","mode":33188,"size":27010,"sha256":"81dba4a142e3bb4886b9eecb4248d7c07a7ae1da6b811f532cc3efa35e350873"},{"path":"/usr/lib64/python3.6/sqlite3/__init__.py","mode":33188,"size":1018,"sha256":"ff6ad4f2c78105413cbcf0aa30a26ad77b463f59c69d9743bfb62322118bdbe2"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":154,"sha256":"86612d5ce991fe3bc546d076257f1ca742e0b7192c2dd2c781cbab7794894cd5"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":154,"sha256":"86612d5ce991fe3bc546d076257f1ca742e0b7192c2dd2c781cbab7794894cd5"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":154,"sha256":"86612d5ce991fe3bc546d076257f1ca742e0b7192c2dd2c781cbab7794894cd5"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/dbapi2.cpython-36.opt-1.pyc","mode":33188,"size":2473,"sha256":"7dca493e185778e10e21cf1c4d150625c170d9852271fce20d1a341b6e28ecb2"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/dbapi2.cpython-36.opt-2.pyc","mode":33188,"size":2473,"sha256":"7dca493e185778e10e21cf1c4d150625c170d9852271fce20d1a341b6e28ecb2"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/dbapi2.cpython-36.pyc","mode":33188,"size":2473,"sha256":"7dca493e185778e10e21cf1c4d150625c170d9852271fce20d1a341b6e28ecb2"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/dump.cpython-36.opt-1.pyc","mode":33188,"size":1916,"sha256":"61bd27d4697278a6b1740d4d894aa22fcee5627dc20a1a7d5ce8431a037609a0"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/dump.cpython-36.opt-2.pyc","mode":33188,"size":1608,"sha256":"743b9419b07182641d81bd8d60a05667ff168b4f3349a0d54558525a1abcf47f"},{"path":"/usr/lib64/python3.6/sqlite3/__pycache__/dump.cpython-36.pyc","mode":33188,"size":1916,"sha256":"61bd27d4697278a6b1740d4d894aa22fcee5627dc20a1a7d5ce8431a037609a0"},{"path":"/usr/lib64/python3.6/sqlite3/dbapi2.py","mode":33188,"size":2687,"sha256":"2031e765b130d7f8a0a1984d0e09576fa9decd4009507df539bb683037ab4dd3"},{"path":"/usr/lib64/python3.6/sqlite3/dump.py","mode":33188,"size":2825,"sha256":"b7d3eb1d97e98f2fd1420dca8f739996ca8380e7e15c732841c6f01ad4d9cfac"},{"path":"/usr/lib64/python3.6/sre_compile.py","mode":33188,"size":19338,"sha256":"c537c442b5b783363b7f419c738dc1fdc242aac755d68ffc09900ac5ac87bb9c"},{"path":"/usr/lib64/python3.6/sre_constants.py","mode":33188,"size":6821,"sha256":"0998cd712b13030830ae00225216d89a163e7e52e84643db8ba532cf8f03b8f1"},{"path":"/usr/lib64/python3.6/sre_parse.py","mode":33188,"size":36536,"sha256":"a10d43996f5dec74c9fd3b62e5af37273875b3b33dc3210133fa789f75ca0dd7"},{"path":"/usr/lib64/python3.6/ssl.py","mode":33188,"size":42702,"sha256":"a1bfc7027ceb8c0b907ce10c28d5e2a0445799c2efc6403bfc5509014e3f816e"},{"path":"/usr/lib64/python3.6/stat.py","mode":33188,"size":5038,"sha256":"35d94a130d4a934af1eea02a58e9701135ce8861893ac3100f038d9398079229"},{"path":"/usr/lib64/python3.6/statistics.py","mode":33188,"size":20673,"sha256":"a934cc890a2e46de391dfb9fca67f2c2fc6070fa01feb4418e2a2466d2832a26"},{"path":"/usr/lib64/python3.6/string.py","mode":33188,"size":11795,"sha256":"ce0c4471de168b423bffdea0d165fbe7af7713f46439173ec2534dc25b49d705"},{"path":"/usr/lib64/python3.6/stringprep.py","mode":33188,"size":12917,"sha256":"60b6c83581093029312efb6670b11c540090b3f78bcf72264467b494f02f21a5"},{"path":"/usr/lib64/python3.6/struct.py","mode":33188,"size":257,"sha256":"9c231f9497caf513a22dee8f790b07f969b0e45854a0bdd6dd84b492e08c2856"},{"path":"/usr/lib64/python3.6/subprocess.py","mode":33188,"size":62339,"sha256":"abc723d33542cc5f9ff16324e3bcb426099e5e42046cce4e7c6f566a4cb15013"},{"path":"/usr/lib64/python3.6/sunau.py","mode":33188,"size":18095,"sha256":"4bb9039f460236e927706d939d87935c982415c8e6e8b366df4ca68ebf6b7001"},{"path":"/usr/lib64/python3.6/symbol.py","mode":33261,"size":2119,"sha256":"15be81c8fd6577b98435a2c33df877faaa710b08621fa85d1cb485b164fd4d3e"},{"path":"/usr/lib64/python3.6/symtable.py","mode":33188,"size":7277,"sha256":"4f93b4e79be759e22178ccd491e0a5f0930a069eda0377dc90cd476039ae68dc"},{"path":"/usr/lib64/python3.6/sysconfig.py","mode":33188,"size":24984,"sha256":"4fdeabb621f31cb36372737b15f08701123780ddccdf762a7d1e1bf902fb1482"},{"path":"/usr/lib64/python3.6/tabnanny.py","mode":33261,"size":11411,"sha256":"8fabeb840a00e0409ef6ec328ce8f5e0703ec6822e0360522938ec96263f80b0"},{"path":"/usr/lib64/python3.6/tarfile.py","mode":33261,"size":93226,"sha256":"6a4b96effbc2809669b2bbc42f849c93f39c90c98e29592ebfe2d6298828f275"},{"path":"/usr/lib64/python3.6/telnetlib.py","mode":33188,"size":23136,"sha256":"adedeb2b103fec6f5ecaec90d8ee8f8312a83b2e405ac3949b57774e2d74a17f"},{"path":"/usr/lib64/python3.6/tempfile.py","mode":33188,"size":26776,"sha256":"8e5c45f5b45c270a7efc02a4765fe2c090267720cb8b5175a7eaf59e684bc32a"},{"path":"/usr/lib64/python3.6/test/__init__.py","mode":33188,"size":47,"sha256":"836cdb388117cf81e78d9fa2a141cca1b14b0179733322e710067749a1b16fe9"},{"path":"/usr/lib64/python3.6/test/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":120,"sha256":"eafa9ed8b48cd42c9bf18345a6eca909f663dde3db1d5bae44c0bc4847235442"},{"path":"/usr/lib64/python3.6/test/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":120,"sha256":"eafa9ed8b48cd42c9bf18345a6eca909f663dde3db1d5bae44c0bc4847235442"},{"path":"/usr/lib64/python3.6/test/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":120,"sha256":"eafa9ed8b48cd42c9bf18345a6eca909f663dde3db1d5bae44c0bc4847235442"},{"path":"/usr/lib64/python3.6/test/support/__init__.py","mode":33188,"size":101904,"sha256":"a4cbeff96d6823179cfa7c6a3ccf882c92f6dec985cc10e64f073ee15e7027aa"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":80117,"sha256":"5d8634992190763efe2043866ce5e4adf0a9a14fa50e60662f33ec23ece517a6"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":56884,"sha256":"c6145eefcc58e769c1b4d0e3cc66c836fd8898ac506e5b0c8470ef2ee6484fd2"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":80267,"sha256":"ebdb108d88d3d3931a967d9169ba087c32c1f810820858f858a5e0a1e40964c6"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/script_helper.cpython-36.opt-1.pyc","mode":33188,"size":7106,"sha256":"115c9ddc18ab0c392562ef6beb9450f38a70e025f08fa0c2a1bb642687b153ea"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/script_helper.cpython-36.opt-2.pyc","mode":33188,"size":5366,"sha256":"5728ab0f53e7ccbb277d84f0bd91fbfacb94f46c6a8ece62c081414bdeec9ba9"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/script_helper.cpython-36.pyc","mode":33188,"size":7106,"sha256":"115c9ddc18ab0c392562ef6beb9450f38a70e025f08fa0c2a1bb642687b153ea"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/testresult.cpython-36.opt-1.pyc","mode":33188,"size":7768,"sha256":"5f4819e9fba1425c9586db28f923a1fbb85c3bf5b3d8c0ee49565693dcba3f01"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/testresult.cpython-36.opt-2.pyc","mode":33188,"size":7690,"sha256":"ec930f5c3cd0178a71adaddea5ca361795b1fb4b71ae900d8d3ac5c431e8b22e"},{"path":"/usr/lib64/python3.6/test/support/__pycache__/testresult.cpython-36.pyc","mode":33188,"size":7768,"sha256":"5f4819e9fba1425c9586db28f923a1fbb85c3bf5b3d8c0ee49565693dcba3f01"},{"path":"/usr/lib64/python3.6/test/support/script_helper.py","mode":33188,"size":10632,"sha256":"a9f6495bf7fb9f98153a772e59c4b555dbc252d32e102da3a5761ab72d1a9d27"},{"path":"/usr/lib64/python3.6/test/support/testresult.py","mode":33188,"size":6669,"sha256":"8787c1865a19c49d50c4697b8835ce2f20b18888adf6a6c70e4ea1b09acb8559"},{"path":"/usr/lib64/python3.6/textwrap.py","mode":33188,"size":19558,"sha256":"f2ded3ee940aff5ce1cfd0f118c013189956bea62473c6d7bdd91b2feaa6b0cf"},{"path":"/usr/lib64/python3.6/this.py","mode":33188,"size":1003,"sha256":"481d0cb3de511eae0b5713dad18542b07eafd9c013bb7690f7497bad49923a71"},{"path":"/usr/lib64/python3.6/threading.py","mode":33188,"size":49029,"sha256":"e1c66e4ae337652cfb29e2c5bd5a326aef537027798d9bb2962e4bbb4e0662e6"},{"path":"/usr/lib64/python3.6/timeit.py","mode":33261,"size":13342,"sha256":"402eaf410e2e163481421d3d9038873585d566b3393bbc12f05aa494391c4135"},{"path":"/usr/lib64/python3.6/token.py","mode":33188,"size":3075,"sha256":"6f283040bef2cc182636e6a0259fb13615ec932bca70b98fa5b45e92df3f1d61"},{"path":"/usr/lib64/python3.6/tokenize.py","mode":33188,"size":29496,"sha256":"122daec65b9c6f24892e474387275c796fd4aa6435051e0b37af80c6c2bcdf14"},{"path":"/usr/lib64/python3.6/trace.py","mode":33261,"size":28733,"sha256":"4de9613e939803e2cedf0565abdb7df5cfb2067804d9df8e89dacbc3cb52f989"},{"path":"/usr/lib64/python3.6/traceback.py","mode":33188,"size":23458,"sha256":"cb5db58698b94b5b2318f6e1af94b6b60c6ec3513cbca1f7a049abb60fefed29"},{"path":"/usr/lib64/python3.6/tracemalloc.py","mode":33188,"size":16658,"sha256":"61a4393f04e42d0316f5b73c496c2c80c0d944377f44ec4d5568e8cf83e5f046"},{"path":"/usr/lib64/python3.6/tty.py","mode":33188,"size":879,"sha256":"066a541e6d38ead952d63cc32afbac51a33acf354799f235c582eab17488105d"},{"path":"/usr/lib64/python3.6/types.py","mode":33188,"size":8870,"sha256":"e2e3cb3caa5b8ec4824b16fc3a4ed4214dc9d2df78ee4306bb939da39c160713"},{"path":"/usr/lib64/python3.6/typing.py","mode":33188,"size":80274,"sha256":"f11374e25fd60b1a8241c6c120a2c51e9126e121862d6b988d3f452cae18969e"},{"path":"/usr/lib64/python3.6/unittest/__init__.py","mode":33188,"size":3179,"sha256":"2bd445ff32866db768a152db0c0513a5d55a15246907452c8d8fd90d76874101"},{"path":"/usr/lib64/python3.6/unittest/__main__.py","mode":33188,"size":485,"sha256":"7d88c310b2df1b04fdf019d72141ee90c6e55be02125f7c90ee2aa0373bf832c"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3017,"sha256":"8198ae17d6cc7825f9b90e269a6e005bd4b227a364245faca1b898add94869a7"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":1256,"sha256":"b46bcaecf85fa1e24986dd6018b7cccf5f85142bac06748acdc1f9ea09f07207"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3017,"sha256":"8198ae17d6cc7825f9b90e269a6e005bd4b227a364245faca1b898add94869a7"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/__main__.cpython-36.opt-1.pyc","mode":33188,"size":415,"sha256":"d1574ade7f3ee8ef4b56a1d165474a0c2abb14848b108ed179d8aaa1b3d29502"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/__main__.cpython-36.opt-2.pyc","mode":33188,"size":382,"sha256":"ab3b49d5d7430b287fa1249f768239a79c25e95cb9cc453e228e6efca66eff25"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/__main__.cpython-36.pyc","mode":33188,"size":415,"sha256":"d1574ade7f3ee8ef4b56a1d165474a0c2abb14848b108ed179d8aaa1b3d29502"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/case.cpython-36.opt-1.pyc","mode":33188,"size":48068,"sha256":"f38588a6ff34cb4b93b24300a1503228b073fa027263651c5bf859c457ffc20c"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/case.cpython-36.opt-2.pyc","mode":33188,"size":32924,"sha256":"142b1d2905c069723bfa53229eab8196613bd682145fa531e4a163f09357f382"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/case.cpython-36.pyc","mode":33188,"size":48122,"sha256":"373aa2560d3e45f81171840f0d5fd714383a0d10e530586456098c98c7d5c49d"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/loader.cpython-36.opt-1.pyc","mode":33188,"size":13757,"sha256":"ab1958a038cefcf9ff7c2dccb311b50cfc456cdfecb2faec23bc65e1d95d035c"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/loader.cpython-36.opt-2.pyc","mode":33188,"size":11075,"sha256":"eb3286262392ec890d6d0a8bdfe7285b80ebc91823c3ff9127095c31fa5ed51c"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/loader.cpython-36.pyc","mode":33188,"size":13868,"sha256":"24595e790e69e2748beafe6fba69370ac0df4eb171e27449b8b6dabd6d5f0c81"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/main.cpython-36.opt-1.pyc","mode":33188,"size":7014,"sha256":"07f85e4d4c19a4bb24b6ec06bf215cc91f20b97a08b20f6e22367ebeb64c90ac"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/main.cpython-36.opt-2.pyc","mode":33188,"size":6836,"sha256":"c3572022b11a4e22a93aa27eabf30907e3e6a494627af36a0c8325aff74d8089"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/main.cpython-36.pyc","mode":33188,"size":7014,"sha256":"07f85e4d4c19a4bb24b6ec06bf215cc91f20b97a08b20f6e22367ebeb64c90ac"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/mock.cpython-36.opt-1.pyc","mode":33188,"size":61788,"sha256":"58ed871b7802af76679b7c16fcd0cbb8c84717e8cfd6ae1101a80990559590bc"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/mock.cpython-36.opt-2.pyc","mode":33188,"size":46180,"sha256":"d4a52a0c4278dbc80ba43ae8841c835cf98ef58cf0962468cb0ec6a88d82595b"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/mock.cpython-36.pyc","mode":33188,"size":61788,"sha256":"58ed871b7802af76679b7c16fcd0cbb8c84717e8cfd6ae1101a80990559590bc"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/result.cpython-36.opt-1.pyc","mode":33188,"size":7228,"sha256":"ce4f96ba4074bfa3f2030414d3399164d7a5fac288b44c405d3352389094570b"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/result.cpython-36.opt-2.pyc","mode":33188,"size":5630,"sha256":"0f1275d7c14641d719b9d08ee29fe0d18b738ec59a507e627dbcb813a0b60996"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/result.cpython-36.pyc","mode":33188,"size":7228,"sha256":"ce4f96ba4074bfa3f2030414d3399164d7a5fac288b44c405d3352389094570b"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/runner.cpython-36.opt-1.pyc","mode":33188,"size":6858,"sha256":"d18076b7087a488065c2e9d9ace58150dc909b1187185eae4600b6ccbcc39881"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/runner.cpython-36.opt-2.pyc","mode":33188,"size":6241,"sha256":"c42cc62d12a0fc8f9845154f941f080cbc562000f38242a6bc81a722f10c3d0f"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/runner.cpython-36.pyc","mode":33188,"size":6858,"sha256":"d18076b7087a488065c2e9d9ace58150dc909b1187185eae4600b6ccbcc39881"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/signals.cpython-36.opt-1.pyc","mode":33188,"size":2174,"sha256":"2b9c8dcdde7b9d55f99d77afc08559e89bc8cc88736f6e5af1a3744404ff37d6"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/signals.cpython-36.opt-2.pyc","mode":33188,"size":2174,"sha256":"2b9c8dcdde7b9d55f99d77afc08559e89bc8cc88736f6e5af1a3744404ff37d6"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/signals.cpython-36.pyc","mode":33188,"size":2174,"sha256":"2b9c8dcdde7b9d55f99d77afc08559e89bc8cc88736f6e5af1a3744404ff37d6"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/suite.cpython-36.opt-1.pyc","mode":33188,"size":9173,"sha256":"4c24c5ca6b015128c4b82b944ba57ad3164083c1da97f95863b0a16ae10b7d37"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/suite.cpython-36.opt-2.pyc","mode":33188,"size":8103,"sha256":"7b53b21e7d3dbcbb89ed0f11ca2e3692a93843cdcc89b9fe3bc52dacdf49fbfb"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/suite.cpython-36.pyc","mode":33188,"size":9173,"sha256":"4c24c5ca6b015128c4b82b944ba57ad3164083c1da97f95863b0a16ae10b7d37"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/util.cpython-36.opt-1.pyc","mode":33188,"size":4688,"sha256":"7a321ff3afebbf24e880b172cfbf968007d2ab4ae6de91085ebe85317c9a4def"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/util.cpython-36.opt-2.pyc","mode":33188,"size":3838,"sha256":"ef0348546f1cde1c301652fec549e4d9fcb4d864adf75eb95e68e631ad0d0384"},{"path":"/usr/lib64/python3.6/unittest/__pycache__/util.cpython-36.pyc","mode":33188,"size":4755,"sha256":"db9ce385137191d1b100b8da2b877579ddfee3ee72738c53998999a816384193"},{"path":"/usr/lib64/python3.6/unittest/case.py","mode":33188,"size":57500,"sha256":"3192ae87370f2e976f095a8504a8493a8209d4f23cfa7f10e4f3289891c656e3"},{"path":"/usr/lib64/python3.6/unittest/loader.py","mode":33188,"size":22224,"sha256":"03a9798485b6c06cedf5288cb28e20a9299cf797c09491c3f5d9357eab529a1a"},{"path":"/usr/lib64/python3.6/unittest/main.py","mode":33188,"size":10552,"sha256":"61ec1bfafe52e1d65b4a8a0d953d5b4e0a27c2a15b8da878c703d9d400281b51"},{"path":"/usr/lib64/python3.6/unittest/mock.py","mode":33188,"size":79856,"sha256":"39e5f79a3d249e125ac1d17f3b12eee27fae15474ae424778691864a59d6f7c7"},{"path":"/usr/lib64/python3.6/unittest/result.py","mode":33188,"size":7442,"sha256":"d25e3fbf3a071559efe65854e1e5aaef995041d340b1d5c0b9a5ef17e7ee6de3"},{"path":"/usr/lib64/python3.6/unittest/runner.py","mode":33188,"size":7751,"sha256":"c781b7735f2f17038ce6296ef31ed832c4301f24d7a319182df26d6293571787"},{"path":"/usr/lib64/python3.6/unittest/signals.py","mode":33188,"size":2403,"sha256":"f8286e818ca56e10e03745bc056cdfd31147678f9a1dc8cb6b0fe96ef9a4362a"},{"path":"/usr/lib64/python3.6/unittest/suite.py","mode":33188,"size":10479,"sha256":"cf7cca2dede53db7dc7574cd8efda2264f240b3747c5ae28dd11bee73976f5af"},{"path":"/usr/lib64/python3.6/unittest/util.py","mode":33188,"size":5433,"sha256":"0c96189e3239153f8579b3bbb83768d54394a4e33c6fe39ea7612aaab8c59df0"},{"path":"/usr/lib64/python3.6/urllib/__init__.py","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":122,"sha256":"de83d4c231da5d6c11372faa00af9560824cd413986c675d1042af5c6383f748"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":122,"sha256":"de83d4c231da5d6c11372faa00af9560824cd413986c675d1042af5c6383f748"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":122,"sha256":"de83d4c231da5d6c11372faa00af9560824cd413986c675d1042af5c6383f748"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/error.cpython-36.opt-1.pyc","mode":33188,"size":2756,"sha256":"516eced6996c08d84d730d9a5151f109e34b83e833f99471d806fd3a9cb8eaa1"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/error.cpython-36.opt-2.pyc","mode":33188,"size":2081,"sha256":"ab25c16a578249e0fb25300cb770b7b9aa2f5aa82a7cd4c96455d6e550b6d152"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/error.cpython-36.pyc","mode":33188,"size":2756,"sha256":"516eced6996c08d84d730d9a5151f109e34b83e833f99471d806fd3a9cb8eaa1"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/parse.cpython-36.opt-1.pyc","mode":33188,"size":30492,"sha256":"3b5ac46622fd19e3ec0da88f2624456b957e9b606c1fe61b5f9344b480889a57"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/parse.cpython-36.opt-2.pyc","mode":33188,"size":21638,"sha256":"bd1bc7b33e48a833173779fabfae35a29a6774eed010a4d7a59a1a83c978ebc9"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/parse.cpython-36.pyc","mode":33188,"size":30492,"sha256":"3b5ac46622fd19e3ec0da88f2624456b957e9b606c1fe61b5f9344b480889a57"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/request.cpython-36.opt-1.pyc","mode":33188,"size":72498,"sha256":"03bc6fbc23bfafabb277ece8fea9640c3676a60d99ef46815a4b2df7f467aa60"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/request.cpython-36.opt-2.pyc","mode":33188,"size":60138,"sha256":"2d0dd9c6602baa83efee944e3f9d7399b3887a256d2730c6005905b4af5816b6"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/request.cpython-36.pyc","mode":33188,"size":72634,"sha256":"cab887eecff97d7447d9354ddbd5c1e2f7b1ba481889aa02ccf2a291cce15403"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/response.cpython-36.opt-1.pyc","mode":33188,"size":3229,"sha256":"cb1145429da42aa7b513c3a7601b2b582ed5ee3a3998bba010eaccf9da40a8f9"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/response.cpython-36.opt-2.pyc","mode":33188,"size":2650,"sha256":"728eb1cfffa96779b9e2ac9929266e46daf34c1b6bc2d677d6f2fcc6e6846a8b"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/response.cpython-36.pyc","mode":33188,"size":3229,"sha256":"cb1145429da42aa7b513c3a7601b2b582ed5ee3a3998bba010eaccf9da40a8f9"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/robotparser.cpython-36.opt-1.pyc","mode":33188,"size":7053,"sha256":"23d54e1cd1b1ff4d1579e2095e5a996958c60b7cf823e7df171aac20c26ef981"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/robotparser.cpython-36.opt-2.pyc","mode":33188,"size":5683,"sha256":"fe94a7377015c4e067162cf2789a828bb50f41ca179051a854fb085d3b198948"},{"path":"/usr/lib64/python3.6/urllib/__pycache__/robotparser.cpython-36.pyc","mode":33188,"size":7053,"sha256":"23d54e1cd1b1ff4d1579e2095e5a996958c60b7cf823e7df171aac20c26ef981"},{"path":"/usr/lib64/python3.6/urllib/error.py","mode":33188,"size":2641,"sha256":"69c065aebb481100575336a563b04abe527de9af3e2e0fe25eb69d644dc0e174"},{"path":"/usr/lib64/python3.6/urllib/parse.py","mode":33188,"size":38327,"sha256":"a10ec218d6ed862b985b9229ec3ec0bcb5848c61659fb3ea3c886f6bd9bb66b3"},{"path":"/usr/lib64/python3.6/urllib/request.py","mode":33188,"size":100028,"sha256":"c5a26678cce7cd741f74d5474c866bd1a5e28abe0a3c250545a959239ea5d70f"},{"path":"/usr/lib64/python3.6/urllib/response.py","mode":33188,"size":2299,"sha256":"89abe5ccaa188488e364c23277a2da627e07e1d5b834e403231dea455532a0fa"},{"path":"/usr/lib64/python3.6/urllib/robotparser.py","mode":33188,"size":8832,"sha256":"f0b44201220e7f3666c0f24078a0895af633a3dd4e1390459315f3526c452ad4"},{"path":"/usr/lib64/python3.6/uu.py","mode":33261,"size":6763,"sha256":"ec08b6687c57801b2b44e1d5067b2f61e945b993ffbfe7d2426d7507474c7fca"},{"path":"/usr/lib64/python3.6/uuid.py","mode":33188,"size":24020,"sha256":"4048e8a537760d97507f0b0c73ed0cb9ca3ac145641d6b77a9243529e7ef39e0"},{"path":"/usr/lib64/python3.6/venv/__init__.py","mode":33188,"size":18651,"sha256":"91a55c5d8ba5ebeda484c9d84e84cb6055424f2f20f9a70fa9faf394072d9806"},{"path":"/usr/lib64/python3.6/venv/__main__.py","mode":33188,"size":145,"sha256":"722537c68c0622f8293d39bb6ab1288f3637d8dc45d6f9aae96e49af8145ca36"},{"path":"/usr/lib64/python3.6/venv/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":13587,"sha256":"d5c84b55ee007d38fd0f6f168a1eb1abe017bbe352e94ee8f8f299bf676c14a3"},{"path":"/usr/lib64/python3.6/venv/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":9459,"sha256":"e69087581539090088e626babb3dac32333c8d33bb654dbe2f7b5ce3a121c0b0"},{"path":"/usr/lib64/python3.6/venv/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":13638,"sha256":"c5cbc3876d4bfb2f5d4eda50de6d697c36670d6492885a97bbc3735683a17e90"},{"path":"/usr/lib64/python3.6/venv/__pycache__/__main__.cpython-36.opt-1.pyc","mode":33188,"size":323,"sha256":"f728347868268f9e5d2e7a568d01a14414798e8dc1da6d312474679b4fd857f5"},{"path":"/usr/lib64/python3.6/venv/__pycache__/__main__.cpython-36.opt-2.pyc","mode":33188,"size":323,"sha256":"f728347868268f9e5d2e7a568d01a14414798e8dc1da6d312474679b4fd857f5"},{"path":"/usr/lib64/python3.6/venv/__pycache__/__main__.cpython-36.pyc","mode":33188,"size":323,"sha256":"f728347868268f9e5d2e7a568d01a14414798e8dc1da6d312474679b4fd857f5"},{"path":"/usr/lib64/python3.6/venv/scripts/common/activate","mode":33188,"size":2218,"sha256":"0f177f8ea78b77da9ada2f125a556a3534a20e54991494a28087f42a89bb9255"},{"path":"/usr/lib64/python3.6/venv/scripts/posix/activate.csh","mode":33188,"size":1276,"sha256":"b55967bf75ecfc6d4d266ba232a54e8b7d7af6eb9c17fa0b7c6d8034f76158cc"},{"path":"/usr/lib64/python3.6/venv/scripts/posix/activate.fish","mode":33188,"size":2438,"sha256":"c31f52e8210e0425102745bbe03854e1a4e6d4866f034f20a71da9685bcb8e69"},{"path":"/usr/lib64/python3.6/warnings.py","mode":33188,"size":18488,"sha256":"2b4617ddc9ac5ceb68394401e719fa643809960188b7f23db0a1d28f0d176f06"},{"path":"/usr/lib64/python3.6/wave.py","mode":33188,"size":17709,"sha256":"a3a6eddfc3a231e52c18f578ea0413fa6bfa6cfc6d0222767905f8b3ee06fe33"},{"path":"/usr/lib64/python3.6/weakref.py","mode":33188,"size":20466,"sha256":"7637407c64a643ac7812c32bf5dfd098672117747903bd739add37282d3de95f"},{"path":"/usr/lib64/python3.6/webbrowser.py","mode":33261,"size":21767,"sha256":"32a3ec046a65ccc3ddd92f028e10117ceba29d9f95799a15cac9a189d20f757f"},{"path":"/usr/lib64/python3.6/wsgiref/__init__.py","mode":33188,"size":587,"sha256":"db2259a74988dc73a209cdf7aaa3b79ab6f213384287a8bd288ad141a935e236"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":718,"sha256":"4f1044ec31a5422c45eac567306b09bea36f2f537655c43a0333121d229a8e31"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":125,"sha256":"72f2e3e4c729b503d554248de8457d94ebc701c4ce7d5423786809c3ac136804"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":718,"sha256":"4f1044ec31a5422c45eac567306b09bea36f2f537655c43a0333121d229a8e31"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/handlers.cpython-36.opt-1.pyc","mode":33188,"size":15708,"sha256":"0cf969835aebee8f0926dda560a934f46a61a06a5f4f0a4110170c94d28597c0"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/handlers.cpython-36.opt-2.pyc","mode":33188,"size":10274,"sha256":"b458dbe4be16e33664ea5ef7a23881ebe04cf85746dd2cb921814115ecd1ed1c"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/handlers.cpython-36.pyc","mode":33188,"size":16150,"sha256":"a5ec4649cc4db9fc9d1390c3a08760b3027a35ca03c322df1e0861b89f39fefd"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/headers.cpython-36.opt-1.pyc","mode":33188,"size":7682,"sha256":"750f07dec69206bd26fbc6c8c019355a2f355863f3159dd222e4c3d4b62b24d6"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/headers.cpython-36.opt-2.pyc","mode":33188,"size":4441,"sha256":"dacb381dcb2c2baf942a0c8c5469ec49d7318e46c3b67b1a1b5a3af28ee75658"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/headers.cpython-36.pyc","mode":33188,"size":7739,"sha256":"4bc19f0091fe174322808065ec2ef85c11cc7c85dde45d8fda527f4f263e1ae9"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/simple_server.cpython-36.opt-1.pyc","mode":33188,"size":5195,"sha256":"3c051f92d12351002eec59fcdd6cd0d390d8886c2ec3a15b34fd0f18b3dbf6c3"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/simple_server.cpython-36.opt-2.pyc","mode":33188,"size":4418,"sha256":"1129fff0e2cb9f4963a1b5be289c862433ddb678d1409c05f224e13fe83a0827"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/simple_server.cpython-36.pyc","mode":33188,"size":5195,"sha256":"3c051f92d12351002eec59fcdd6cd0d390d8886c2ec3a15b34fd0f18b3dbf6c3"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/util.cpython-36.opt-1.pyc","mode":33188,"size":5194,"sha256":"bda233cf57666516032fd7c606d01403cbc1006ecb8527e408c4a3419d0b5346"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/util.cpython-36.opt-2.pyc","mode":33188,"size":3621,"sha256":"efe297263be2f9fcf954a2fc32b93d07dde9f029e6ed7ff41c46633d290140f7"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/util.cpython-36.pyc","mode":33188,"size":5194,"sha256":"bda233cf57666516032fd7c606d01403cbc1006ecb8527e408c4a3419d0b5346"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/validate.cpython-36.opt-1.pyc","mode":33188,"size":14802,"sha256":"4c0d5d563a744508de79e1b57cea982eae4048087500b72f59b31af248f6bb4a"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/validate.cpython-36.opt-2.pyc","mode":33188,"size":11169,"sha256":"cb0bdbbb2225b37e281e5a5700838f7460f0997d26cbe8959af2d398b4b5d5fa"},{"path":"/usr/lib64/python3.6/wsgiref/__pycache__/validate.cpython-36.pyc","mode":33188,"size":14802,"sha256":"4c0d5d563a744508de79e1b57cea982eae4048087500b72f59b31af248f6bb4a"},{"path":"/usr/lib64/python3.6/wsgiref/handlers.py","mode":33188,"size":21001,"sha256":"cf747fbe6ff2329911d47f73ccdcd24be3cfc97c14465f1e8a2d3fed40bc4c8e"},{"path":"/usr/lib64/python3.6/wsgiref/headers.py","mode":33188,"size":6766,"sha256":"0fbf95a47d8e4c0d831fd52312ec43076cbf503c190269876f170a5cf5585fb9"},{"path":"/usr/lib64/python3.6/wsgiref/simple_server.py","mode":33188,"size":5139,"sha256":"db7489a683b64c306ed1b4e0b909eed5c8977fc89898bb7bd55e31183bbe7aea"},{"path":"/usr/lib64/python3.6/wsgiref/util.py","mode":33188,"size":5634,"sha256":"5f75aef68149b582884fb20000c24bf301e441084d4900f7061df425efb8f741"},{"path":"/usr/lib64/python3.6/wsgiref/validate.py","mode":33188,"size":15163,"sha256":"4d33d7f6c4b959cb0ac459ca01303bdc37ece008f4db6d6dabcb3dcdf167b5a1"},{"path":"/usr/lib64/python3.6/xdrlib.py","mode":33188,"size":5913,"sha256":"5bae885a7da49c1fdca1136bf5aece233f0b8f4a6948da3969072c26de395e83"},{"path":"/usr/lib64/python3.6/xml/__init__.py","mode":33188,"size":557,"sha256":"34296f728e7fe68cccb97a9f6edbf3bf3a686f44044c744fe85f207a92ed4811"},{"path":"/usr/lib64/python3.6/xml/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":686,"sha256":"4749a76e8ba8c0501b38b79c7a3a25c050c51b461c11a512ba9d461d371a9ba5"},{"path":"/usr/lib64/python3.6/xml/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":163,"sha256":"eddf9fe43b1c821742e2856bad62ccd1250627a73739671ca40b9c68a0708cc1"},{"path":"/usr/lib64/python3.6/xml/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":686,"sha256":"4749a76e8ba8c0501b38b79c7a3a25c050c51b461c11a512ba9d461d371a9ba5"},{"path":"/usr/lib64/python3.6/xml/dom/NodeFilter.py","mode":33188,"size":936,"sha256":"9bfacbbb64e239a75591a7260b3ed86748eeb4366e6c40f3542753e79bace9a7"},{"path":"/usr/lib64/python3.6/xml/dom/__init__.py","mode":33188,"size":4019,"sha256":"b415a6f3d3663c3ac332ee4a0f4213eadad9281508dc97410e258a03633b063a"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/NodeFilter.cpython-36.opt-1.pyc","mode":33188,"size":953,"sha256":"b7e088fcd016ff9e27a261bd8a7505323499019831cbd3cc8c6d81e093e20474"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/NodeFilter.cpython-36.opt-2.pyc","mode":33188,"size":860,"sha256":"b75ec317fa08765fe70448043e46e970afbab6afff2e6cb8126df25ed0cc47bf"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/NodeFilter.cpython-36.pyc","mode":33188,"size":953,"sha256":"b7e088fcd016ff9e27a261bd8a7505323499019831cbd3cc8c6d81e093e20474"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":5433,"sha256":"da5005e993c2b65d46f1a986266f64d2fddb0d47c9f25655fc9603b3cba5668b"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":4638,"sha256":"5c755e275c113de1f769de38e49d2f0369b6296306c1fe1d3503173002fc8b0d"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":5433,"sha256":"da5005e993c2b65d46f1a986266f64d2fddb0d47c9f25655fc9603b3cba5668b"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/domreg.cpython-36.opt-1.pyc","mode":33188,"size":2823,"sha256":"b801e78f2bb13059ac9b692cc41838cb6490e0cea46c08d40b0b801f1ddb758a"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/domreg.cpython-36.opt-2.pyc","mode":33188,"size":1621,"sha256":"186c2ef357ad1b911c883bee517601e45ac2498fb147a34c40939eb22f95338c"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/domreg.cpython-36.pyc","mode":33188,"size":2823,"sha256":"b801e78f2bb13059ac9b692cc41838cb6490e0cea46c08d40b0b801f1ddb758a"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/expatbuilder.cpython-36.opt-1.pyc","mode":33188,"size":26620,"sha256":"7fc668189c5905c3aa7be70634ac748b92d1d89a94ee80264f1887c32f42c118"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/expatbuilder.cpython-36.opt-2.pyc","mode":33188,"size":23994,"sha256":"06f8006bd95428fffe1f8b3a85d2665fc5677d8d9a46594268eb139944443d93"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/expatbuilder.cpython-36.pyc","mode":33188,"size":27146,"sha256":"dc987e33e347839cbdebc8158322fa598ebee57f9b073b3d3d7d391a82e15c2a"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/minicompat.cpython-36.opt-1.pyc","mode":33188,"size":2699,"sha256":"d88792920b81c046be4b0e2ee08c6f69728ac3e9b7f608358976cb247ec1ba02"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/minicompat.cpython-36.opt-2.pyc","mode":33188,"size":2521,"sha256":"9a2be819c799ed33044e12d28b0bc3b811bdbf23f34d477a7e8aa5ab89a9ba3e"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/minicompat.cpython-36.pyc","mode":33188,"size":2791,"sha256":"a20e24f8c72bf7fad4061f91e2ca6e5b4962ccb379cfe3fad7603e423de40bc7"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/minidom.cpython-36.opt-1.pyc","mode":33188,"size":55746,"sha256":"c0e9ca2a4d8237f6c3545e7dd4fc18744c4af69c7ddb3960fb16315ddc1f8f36"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/minidom.cpython-36.opt-2.pyc","mode":33188,"size":54172,"sha256":"02e0f9a27d0bcc35c049776e487f3fe3051928e93787f853a6876714b3281865"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/minidom.cpython-36.pyc","mode":33188,"size":55848,"sha256":"3e7bd7e51ace5d54fc75e0b5d0139028dad784f223e3a211751da38de83429ea"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/pulldom.cpython-36.opt-1.pyc","mode":33188,"size":10537,"sha256":"7fb905350ab7703e703e0300cbe820e503ff708487f22851f1939631bb95a103"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/pulldom.cpython-36.opt-2.pyc","mode":33188,"size":10103,"sha256":"82d47c32ab57a38171e4c059c23b704c3655bac5c45f6d645879836271dee37c"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/pulldom.cpython-36.pyc","mode":33188,"size":10537,"sha256":"7fb905350ab7703e703e0300cbe820e503ff708487f22851f1939631bb95a103"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/xmlbuilder.cpython-36.opt-1.pyc","mode":33188,"size":13523,"sha256":"1fd753f2b5d60402d7a89ee3ebafeb8d2fa023138910461056262a0abc2de594"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/xmlbuilder.cpython-36.opt-2.pyc","mode":33188,"size":13094,"sha256":"6103530edee65f9a0bfc4c4a8be2c211a83064e61c559306478d55a3ce133bee"},{"path":"/usr/lib64/python3.6/xml/dom/__pycache__/xmlbuilder.cpython-36.pyc","mode":33188,"size":13553,"sha256":"892d2315d06bb33e8ae8358155b1c03486f1c195211c50898dee30957f995f72"},{"path":"/usr/lib64/python3.6/xml/dom/domreg.py","mode":33188,"size":3451,"sha256":"826b02a803930834b96b1086cbee7db1d21c684f65dd3073706dc7bb5ba1a3e8"},{"path":"/usr/lib64/python3.6/xml/dom/expatbuilder.py","mode":33188,"size":35756,"sha256":"76d08b0bdb23aadf525afcdad04696a24541e88e090172eec8bfc485f8b7cceb"},{"path":"/usr/lib64/python3.6/xml/dom/minicompat.py","mode":33188,"size":3367,"sha256":"42974c4c67803dfe80b016ff8aeea0d1e5c751703ab3aec5be765f4e534367be"},{"path":"/usr/lib64/python3.6/xml/dom/minidom.py","mode":33188,"size":66819,"sha256":"750e0efce304ff642dbd9923faebbd50b45823319b6f963413495774480ba18e"},{"path":"/usr/lib64/python3.6/xml/dom/pulldom.py","mode":33188,"size":11761,"sha256":"0e112cde1ea72d712c6eb3fe2e1bb25ae7b9ef3ee7c89d3e663ce931dbeb2ef0"},{"path":"/usr/lib64/python3.6/xml/dom/xmlbuilder.py","mode":33188,"size":12996,"sha256":"9a067e95694fcb0bf218a8ffe0e2a2437d03a6edd9618c8828ca1d22098797f5"},{"path":"/usr/lib64/python3.6/xml/etree/ElementInclude.py","mode":33188,"size":5151,"sha256":"bc836914102f1434b0ca460e47ed54231e609f4cf75792df672c18efd36bac0f"},{"path":"/usr/lib64/python3.6/xml/etree/ElementPath.py","mode":33188,"size":9935,"sha256":"8d4a9f0a5c4c320cea92b1635dd41282bc144166c3a1776cfe13eda428cc0152"},{"path":"/usr/lib64/python3.6/xml/etree/ElementTree.py","mode":33188,"size":57029,"sha256":"9576195c51d1a6e82d8472d7fc85059793e912c04210a2b068cc13d6e5ae7593"},{"path":"/usr/lib64/python3.6/xml/etree/__init__.py","mode":33188,"size":1604,"sha256":"171cc64fd9c7ba894922a35cdec74c4e34ebfd1e7973ad25c01b80ddde35b4cd"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementInclude.cpython-36.opt-1.pyc","mode":33188,"size":1561,"sha256":"9e355539022ba3ecb609d71a55f24b41442ec00baf833ab898f882555e1b44ba"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementInclude.cpython-36.opt-2.pyc","mode":33188,"size":1561,"sha256":"9e355539022ba3ecb609d71a55f24b41442ec00baf833ab898f882555e1b44ba"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementInclude.cpython-36.pyc","mode":33188,"size":1561,"sha256":"9e355539022ba3ecb609d71a55f24b41442ec00baf833ab898f882555e1b44ba"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementPath.cpython-36.opt-1.pyc","mode":33188,"size":6137,"sha256":"37b493ca48419b3fb7259ef6279ed005ab8bf97781b34f801ae2f57a3ae1442b"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementPath.cpython-36.opt-2.pyc","mode":33188,"size":6137,"sha256":"37b493ca48419b3fb7259ef6279ed005ab8bf97781b34f801ae2f57a3ae1442b"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementPath.cpython-36.pyc","mode":33188,"size":6137,"sha256":"37b493ca48419b3fb7259ef6279ed005ab8bf97781b34f801ae2f57a3ae1442b"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementTree.cpython-36.opt-1.pyc","mode":33188,"size":44427,"sha256":"82e604e0cb9a6d53794674c0e309315c9e76096411c3926ac4827fe0a85ba3b9"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementTree.cpython-36.opt-2.pyc","mode":33188,"size":28144,"sha256":"ae4d71ab15beca5aed4c595a96dcbf00d260de2146c5a79afb02733ce9554391"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/ElementTree.cpython-36.pyc","mode":33188,"size":44730,"sha256":"8d1d4b6a6588166e88443480853aab1149ee905709c580f41bb6cef37466e5c4"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":125,"sha256":"5699135811e671d2acb15724259787cc0d52cbe203e5df4d42824f0a2915d028"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":125,"sha256":"5699135811e671d2acb15724259787cc0d52cbe203e5df4d42824f0a2915d028"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":125,"sha256":"5699135811e671d2acb15724259787cc0d52cbe203e5df4d42824f0a2915d028"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/cElementTree.cpython-36.opt-1.pyc","mode":33188,"size":167,"sha256":"77afaa742d14ffe528d74b2cf869da6a3637fe9aca034b84751215b3ef61316d"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/cElementTree.cpython-36.opt-2.pyc","mode":33188,"size":167,"sha256":"77afaa742d14ffe528d74b2cf869da6a3637fe9aca034b84751215b3ef61316d"},{"path":"/usr/lib64/python3.6/xml/etree/__pycache__/cElementTree.cpython-36.pyc","mode":33188,"size":167,"sha256":"77afaa742d14ffe528d74b2cf869da6a3637fe9aca034b84751215b3ef61316d"},{"path":"/usr/lib64/python3.6/xml/etree/cElementTree.py","mode":33188,"size":82,"sha256":"d0f57acab07fe4f9c116c3392d85946bac8e78608f409cea70005f16ea019b57"},{"path":"/usr/lib64/python3.6/xml/parsers/__init__.py","mode":33188,"size":167,"sha256":"b88497adc30d5d5eda7789c25a2206ee9270c932d584d7ac42680325651da45c"},{"path":"/usr/lib64/python3.6/xml/parsers/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":299,"sha256":"ee8ba12b8421c247b71535d44780d6f0caf95116334eb5a1da3241e8c982df2c"},{"path":"/usr/lib64/python3.6/xml/parsers/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":129,"sha256":"0f3a85c727a6a5099130bcce766a7f30f68847e2552829cf64da6d3536fba17c"},{"path":"/usr/lib64/python3.6/xml/parsers/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":299,"sha256":"ee8ba12b8421c247b71535d44780d6f0caf95116334eb5a1da3241e8c982df2c"},{"path":"/usr/lib64/python3.6/xml/parsers/__pycache__/expat.cpython-36.opt-1.pyc","mode":33188,"size":328,"sha256":"dc8faa41f2cfd2869a00e2ba3df93db57c90a66b183ee01118aa284455bfa711"},{"path":"/usr/lib64/python3.6/xml/parsers/__pycache__/expat.cpython-36.opt-2.pyc","mode":33188,"size":262,"sha256":"bf168881ccc09e4345e6862f6a1256f3390a088bf4ad285e42d9cc61fdde778f"},{"path":"/usr/lib64/python3.6/xml/parsers/__pycache__/expat.cpython-36.pyc","mode":33188,"size":328,"sha256":"dc8faa41f2cfd2869a00e2ba3df93db57c90a66b183ee01118aa284455bfa711"},{"path":"/usr/lib64/python3.6/xml/parsers/expat.py","mode":33188,"size":248,"sha256":"64e1947747c2874117a7458bba1f07c86620cc0ed9a4a4116d262878e4a2aa09"},{"path":"/usr/lib64/python3.6/xml/sax/__init__.py","mode":33188,"size":3630,"sha256":"d23507defebf701605653a0cc8d3117c087eb4a4ec4a5eb9bea8780cb5f140d2"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3162,"sha256":"144b92f3c09aeccae413be27206cbb7ccac40882fcf701e37ada5184b9005f00"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":2110,"sha256":"9d479856c24cf0a560d334a55fddba75eea230a05fc39af73df4017f870ef4d1"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3162,"sha256":"144b92f3c09aeccae413be27206cbb7ccac40882fcf701e37ada5184b9005f00"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/_exceptions.cpython-36.opt-1.pyc","mode":33188,"size":5467,"sha256":"b29105da18cae3bdb1605537831b2e76c546231c92441c49354e79759bc429d6"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/_exceptions.cpython-36.opt-2.pyc","mode":33188,"size":2793,"sha256":"089845174799b2408a2e9eaa64d050641d743951937f507f0f76293053335567"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/_exceptions.cpython-36.pyc","mode":33188,"size":5467,"sha256":"b29105da18cae3bdb1605537831b2e76c546231c92441c49354e79759bc429d6"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/expatreader.cpython-36.opt-1.pyc","mode":33188,"size":12395,"sha256":"6045e7fcb1ddc49ba1ea1d067c9e55d37aafc31413c9e56bbcf53bd10cd95509"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/expatreader.cpython-36.opt-2.pyc","mode":33188,"size":11982,"sha256":"afe8e73b32cd9a78283c83e5eb3e042803cfe47c69d38079a4b3e6133f4760bc"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/expatreader.cpython-36.pyc","mode":33188,"size":12395,"sha256":"6045e7fcb1ddc49ba1ea1d067c9e55d37aafc31413c9e56bbcf53bd10cd95509"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/handler.cpython-36.opt-1.pyc","mode":33188,"size":12315,"sha256":"77434a4d669f5a39829cf8db33f3b04e71103551e614117cf9d570330270d24a"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/handler.cpython-36.opt-2.pyc","mode":33188,"size":4506,"sha256":"b40de3b0729d4c8e68575210cf29d4dac9bf37dfff9fc3e74af699d00a2726fa"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/handler.cpython-36.pyc","mode":33188,"size":12315,"sha256":"77434a4d669f5a39829cf8db33f3b04e71103551e614117cf9d570330270d24a"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/saxutils.cpython-36.opt-1.pyc","mode":33188,"size":12809,"sha256":"223c1a7095aaa0ad93a10d10f8925c96513797afb7f90630c2dbd22894e8c3e1"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/saxutils.cpython-36.opt-2.pyc","mode":33188,"size":11152,"sha256":"50740f76d102e3d687ff358f0695f36442246dac951c7c7f964cd7823cc5dbb1"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/saxutils.cpython-36.pyc","mode":33188,"size":12809,"sha256":"223c1a7095aaa0ad93a10d10f8925c96513797afb7f90630c2dbd22894e8c3e1"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/xmlreader.cpython-36.opt-1.pyc","mode":33188,"size":16924,"sha256":"dd4396699cd0565d74d484b168b6670428483fe84e9954020eaea80ec321bd98"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/xmlreader.cpython-36.opt-2.pyc","mode":33188,"size":10461,"sha256":"6ef062bd42fedd56aea8180ade32b5d8086a5e630650d0d3a25d0ddabdfd1675"},{"path":"/usr/lib64/python3.6/xml/sax/__pycache__/xmlreader.cpython-36.pyc","mode":33188,"size":16924,"sha256":"dd4396699cd0565d74d484b168b6670428483fe84e9954020eaea80ec321bd98"},{"path":"/usr/lib64/python3.6/xml/sax/_exceptions.py","mode":33188,"size":4785,"sha256":"cfa45778e457731e0988d9ceef29cf9eeef916f22d7bd53f4cb08c7a2b8b2ce2"},{"path":"/usr/lib64/python3.6/xml/sax/expatreader.py","mode":33188,"size":15704,"sha256":"fadb70de2344c8a74694e8565042be44d7505f23708884c45e0c10deb59de2d6"},{"path":"/usr/lib64/python3.6/xml/sax/handler.py","mode":33188,"size":13922,"sha256":"5882e7a08f97768b63370b2fe2d557d573708494fcb79d068d3e7807b53f4e15"},{"path":"/usr/lib64/python3.6/xml/sax/saxutils.py","mode":33188,"size":12205,"sha256":"8aa4d2667cb13160730b346d37203fd6104498f92b2a633ba1aed04cd72c4f04"},{"path":"/usr/lib64/python3.6/xml/sax/xmlreader.py","mode":33188,"size":12684,"sha256":"922a6e2995952366b366c13736d715d77fa1868ee453fdabe35043059357768f"},{"path":"/usr/lib64/python3.6/xmlrpc/__init__.py","mode":33188,"size":38,"sha256":"87ad5c8954dd56fbbca04517bf87477ff4dce575170c7dd1281d7ef1f4214ac8"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":122,"sha256":"e847707a445f302cf8cc69d3c2405aeae9dee49405f2b11ac2dee120ba02d0e0"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/__init__.cpython-36.opt-2.pyc","mode":33188,"size":122,"sha256":"e847707a445f302cf8cc69d3c2405aeae9dee49405f2b11ac2dee120ba02d0e0"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":122,"sha256":"e847707a445f302cf8cc69d3c2405aeae9dee49405f2b11ac2dee120ba02d0e0"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/client.cpython-36.opt-1.pyc","mode":33188,"size":34520,"sha256":"247ee2151bc9fc28af15b65235e2bf0b544a10d9fee6d10ccbcf4f38b43b772d"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/client.cpython-36.opt-2.pyc","mode":33188,"size":29082,"sha256":"7d13a3ec8f7139f988a032ce0d6645dd16c4fef1adfca0952c4986620b88ac0c"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/client.cpython-36.pyc","mode":33188,"size":34665,"sha256":"5cd023c3140b5359fc6b94b10b583bfd3570e71a33e786fef9fc6ba45cbe3f38"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/server.cpython-36.opt-1.pyc","mode":33188,"size":29459,"sha256":"1721127ba201a1b1742e7e75c95739b7f4170dc3cbfbf30566ee5d6ff93733ba"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/server.cpython-36.opt-2.pyc","mode":33188,"size":18324,"sha256":"1e9cd4cce6c2767178cf4b0e7ca6cc2ec3ea6415e0d7ad3d0cd408a4bf14e02e"},{"path":"/usr/lib64/python3.6/xmlrpc/__pycache__/server.cpython-36.pyc","mode":33188,"size":29556,"sha256":"eea630d68ca7838d3b41dbd37c20dd434d2b771e78f1bc40094b672c37ce06ac"},{"path":"/usr/lib64/python3.6/xmlrpc/client.py","mode":33188,"size":48988,"sha256":"c14db6569ba7193688e070e1ef495ce90c7b90fdf40fb1b7c6998f657da6bacc"},{"path":"/usr/lib64/python3.6/xmlrpc/server.py","mode":33188,"size":37170,"sha256":"5f9a4257a4d2328a7a722ea341e5dd5f73e9b3002af1a2f20ba0069300e40df0"},{"path":"/usr/lib64/python3.6/zipapp.py","mode":33188,"size":7157,"sha256":"b499fb8e70a8b38238528adb999b7cf43d52da3896463bb2b7912878db6ff791"},{"path":"/usr/lib64/python3.6/zipfile.py","mode":33188,"size":76282,"sha256":"04a6cefbbdcc86bba24d5d661e1de53c797b513c4fdacf2a3d9134fe41a11f9e"},{"path":"/usr/share/licenses/python3-libs/LICENSE","mode":33188,"size":12763,"sha256":"b9a6d9320b8f2693e8d41e496ce56caadacaddcca9be2a64a61749278f425cf2"}]}},{"name":"python3-pip-wheel","version":"9.0.3-16.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-pip-wheel:python3-pip-wheel:9.0.3-16.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-pip-wheel:9.0.3-16.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-pip-wheel@0:9.0.3-16.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"python3-pip-wheel","version":"9.0.3","epoch":0,"architecture":"noarch","release":"16.el8","sourceRpm":"python-pip-9.0.3-16.el8.src.rpm","size":1255748,"license":"MIT and Python and ASL 2.0 and BSD and ISC and LGPLv2 and MPLv2.0 and (ASL 2.0 or BSD)","vendor":"CentOS","files":[{"path":"/usr/share/licenses/python3-pip-wheel/LICENSE.txt","mode":33188,"size":1090,"sha256":"fc89805a1f8ebf63b0fa389bead64bb23136f386b397e66ef4ec980f1e72e34f"},{"path":"/usr/share/python3-wheels/pip-9.0.3-py2.py3-none-any.whl","mode":33261,"size":1254658,"sha256":"b289c9b8fa942dd1bb4e25bf6ae45ab259dfcfd53321669987c072b780c0f847"}]}},{"name":"python3-rpm","version":"4.14.2-37.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-rpm:python3-rpm:4.14.2-37.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-rpm:4.14.2-37.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-rpm@0:4.14.2-37.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"python3-rpm","version":"4.14.2","epoch":0,"architecture":"x86_64","release":"37.el8","sourceRpm":"rpm-4.14.2-37.el8.src.rpm","size":430929,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/07/90bc18bc680d2f995f7a0f58fd7a7a3982ab4b","mode":41471,"size":87,"sha256":""},{"path":"/usr/lib/.build-id/26/ac0d9abde1b8aab556544d6ed0c18f1681283c","mode":41471,"size":87,"sha256":""},{"path":"/usr/lib/.build-id/31/ea6e3fb3ca7a7b081b1890c6cb99dec3c4e7c9","mode":41471,"size":57,"sha256":""},{"path":"/usr/lib/.build-id/3f/0204a356dc463e15af580702d34f30e67fde4b","mode":41471,"size":86,"sha256":""},{"path":"/usr/lib/.build-id/b0/d565e6479de0072f5de4770f38a83dcde8fc4e","mode":41471,"size":58,"sha256":""},{"path":"/usr/lib/.build-id/bd/d0f3985c46c35b67717f092f64c19e895e878b","mode":41471,"size":58,"sha256":""},{"path":"/usr/lib64/python3.6/site-packages/rpm-4.14.2-py3.6.egg-info","mode":33188,"size":222,"sha256":"201ffd9afb0dffe735c0cc8d92e35124c45ab8227a15ecf7dda584081c2288c5"},{"path":"/usr/lib64/python3.6/site-packages/rpm/__init__.py","mode":33188,"size":3508,"sha256":"25ea3697bcb624a4142f101cf88f37432b4f0e3bc8accb2e1e433e5ef0ad1c01"},{"path":"/usr/lib64/python3.6/site-packages/rpm/__pycache__/__init__.cpython-36.opt-1.pyc","mode":33188,"size":3619,"sha256":"119087effaa4b78f81a956dae1368bb23a51e2d3affb2c1d71a9c2d94fd5f540"},{"path":"/usr/lib64/python3.6/site-packages/rpm/__pycache__/__init__.cpython-36.pyc","mode":33188,"size":3619,"sha256":"119087effaa4b78f81a956dae1368bb23a51e2d3affb2c1d71a9c2d94fd5f540"},{"path":"/usr/lib64/python3.6/site-packages/rpm/__pycache__/transaction.cpython-36.opt-1.pyc","mode":33188,"size":5616,"sha256":"ae147e164c7885bfb5480dfe2de30bfa71c027e6eaf604a8c73ad54999b13b6a"},{"path":"/usr/lib64/python3.6/site-packages/rpm/__pycache__/transaction.cpython-36.pyc","mode":33188,"size":5616,"sha256":"ae147e164c7885bfb5480dfe2de30bfa71c027e6eaf604a8c73ad54999b13b6a"},{"path":"/usr/lib64/python3.6/site-packages/rpm/_rpm.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":173816,"sha256":"360bed4589a4bb37cd10d00e99dd4f26cc120aef65bfc5f2152ca9b582c2cd82"},{"path":"/usr/lib64/python3.6/site-packages/rpm/_rpm.so","mode":33261,"size":173776,"sha256":"0af0d60d4cf6912640e282249d99942ce440c799e7e40a46d8bd774c129a1946"},{"path":"/usr/lib64/python3.6/site-packages/rpm/_rpmb.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":22328,"sha256":"9e4dab0b6e45ae59649769c00420422e0aa235081ee436b571f5f7ce612cad31"},{"path":"/usr/lib64/python3.6/site-packages/rpm/_rpmb.so","mode":33261,"size":22304,"sha256":"a2abf6ce3c7275a1f116fb72152ece9f010842b9e0354efeec9a66445cb75ea2"},{"path":"/usr/lib64/python3.6/site-packages/rpm/_rpms.cpython-36m-x86_64-linux-gnu.so","mode":33261,"size":7888,"sha256":"4340f6490ba9a875b53a36f19b9bb8d6c10956b6bff7ff2ee8589c4ddc13e1d5"},{"path":"/usr/lib64/python3.6/site-packages/rpm/_rpms.so","mode":33261,"size":11960,"sha256":"4252054be2a1ddc6ab3e69e5e2800876fc6b4f8c67c1197a8a80df642c2eda7e"},{"path":"/usr/lib64/python3.6/site-packages/rpm/transaction.py","mode":33188,"size":5892,"sha256":"c75eed6b47c141c7f5d25e73fbf2c9b15345234f3c346ffbd6c3ca2a490c1c82"}]}},{"name":"python3-setuptools-wheel","version":"39.2.0-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:python3-setuptools-wheel:python3-setuptools-wheel:39.2.0-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:python3-setuptools-wheel:39.2.0-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/python3-setuptools-wheel@0:39.2.0-5.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"python3-setuptools-wheel","version":"39.2.0","epoch":0,"architecture":"noarch","release":"5.el8","sourceRpm":"python-setuptools-39.2.0-5.el8.src.rpm","size":347696,"license":"MIT","vendor":"CentOS","files":[{"path":"/usr/share/licenses/python3-setuptools-wheel/LICENSE","mode":33188,"size":1078,"sha256":"c32a3ac395af6321efd28be73d06a00f0db6ab887d1c21d4fec46128d2056d5a"},{"path":"/usr/share/python3-wheels/setuptools-39.2.0-py2.py3-none-any.whl","mode":33261,"size":346618,"sha256":"938955c41e6dcc2e73ccaf51bd8f755c64df739929a4acff453fde2d0b921bb2"}]}},{"name":"readline","version":"7.0-10.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:readline:readline:7.0-10.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:readline:7.0-10.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/readline@0:7.0-10.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"readline","version":"7.0","epoch":0,"architecture":"x86_64","release":"10.el8","sourceRpm":"readline-7.0-10.el8.src.rpm","size":466321,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/cd/1bc007ec2e558d662585bf8c5bbcd2b9526faa","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/d8/81f0a1b2a891e387f02769db50c350d505b888","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib64/libhistory.so.7","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libhistory.so.7.0","mode":33261,"size":48304,"sha256":"70b02eea19da0311c6a53aac3e73c65fe167c8520ace5f623aa25c03978be1f8"},{"path":"/usr/lib64/libreadline.so.7","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libreadline.so.7.0","mode":33261,"size":338648,"sha256":"69c5979f31f86a1bf7ff92f1b10cac34034a7edf69dc0c59597029aac9a269ee"},{"path":"/usr/share/licenses/readline/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"},{"path":"/usr/share/licenses/readline/USAGE","mode":33188,"size":2025,"sha256":"0759c74d61889b687f33cb03899630d8ecc09c5ebe7cedd2dd2e17eeef193f93"}]}},{"name":"rootfiles","version":"8.1-22.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:rootfiles:rootfiles:8.1-22.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:rootfiles:8.1-22.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/rootfiles@0:8.1-22.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"rootfiles","version":"8.1","epoch":0,"architecture":"noarch","release":"22.el8","sourceRpm":"rootfiles-8.1-22.el8.src.rpm","size":599,"license":"Public Domain","vendor":"CentOS","files":[{"path":"/root/.bash_logout","mode":33188,"size":18,"sha256":"2584c4ba8b0d2a52d94023f420b7e356a1b1a3f2291ad5eba06683d58c48570d"},{"path":"/root/.bash_profile","mode":33188,"size":176,"sha256":"173704a195292bed3d32ebaff5ace8810f7d02e986c43c0cb514d173dc4b2d5c"},{"path":"/root/.bashrc","mode":33188,"size":176,"sha256":"413f2dc32504db2907974b6a9fea78414e804048bd9f3a02c28bd6292b87b0ed"},{"path":"/root/.cshrc","mode":33188,"size":100,"sha256":"4e9418cde048f912e4aadb76ba55045b5d9af0e0565f7091bfc752154451eca9"},{"path":"/root/.tcshrc","mode":33188,"size":129,"sha256":"1bb91935e2cee1d5d2ab7e8d92125acbfac12d9bf3f1c7922aa4ce77ae7ea131"}]}},{"name":"rpm","version":"4.14.2","type":"python","foundBy":"python-package-cataloger","locations":[{"path":"/usr/lib64/python3.6/site-packages/rpm-4.14.2-py3.6.egg-info","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":["UNKNOWN"],"language":"python","cpes":["cpe:2.3:a:rpm:rpm:4.14.2:*:*:*:*:python:*:*","cpe:2.3:a:python-rpm:rpm:4.14.2:*:*:*:*:python:*:*","cpe:2.3:a:*:rpm:4.14.2:*:*:*:*:python:*:*","cpe:2.3:a:rpm:rpm:4.14.2:*:*:*:*:*:*:*","cpe:2.3:a:python-rpm:rpm:4.14.2:*:*:*:*:*:*:*","cpe:2.3:a:*:rpm:4.14.2:*:*:*:*:*:*:*"],"purl":"pkg:pypi/rpm@4.14.2","metadataType":"PythonPackageMetadata","metadata":{"name":"rpm","version":"4.14.2","license":"UNKNOWN","author":"UNKNOWN","authorEmail":"rpm-maint@lists.rpm.org","platform":"UNKNOWN","sitePackagesRootPath":"/usr/lib64/python3.6"}},{"name":"rpm","version":"4.14.2-37.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:rpm:rpm:4.14.2-37.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:rpm:4.14.2-37.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/rpm@0:4.14.2-37.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"rpm","version":"4.14.2","epoch":0,"architecture":"x86_64","release":"37.el8","sourceRpm":"rpm-4.14.2-37.el8.src.rpm","size":2084270,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/bin/rpm","mode":33261,"size":21400,"sha256":"83f359b04cf6c0de3e03e11dd177f3d4cf9d7e517490c4db4a4946779159c1e6"},{"path":"/usr/bin/rpm2archive","mode":33261,"size":16360,"sha256":"d7010bcc367eaba99bfe579aa26ed89c96cc7ef52e41a271d7a1a9ec21cc3fd6"},{"path":"/usr/bin/rpm2cpio","mode":33261,"size":12256,"sha256":"12cfe6f5ba6d71c1d4772a6d1f6f9d2f3f8e6ec39304ef795db27998c3f9d506"},{"path":"/usr/bin/rpmdb","mode":33261,"size":17424,"sha256":"7533a93f2bf3eaf36e2d5c24675920d474109a1bbb8ae8589f774eea6f3c9d27"},{"path":"/usr/bin/rpmkeys","mode":33261,"size":17336,"sha256":"40d600c9a165fe9f0846c1549f26f2f4b5fad8b25ccb8431ad7ed4cddb2d14aa"},{"path":"/usr/bin/rpmquery","mode":41471,"size":3,"sha256":""},{"path":"/usr/bin/rpmverify","mode":41471,"size":3,"sha256":""},{"path":"/usr/lib/.build-id/42/3b133f4c3f8fce6676351a82f6a9d3b787e05a","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/57/6d4b38267c1d098e7114d02c53675f219469a2","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/7f/add46c559566e4950a500d882be1708774a71d","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/d2/86c4e5b81c1bb250e34f612b51953418cf1765","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/ea/ad790382d798fee0d67b71821ffe1b4aed83a5","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/rpm/macros","mode":33188,"size":43387,"sha256":"d4410b0807c240e7a4144986f7d7649c73c354faeda7e3b027d0b1d0a3f368f2"},{"path":"/usr/lib/rpm/platform/aarch64-linux/macros","mode":33188,"size":3037,"sha256":"fb512542e0d06a13ef94b67afd8f665b9e66638788a25dc8892cdffb99ba71ec"},{"path":"/usr/lib/rpm/platform/alpha-linux/macros","mode":33188,"size":3036,"sha256":"d12be62450a06d0f64bb418d4ec51ad381f8c8871c7bf0989f6ced5c0d3075d0"},{"path":"/usr/lib/rpm/platform/alphaev5-linux/macros","mode":33188,"size":3047,"sha256":"5ef22473f381862949e300105c1fd3aef3c30d2549cbef378701a38b38b4cce3"},{"path":"/usr/lib/rpm/platform/alphaev56-linux/macros","mode":33188,"size":3048,"sha256":"22958c1d46ffda385968427641d39c35c4cb6253784c5420f1478dc74bf3f6e7"},{"path":"/usr/lib/rpm/platform/alphaev6-linux/macros","mode":33188,"size":3047,"sha256":"c739443a3c26d3cc58c3d5140ac6d5976d1ac68b08593ebfe338db5a668b63b2"},{"path":"/usr/lib/rpm/platform/alphaev67-linux/macros","mode":33188,"size":3048,"sha256":"408093fc7379c2f31883cb31307aaaefb57f7eafd7b86b9a99b0d40759c9bc92"},{"path":"/usr/lib/rpm/platform/alphapca56-linux/macros","mode":33188,"size":3049,"sha256":"70abc441f14f587c2c91e72bf83f74940d6af277cfbb6ac7d04fbcae0e598b91"},{"path":"/usr/lib/rpm/platform/amd64-linux/macros","mode":33188,"size":3033,"sha256":"d46e0ba264eaec5072e60eb3b070c8dfd8aac4b9136ccfb05294f1a81251df54"},{"path":"/usr/lib/rpm/platform/armv3l-linux/macros","mode":33188,"size":3039,"sha256":"a8398009f8a18e8131db229bacb461df8327f49106a07a8876f86b4833a92134"},{"path":"/usr/lib/rpm/platform/armv4b-linux/macros","mode":33188,"size":3039,"sha256":"e8cbbf9aa930578c1371d1c1fac375488d642fcca9d4d4be7c35e8ccc6cdbc1d"},{"path":"/usr/lib/rpm/platform/armv4l-linux/macros","mode":33188,"size":3039,"sha256":"7c9add18208109699bcaf94cf94ffd6eaf501cca25f0d5876d9181d910cff666"},{"path":"/usr/lib/rpm/platform/armv5tejl-linux/macros","mode":33188,"size":3044,"sha256":"7eddc01d3602d9f64fb278f9a78c275a316f7af289d1edaea45c08b83b12d7c2"},{"path":"/usr/lib/rpm/platform/armv5tel-linux/macros","mode":33188,"size":3043,"sha256":"eac1f1d332ed468b0ca9fc23043bf79ec88f58dbee183066f9e7b553c45ea0b3"},{"path":"/usr/lib/rpm/platform/armv5tl-linux/macros","mode":33188,"size":3041,"sha256":"2866ded7c0a3c7f394cf49143e56237e33c75beef329a71a2bd926484f501748"},{"path":"/usr/lib/rpm/platform/armv6hl-linux/macros","mode":33188,"size":3067,"sha256":"37eef6cb39b090ad15f899d1dfc0c6e0a0a7bb5feee2a661f75997ba23f1ad1d"},{"path":"/usr/lib/rpm/platform/armv6l-linux/macros","mode":33188,"size":3039,"sha256":"84e4fb0f49da78882a8ba9e78fb79e049bd7f0fe4ea27d0e6eef32faf39650b6"},{"path":"/usr/lib/rpm/platform/armv7hl-linux/macros","mode":33188,"size":3075,"sha256":"8a5ea922a2a4282d42ff1d7c46c2074580d0ef10771e5f462ba455b3b208f0ac"},{"path":"/usr/lib/rpm/platform/armv7hnl-linux/macros","mode":33188,"size":3070,"sha256":"acece40e00e3667265f92404deac6616263bbb58cffa572b4707cdd51780e31e"},{"path":"/usr/lib/rpm/platform/armv7l-linux/macros","mode":33188,"size":3039,"sha256":"8ef4d2135cecf4563c5a3af797b757236a55a645a90df41f68b2748af7b5cf56"},{"path":"/usr/lib/rpm/platform/athlon-linux/macros","mode":33188,"size":3039,"sha256":"4c9279ca9f95b776f25b4ceefa98e9c0d8d6be6d947f9a85873317e25f03dd67"},{"path":"/usr/lib/rpm/platform/geode-linux/macros","mode":33188,"size":3043,"sha256":"b7ec000a1d6311590cfb1721f7949d4a9cb1f675ad2a40e6c19a4d9a7be68d10"},{"path":"/usr/lib/rpm/platform/i386-linux/macros","mode":33188,"size":3049,"sha256":"2660bb2b2fe3aa9d3ea444646ebc335f65f77acb6a9b06ad2566814a26507682"},{"path":"/usr/lib/rpm/platform/i486-linux/macros","mode":33188,"size":3037,"sha256":"ed74b4a5125a2ba6d772f0209d48f432ae72f84f6b1e5d543f55c6464ec72947"},{"path":"/usr/lib/rpm/platform/i586-linux/macros","mode":33188,"size":3037,"sha256":"f8da92d7d47cccd3c1c0cf04714a2cd80112cb606b0bf5728f6f071cb01a8c24"},{"path":"/usr/lib/rpm/platform/i686-linux/macros","mode":33188,"size":3037,"sha256":"74e11ddaf6ba99e925361327caba945bd4d919851aa526b01562afcc909abdd2"},{"path":"/usr/lib/rpm/platform/ia32e-linux/macros","mode":33188,"size":3033,"sha256":"d46e0ba264eaec5072e60eb3b070c8dfd8aac4b9136ccfb05294f1a81251df54"},{"path":"/usr/lib/rpm/platform/ia64-linux/macros","mode":33188,"size":3024,"sha256":"860799d04d554170e1145f135f49124df9cfbc15e9fc770e76f15e8c897c4a0c"},{"path":"/usr/lib/rpm/platform/m68k-linux/macros","mode":33188,"size":3075,"sha256":"836fcd20cffa9ff7f108f3d2a1c857b207eb4b1cb819ae269559fc99b40a15d0"},{"path":"/usr/lib/rpm/platform/mips-linux/macros","mode":33188,"size":3026,"sha256":"630c6435736c40185fee0a2b7d57e2153b2fd2ae9255d23db6f0712b540e7f57"},{"path":"/usr/lib/rpm/platform/mips64-linux/macros","mode":33188,"size":3034,"sha256":"7f42bfdd9ca6f2ba23a9d7b635169e64e90139a00ca16e7207d81e9a437510f7"},{"path":"/usr/lib/rpm/platform/mips64el-linux/macros","mode":33188,"size":3038,"sha256":"998f71983432f0be3da3045dc413e79f925afd90ddc2d9c004bc991573598abd"},{"path":"/usr/lib/rpm/platform/mips64r6-linux/macros","mode":33188,"size":3040,"sha256":"1faebec485360d66840aa1ec31fe9c522c59e2fb9cb7fb9fc2d5b4f3903d462a"},{"path":"/usr/lib/rpm/platform/mips64r6el-linux/macros","mode":33188,"size":3044,"sha256":"058675f1bf0b09ca5a603df9e342dd030e3e406f3445068e78708cc396371be6"},{"path":"/usr/lib/rpm/platform/mipsel-linux/macros","mode":33188,"size":3030,"sha256":"9918bcd29e5f937549dceb1127f2775294e496dee38cf2735498168940fbe164"},{"path":"/usr/lib/rpm/platform/mipsr6-linux/macros","mode":33188,"size":3032,"sha256":"a2fdb02bd959921af4154eb8956ac392f26996cba6e7ddabe0a14e0706e0f53b"},{"path":"/usr/lib/rpm/platform/mipsr6el-linux/macros","mode":33188,"size":3036,"sha256":"10c088db50be0d770c729d6b85471e467ae5e74d0e7727e8b27a4eb71031f5a9"},{"path":"/usr/lib/rpm/platform/noarch-linux/macros","mode":33188,"size":2941,"sha256":"bff340ac94d0096ecb18528380a8389e8690f870426338d95589d4c0de63cda5"},{"path":"/usr/lib/rpm/platform/pentium3-linux/macros","mode":33188,"size":3041,"sha256":"0b7be3f55f06a1c5db5b6d70a9fafafb5553c94a540a0efeb3d5610d767e3201"},{"path":"/usr/lib/rpm/platform/pentium4-linux/macros","mode":33188,"size":3041,"sha256":"ce87446960e94f8d9d09d2527f3e6e1e14e4d9b9e93853a2bdc0aa30f1a379d5"},{"path":"/usr/lib/rpm/platform/ppc-linux/macros","mode":33188,"size":3023,"sha256":"e4a7673022c6a463041b3d99f48f4d7f74fb93b56190557566530b701624baa9"},{"path":"/usr/lib/rpm/platform/ppc32dy4-linux/macros","mode":33188,"size":3023,"sha256":"e4a7673022c6a463041b3d99f48f4d7f74fb93b56190557566530b701624baa9"},{"path":"/usr/lib/rpm/platform/ppc64-linux/macros","mode":33188,"size":3031,"sha256":"310da370dce71efb7a310e52b3aa957c0287a68676c1151367697e9d8af72027"},{"path":"/usr/lib/rpm/platform/ppc64iseries-linux/macros","mode":33188,"size":3020,"sha256":"346d040b05a4b9a3cff7583f56611da6b1171ab14202e08587736f04ae995f69"},{"path":"/usr/lib/rpm/platform/ppc64le-linux/macros","mode":33188,"size":3035,"sha256":"e668c7f2ea9ef7f06276a01d759e03b4877592de9ad2d994f9cf717fa23a40e6"},{"path":"/usr/lib/rpm/platform/ppc64p7-linux/macros","mode":33188,"size":3058,"sha256":"12d994fa3a8d2538ffc9f634e41043439fec942415a9c99e95a343df18bc8dee"},{"path":"/usr/lib/rpm/platform/ppc64pseries-linux/macros","mode":33188,"size":3020,"sha256":"346d040b05a4b9a3cff7583f56611da6b1171ab14202e08587736f04ae995f69"},{"path":"/usr/lib/rpm/platform/ppc8260-linux/macros","mode":33188,"size":3023,"sha256":"e4a7673022c6a463041b3d99f48f4d7f74fb93b56190557566530b701624baa9"},{"path":"/usr/lib/rpm/platform/ppc8560-linux/macros","mode":33188,"size":3023,"sha256":"e4a7673022c6a463041b3d99f48f4d7f74fb93b56190557566530b701624baa9"},{"path":"/usr/lib/rpm/platform/ppciseries-linux/macros","mode":33188,"size":3023,"sha256":"e4a7673022c6a463041b3d99f48f4d7f74fb93b56190557566530b701624baa9"},{"path":"/usr/lib/rpm/platform/ppcpseries-linux/macros","mode":33188,"size":3023,"sha256":"e4a7673022c6a463041b3d99f48f4d7f74fb93b56190557566530b701624baa9"},{"path":"/usr/lib/rpm/platform/riscv64-linux/macros","mode":33188,"size":3037,"sha256":"46395b79cc0ad581f0d2d72624bc42ea10c43d50ad0bea80a71c7a8af36bba1b"},{"path":"/usr/lib/rpm/platform/s390-linux/macros","mode":33188,"size":3026,"sha256":"36bfa1b1e3a3fa173645a9e197662b2937af0fe6382b09029b06a634876697f5"},{"path":"/usr/lib/rpm/platform/s390x-linux/macros","mode":33188,"size":3032,"sha256":"deb6eb8a4e922f3c250ac4c51595ad29fb15d89133e93f63067ead5a7b4f1397"},{"path":"/usr/lib/rpm/platform/sh-linux/macros","mode":33188,"size":3017,"sha256":"7c9e53dc71974d67e9f8cd8f9f43195c4f85baec0cda27046b1813fa47d09b90"},{"path":"/usr/lib/rpm/platform/sh3-linux/macros","mode":33188,"size":3022,"sha256":"ddd7defc6670555c21792e907e2117af891bfe4fe8b436a5f03435671472fe31"},{"path":"/usr/lib/rpm/platform/sh4-linux/macros","mode":33188,"size":3029,"sha256":"54f9e8f34beb7fa418f6f39fce5538be34a1ed4cd46019451d046ae9788e4b00"},{"path":"/usr/lib/rpm/platform/sh4a-linux/macros","mode":33188,"size":3031,"sha256":"443b6e76fc4cd7d265cd18b7dee1c5a514dc02527a05be7967de4f44a3f8d724"},{"path":"/usr/lib/rpm/platform/sparc-linux/macros","mode":33188,"size":3052,"sha256":"e5159a3b98d32c1b1cf1e9b18d791360f6cec6a2e547476d46100d728ab5b0f7"},{"path":"/usr/lib/rpm/platform/sparc64-linux/macros","mode":33188,"size":3060,"sha256":"f9b8a21ba703caaf01a2946744828a966d385c4b3b917429b2178277fc866286"},{"path":"/usr/lib/rpm/platform/sparc64v-linux/macros","mode":33188,"size":3057,"sha256":"57131ae62d1f9c7dfb9c7738cd54113336edf93eb4ce088cdf1f67025b46cf69"},{"path":"/usr/lib/rpm/platform/sparcv8-linux/macros","mode":33188,"size":3057,"sha256":"b020d3e6f8472f032eaf6d9e45bf980a1fe79310ebe1977dc29096a5effe990e"},{"path":"/usr/lib/rpm/platform/sparcv9-linux/macros","mode":33188,"size":3052,"sha256":"e5159a3b98d32c1b1cf1e9b18d791360f6cec6a2e547476d46100d728ab5b0f7"},{"path":"/usr/lib/rpm/platform/sparcv9v-linux/macros","mode":33188,"size":3049,"sha256":"12ec822dbcf1de953eff897803a92da39eb23f2c004186412a7a068a58488903"},{"path":"/usr/lib/rpm/platform/x86_64-linux/macros","mode":33188,"size":3033,"sha256":"d46e0ba264eaec5072e60eb3b070c8dfd8aac4b9136ccfb05294f1a81251df54"},{"path":"/usr/lib/rpm/python-macro-helper","mode":33188,"size":634,"sha256":"40fa71de2e6a820ab7f78c5bbc78c24df6a294f62f8c5d1b8be250099269c0cd"},{"path":"/usr/lib/rpm/rpm.daily","mode":33188,"size":296,"sha256":"b98748f664b3245cb7f3d22927b541ee659c221094df7e4d7e5950b6d73eb37d"},{"path":"/usr/lib/rpm/rpm.log","mode":33188,"size":61,"sha256":"ed0a8b7f8ec41ea0d6d8d7ccdc698d216cd7a7154e77bbdaf8eb02bc4535ab0a"},{"path":"/usr/lib/rpm/rpm.supp","mode":33188,"size":688,"sha256":"d88d7b62b79bf754a47ba69d0997ae82c4f0e5ea6af3f8fe2e40ffb1fc3fe054"},{"path":"/usr/lib/rpm/rpm2cpio.sh","mode":33261,"size":1249,"sha256":"9a4f2fc1e0e7dc8f2b93809d5ed2eb1fa4ab36e3442b95243cb209ba823741b7"},{"path":"/usr/lib/rpm/rpmdb_dump","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib/rpm/rpmdb_load","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib/rpm/rpmdb_loadcvt","mode":33261,"size":1467,"sha256":"3a493a0f840898a69a353108c12fa743812618f7e46926a43e2afe6a50dba175"},{"path":"/usr/lib/rpm/rpmdb_recover","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib/rpm/rpmdb_stat","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib/rpm/rpmdb_upgrade","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib/rpm/rpmdb_verify","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib/rpm/rpmpopt-4.14.2","mode":33188,"size":11424,"sha256":"a026eacac6acd078cc5cfe811cbb827eec891b0da4afa8fffddf13aad5820086"},{"path":"/usr/lib/rpm/rpmrc","mode":33188,"size":17154,"sha256":"0376c2bcaeda95235883c368d021659d839eb55bba793187cc63bb3ecb207980"},{"path":"/usr/lib/rpm/tgpg","mode":33261,"size":929,"sha256":"c02352279bc7e500ef1ce692935971047606f54e8d4673dcf6ed8ef6def25752"},{"path":"/usr/lib/tmpfiles.d/rpm.conf","mode":33188,"size":22,"sha256":"175c0da0b7f1425939a2f3f109dd6dfa1caef09de6a9cc3a22acde02cb654ef1"},{"path":"/usr/share/licenses/rpm/COPYING","mode":33188,"size":44170,"sha256":"d56f4f1f290f6920cb053aef0dbcd0b853cda289e2568b364ddbfce220a6f3e0"},{"path":"/var/lib/rpm/Basenames","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Conflictname","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Dirnames","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Group","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Installtid","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Name","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Obsoletename","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Packages","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Providename","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Requirename","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Sha1header","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Sigmd5","mode":33188,"size":0,"sha256":""},{"path":"/var/lib/rpm/Triggername","mode":33188,"size":0,"sha256":""}]}},{"name":"rpm-build-libs","version":"4.14.2-37.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:rpm-build-libs:rpm-build-libs:4.14.2-37.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:rpm-build-libs:4.14.2-37.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/rpm-build-libs@0:4.14.2-37.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"rpm-build-libs","version":"4.14.2","epoch":0,"architecture":"x86_64","release":"37.el8","sourceRpm":"rpm-4.14.2-37.el8.src.rpm","size":215992,"license":"GPLv2+ and LGPLv2+ with exceptions","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/54/b565122859e476d79290af14e77c96c3ff1e16","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/78/8b458e950e30c546a2783a1f79976d879f2acb","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/librpmbuild.so.8","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib64/librpmbuild.so.8.1.0","mode":33261,"size":187808,"sha256":"65434add6d9541c1c95a4078e2cd487d9aef6be21db496b9bffff6b194f2b5b1"},{"path":"/usr/lib64/librpmsign.so.8","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/librpmsign.so.8.1.0","mode":33261,"size":28184,"sha256":"eb41c1fee562ff3f8a60c13253b9b674da592ed5f676f210c68b9c76c771dc1a"}]}},{"name":"rpm-libs","version":"4.14.2-37.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:rpm-libs:rpm-libs:4.14.2-37.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:rpm-libs:4.14.2-37.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/rpm-libs@0:4.14.2-37.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"rpm-libs","version":"4.14.2","epoch":0,"architecture":"x86_64","release":"37.el8","sourceRpm":"rpm-4.14.2-37.el8.src.rpm","size":722464,"license":"GPLv2+ and LGPLv2+ with exceptions","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/6d/18621c3090c8201731b5098fa9810d138d3a72","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/8f/cddbaa9d4ddd05ea8ef6574317a4c19d7a3100","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib64/librpm.so.8","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib64/librpm.so.8.1.0","mode":33261,"size":515048,"sha256":"be9f21ac36213226ef45c5c6f4975558acef4151e1eb28919ee10212cd2fe9b0"},{"path":"/usr/lib64/librpmio.so.8","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/librpmio.so.8.1.0","mode":33261,"size":207416,"sha256":"e761b77a5984cc284497e4de4bc5853ca10f475e51cc9955c67a360d83979080"}]}},{"name":"sed","version":"4.5-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:sed:sed:4.5-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:sed:4.5-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/sed@0:4.5-1.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"sed","version":"4.5","epoch":0,"architecture":"x86_64","release":"1.el8","sourceRpm":"sed-4.5-1.el8.src.rpm","size":776854,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/sed","mode":33261,"size":129928,"sha256":"f3d1b35b5f6e79df105e3c1d99fa12bd7ad44dabfbf0fadec5eb54cbbe414592"},{"path":"/usr/lib/.build-id/b4/6ebb3ddb6628e5d3659d0fa68b8e8e187e5b29","mode":41471,"size":23,"sha256":""},{"path":"/usr/share/licenses/sed/COPYING","mode":33188,"size":35151,"sha256":"e79e9c8a0c85d735ff98185918ec94ed7d175efc377012787aebcf3b80f0d90b"}]}},{"name":"setup","version":"2.12.2-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:setup:setup:2.12.2-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:setup:2.12.2-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/setup@0:2.12.2-5.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"setup","version":"2.12.2","epoch":0,"architecture":"noarch","release":"5.el8","sourceRpm":"setup-2.12.2-5.el8.src.rpm","size":724831,"license":"Public Domain","vendor":"CentOS","files":[{"path":"/etc/aliases","mode":33188,"size":1529,"sha256":"a4c569569f893bc22fbe696c459f8fba0fe4565022637300b705b54a95c47bce"},{"path":"/etc/bashrc","mode":33188,"size":3019,"sha256":"d925e7ec2fdd6861be5f3a6d5a08a1ff13a10d23ebbb8d26717b1b75ca4f118f"},{"path":"/etc/csh.cshrc","mode":33188,"size":1629,"sha256":"51e9d0f4d05d1ba38da624f4c063808361faf53f3d140f5a331ebf8db029384e"},{"path":"/etc/csh.login","mode":33188,"size":1078,"sha256":"792cec9fd4aaa93a5a759ad2dbfc2289c561cb39df57b50fbebb4a40b82c23fc"},{"path":"/etc/environment","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/etc/ethertypes","mode":33188,"size":1362,"sha256":"ed38f9d644befc87eb41a8649c310073240d9a8cd75b2f9c115b5d9d7e5d033c"},{"path":"/etc/exports","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/etc/filesystems","mode":33188,"size":66,"sha256":"ba1ed4fe76cd63c37dbd44a040921db7810c4b63f46ee6635779627a4a36a196"},{"path":"/etc/group","mode":33188,"size":264,"sha256":"5be46faf83078411c18ce0f3cb5e5fc5b56b8cb214a7f5a65dbbef6cb8249e16"},{"path":"/etc/gshadow","mode":32768,"size":198,"sha256":"50b56bf2e0d5dd28900aa04478a9d4cc2ca1ea3452a76a71c71b5ade7f2221cd"},{"path":"/etc/host.conf","mode":33188,"size":9,"sha256":"380f5fe21d755923b44203b58ca3c8b9681c485d152bd5d7e3914f67d821d32a"},{"path":"/etc/hosts","mode":33188,"size":158,"sha256":"498f494232085ec83303a2bc6f04bea840c2b210fbbeda31a46a6e5674d4fc0e"},{"path":"/etc/inputrc","mode":33188,"size":942,"sha256":"3df12b75483c9019090f18bdf46c47399959eddc2b721cf9b563f4010a89a830"},{"path":"/etc/motd","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/etc/networks","mode":33188,"size":58,"sha256":"ae89ab2e35076a070ae7cf5b0edf600c3ea6999e15db9b543ef35dfc76d37cb1"},{"path":"/etc/passwd","mode":33188,"size":533,"sha256":"d137fa8bf6ca9020c35a5bf992f32d4c803497e856e0254618f5abcb2f2425c6"},{"path":"/etc/printcap","mode":33188,"size":233,"sha256":"f809352567a37d932b014311cf626774b97b63ec06d4f7bdd8a9cfcc34c691d9"},{"path":"/etc/profile","mode":33188,"size":2123,"sha256":"b68fe1cd69c9cd923e5dece44bbb6239f3c6e8f747770f6779093b807ba21e99"},{"path":"/etc/profile.d/csh.local","mode":33188,"size":80,"sha256":"07a2a80f1386c89941b3da4cda68790afe19f7425a14e01acdc2fbddb73b5508"},{"path":"/etc/profile.d/lang.csh","mode":33188,"size":2486,"sha256":"ca36c6c6c22c6f2df04529ef468d808c61eba3324189dbb3d56351b288920ac2"},{"path":"/etc/profile.d/lang.sh","mode":33188,"size":2312,"sha256":"1315a04361297386158bb7cde1910d4f74d7f57784b4bb87187704a94100edd7"},{"path":"/etc/profile.d/sh.local","mode":33188,"size":81,"sha256":"3c5de252d65ae8c40e54c21be09dc574ca3641d036d7b44174939a7e64863920"},{"path":"/etc/protocols","mode":33188,"size":6568,"sha256":"d0e614d3ac7c6d9f6fe7b6c8ac678f26cca185de66f5dd34b56e634b2398a8cd"},{"path":"/etc/services","mode":33188,"size":692252,"sha256":"ac7ed9a0608f2ee925d17dfa8154102f56d863e0ab53f39053ff27120ce571ce"},{"path":"/etc/shadow","mode":32768,"size":346,"sha256":"6e9245a475b954564b983ab97760a4dca7a284630c794cb4d8d83247f66ac6db"},{"path":"/etc/shells","mode":33188,"size":44,"sha256":"4ec4e8c524a4f10ca5898ccfaa6d29e7e08aff3a681f6bafbb62e7bec91aa154"},{"path":"/etc/subgid","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/etc/subuid","mode":33188,"size":0,"sha256":"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"},{"path":"/usr/share/licenses/setup/COPYING","mode":33188,"size":118,"sha256":"628095e1ef656bbe9034cf5bfa3c220880a16cd0ceea25b17cd2198ea3503e03"},{"path":"/var/log/lastlog","mode":33188,"size":0,"sha256":""}]}},{"name":"setuptools","version":"39.2.0","type":"python","foundBy":"python-package-cataloger","locations":[{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/METADATA","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/RECORD","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"},{"path":"/usr/lib/python3.6/site-packages/setuptools-39.2.0.dist-info/top_level.txt","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":["UNKNOWN"],"language":"python","cpes":["cpe:2.3:a:setuptools:setuptools:39.2.0:*:*:*:*:python:*:*","cpe:2.3:a:python-setuptools:setuptools:39.2.0:*:*:*:*:python:*:*","cpe:2.3:a:*:setuptools:39.2.0:*:*:*:*:python:*:*","cpe:2.3:a:setuptools:setuptools:39.2.0:*:*:*:*:*:*:*","cpe:2.3:a:python-setuptools:setuptools:39.2.0:*:*:*:*:*:*:*","cpe:2.3:a:*:setuptools:39.2.0:*:*:*:*:*:*:*"],"purl":"pkg:pypi/setuptools@39.2.0","metadataType":"PythonPackageMetadata","metadata":{"name":"setuptools","version":"39.2.0","license":"UNKNOWN","author":"Python Packaging Authority","authorEmail":"distutils-sig@python.org","platform":"UNKNOWN","files":[{"path":"easy_install.py","digest":{"algorithm":"sha256","value":"MDC9vt5AxDsXX5qcKlBz2TnW6Tpuv_AobnfhCJ9X3PM"},"size":"126"},{"path":"pkg_resources/__init__.py","digest":{"algorithm":"sha256","value":"D6DGFHIzVnG-ByUliqZuw3dkB3ccE6z5jdhDJFap12Y"},"size":"103822"},{"path":"pkg_resources/py31compat.py","digest":{"algorithm":"sha256","value":"-ysVqoxLetAnL94uM0kHkomKQTC1JZLN2ZUjqUhMeKE"},"size":"600"},{"path":"pkg_resources/_vendor/__init__.py","digest":{"algorithm":"sha256","value":"47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU"},"size":"0"},{"path":"pkg_resources/_vendor/appdirs.py","digest":{"algorithm":"sha256","value":"tgGaL0m4Jo2VeuGfoOOifLv7a7oUEJu2n1vRkqoPw-0"},"size":"22374"},{"path":"pkg_resources/_vendor/pyparsing.py","digest":{"algorithm":"sha256","value":"PifeLY3-WhIcBVzLtv0U4T_pwDtPruBhBCkg5vLqa28"},"size":"229867"},{"path":"pkg_resources/_vendor/six.py","digest":{"algorithm":"sha256","value":"A6hdJZVjI3t_geebZ9BzUvwRrIXo0lfwzQlM2LcKyas"},"size":"30098"},{"path":"pkg_resources/_vendor/packaging/__about__.py","digest":{"algorithm":"sha256","value":"zkcCPTN_6TcLW0Nrlg0176-R1QQ_WVPTm8sz1R4-HjM"},"size":"720"},{"path":"pkg_resources/_vendor/packaging/__init__.py","digest":{"algorithm":"sha256","value":"_vNac5TrzwsrzbOFIbF-5cHqc_Y2aPT2D7zrIR06BOo"},"size":"513"},{"path":"pkg_resources/_vendor/packaging/_compat.py","digest":{"algorithm":"sha256","value":"Vi_A0rAQeHbU-a9X0tt1yQm9RqkgQbDSxzRw8WlU9kA"},"size":"860"},{"path":"pkg_resources/_vendor/packaging/_structures.py","digest":{"algorithm":"sha256","value":"RImECJ4c_wTlaTYYwZYLHEiebDMaAJmK1oPARhw1T5o"},"size":"1416"},{"path":"pkg_resources/_vendor/packaging/markers.py","digest":{"algorithm":"sha256","value":"uEcBBtGvzqltgnArqb9c4RrcInXezDLos14zbBHhWJo"},"size":"8248"},{"path":"pkg_resources/_vendor/packaging/requirements.py","digest":{"algorithm":"sha256","value":"SikL2UynbsT0qtY9ltqngndha_sfo0w6XGFhAhoSoaQ"},"size":"4355"},{"path":"pkg_resources/_vendor/packaging/specifiers.py","digest":{"algorithm":"sha256","value":"SAMRerzO3fK2IkFZCaZkuwZaL_EGqHNOz4pni4vhnN0"},"size":"28025"},{"path":"pkg_resources/_vendor/packaging/utils.py","digest":{"algorithm":"sha256","value":"3m6WvPm6NNxE8rkTGmn0r75B_GZSGg7ikafxHsBN1WA"},"size":"421"},{"path":"pkg_resources/_vendor/packaging/version.py","digest":{"algorithm":"sha256","value":"OwGnxYfr2ghNzYx59qWIBkrK3SnB6n-Zfd1XaLpnnM0"},"size":"11556"},{"path":"pkg_resources/extern/__init__.py","digest":{"algorithm":"sha256","value":"JUtlHHvlxHSNuB4pWqNjcx7n6kG-fwXg7qmJ2zNJlIY"},"size":"2487"},{"path":"setuptools/__init__.py","digest":{"algorithm":"sha256","value":"WWIdCbFJnZ9fZoaWDN_x1vDA_Rkm-Sc15iKvPtIYKFs"},"size":"5700"},{"path":"setuptools/archive_util.py","digest":{"algorithm":"sha256","value":"kw8Ib_lKjCcnPKNbS7h8HztRVK0d5RacU3r_KRdVnmM"},"size":"6592"},{"path":"setuptools/build_meta.py","digest":{"algorithm":"sha256","value":"FllaKTr1vSJyiUeRjVJEZmeEaRzhYueNlimtcwaJba8"},"size":"5671"},{"path":"setuptools/config.py","digest":{"algorithm":"sha256","value":"3L9wwF1_uprsyHsUHXXsyLmJUA5HIczJYQ2BFzLWjc0"},"size":"18006"},{"path":"setuptools/dep_util.py","digest":{"algorithm":"sha256","value":"fgixvC1R7sH3r13ktyf7N0FALoqEXL1cBarmNpSEoWg"},"size":"935"},{"path":"setuptools/depends.py","digest":{"algorithm":"sha256","value":"hC8QIDcM3VDpRXvRVA6OfL9AaQfxvhxHcN_w6sAyNq8"},"size":"5837"},{"path":"setuptools/dist.py","digest":{"algorithm":"sha256","value":"1j3kuNEGaaAzWz0iLWItxziNyJTZC8MgcTfMZ4U4Wes"},"size":"42613"},{"path":"setuptools/extension.py","digest":{"algorithm":"sha256","value":"uc6nHI-MxwmNCNPbUiBnybSyqhpJqjbhvOQ-emdvt_E"},"size":"1729"},{"path":"setuptools/glibc.py","digest":{"algorithm":"sha256","value":"X64VvGPL2AbURKwYRsWJOXXGAYOiF_v2qixeTkAULuU"},"size":"3146"},{"path":"setuptools/glob.py","digest":{"algorithm":"sha256","value":"Y-fpv8wdHZzv9DPCaGACpMSBWJ6amq_1e0R_i8_el4w"},"size":"5207"},{"path":"setuptools/launch.py","digest":{"algorithm":"sha256","value":"sd7ejwhBocCDx_wG9rIs0OaZ8HtmmFU8ZC6IR_S0Lvg"},"size":"787"},{"path":"setuptools/lib2to3_ex.py","digest":{"algorithm":"sha256","value":"t5e12hbR2pi9V4ezWDTB4JM-AISUnGOkmcnYHek3xjg"},"size":"2013"},{"path":"setuptools/monkey.py","digest":{"algorithm":"sha256","value":"H_yJ91EtDWu20v5JsEmFeDckiYVMhpE3nMcEdxxd-Ig"},"size":"5261"},{"path":"setuptools/msvc.py","digest":{"algorithm":"sha256","value":"8EiV9ypb3EQJQssPcH1HZbdNsbRvqsFnJ7wPFEGwFIo"},"size":"40877"},{"path":"setuptools/namespaces.py","digest":{"algorithm":"sha256","value":"F0Nrbv8KCT2OrO7rwa03om4N4GZKAlnce-rr-cgDQa8"},"size":"3199"},{"path":"setuptools/package_index.py","digest":{"algorithm":"sha256","value":"whsYoQBtGtQMm5bfAiYebGYLMl-HaEChPorAUEd6zdQ"},"size":"40136"},{"path":"setuptools/pep425tags.py","digest":{"algorithm":"sha256","value":"I7lxWpy9XKELBJ0CVYiT7OPW0hkBFe0kNpbEBwXV_XQ"},"size":"10873"},{"path":"setuptools/py27compat.py","digest":{"algorithm":"sha256","value":"3mwxRMDk5Q5O1rSXOERbQDXhFqwDJhhUitfMW_qpUCo"},"size":"536"},{"path":"setuptools/py31compat.py","digest":{"algorithm":"sha256","value":"XuU1HCsGE_3zGvBRIhYw2iB-IhCFK4-Pxw_jMiqdNVk"},"size":"1192"},{"path":"setuptools/py33compat.py","digest":{"algorithm":"sha256","value":"NKS84nl4LjLIoad6OQfgmygZn4mMvrok_b1N1tzebew"},"size":"1182"},{"path":"setuptools/py36compat.py","digest":{"algorithm":"sha256","value":"VUDWxmu5rt4QHlGTRtAFu6W5jvfL6WBjeDAzeoBy0OM"},"size":"2891"},{"path":"setuptools/sandbox.py","digest":{"algorithm":"sha256","value":"9UbwfEL5QY436oMI1LtFWohhoZ-UzwHvGyZjUH_qhkw"},"size":"14276"},{"path":"setuptools/script (dev).tmpl","digest":{"algorithm":"sha256","value":"f7MR17dTkzaqkCMSVseyOCMVrPVSMdmTQsaB8cZzfuI"},"size":"201"},{"path":"setuptools/script.tmpl","digest":{"algorithm":"sha256","value":"WGTt5piezO27c-Dbx6l5Q4T3Ff20A5z7872hv3aAhYY"},"size":"138"},{"path":"setuptools/site-patch.py","digest":{"algorithm":"sha256","value":"BVt6yIrDMXJoflA5J6DJIcsJUfW_XEeVhOzelTTFDP4"},"size":"2307"},{"path":"setuptools/ssl_support.py","digest":{"algorithm":"sha256","value":"YBDJsCZjSp62CWjxmSkke9kn9rhHHj25Cus6zhJRW3c"},"size":"8492"},{"path":"setuptools/unicode_utils.py","digest":{"algorithm":"sha256","value":"NOiZ_5hD72A6w-4wVj8awHFM3n51Kmw1Ic_vx15XFqw"},"size":"996"},{"path":"setuptools/version.py","digest":{"algorithm":"sha256","value":"og_cuZQb0QI6ukKZFfZWPlr1HgJBPPn2vO2m_bI9ZTE"},"size":"144"},{"path":"setuptools/wheel.py","digest":{"algorithm":"sha256","value":"2V7-XGD0jRFvEOo3btpl1I7kUwaZIUFmqnAVYeoMwPs"},"size":"7778"},{"path":"setuptools/windows_support.py","digest":{"algorithm":"sha256","value":"5GrfqSP2-dLGJoZTq2g6dCKkyQxxa2n5IQiXlJCoYEE"},"size":"714"},{"path":"setuptools/_vendor/__init__.py","digest":{"algorithm":"sha256","value":"47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU"},"size":"0"},{"path":"setuptools/_vendor/pyparsing.py","digest":{"algorithm":"sha256","value":"PifeLY3-WhIcBVzLtv0U4T_pwDtPruBhBCkg5vLqa28"},"size":"229867"},{"path":"setuptools/_vendor/six.py","digest":{"algorithm":"sha256","value":"A6hdJZVjI3t_geebZ9BzUvwRrIXo0lfwzQlM2LcKyas"},"size":"30098"},{"path":"setuptools/_vendor/packaging/__about__.py","digest":{"algorithm":"sha256","value":"zkcCPTN_6TcLW0Nrlg0176-R1QQ_WVPTm8sz1R4-HjM"},"size":"720"},{"path":"setuptools/_vendor/packaging/__init__.py","digest":{"algorithm":"sha256","value":"_vNac5TrzwsrzbOFIbF-5cHqc_Y2aPT2D7zrIR06BOo"},"size":"513"},{"path":"setuptools/_vendor/packaging/_compat.py","digest":{"algorithm":"sha256","value":"Vi_A0rAQeHbU-a9X0tt1yQm9RqkgQbDSxzRw8WlU9kA"},"size":"860"},{"path":"setuptools/_vendor/packaging/_structures.py","digest":{"algorithm":"sha256","value":"RImECJ4c_wTlaTYYwZYLHEiebDMaAJmK1oPARhw1T5o"},"size":"1416"},{"path":"setuptools/_vendor/packaging/markers.py","digest":{"algorithm":"sha256","value":"Gvpk9EY20yKaMTiKgQZ8yFEEpodqVgVYtfekoic1Yts"},"size":"8239"},{"path":"setuptools/_vendor/packaging/requirements.py","digest":{"algorithm":"sha256","value":"t44M2HVWtr8phIz2OhnILzuGT3rTATaovctV1dpnVIg"},"size":"4343"},{"path":"setuptools/_vendor/packaging/specifiers.py","digest":{"algorithm":"sha256","value":"SAMRerzO3fK2IkFZCaZkuwZaL_EGqHNOz4pni4vhnN0"},"size":"28025"},{"path":"setuptools/_vendor/packaging/utils.py","digest":{"algorithm":"sha256","value":"3m6WvPm6NNxE8rkTGmn0r75B_GZSGg7ikafxHsBN1WA"},"size":"421"},{"path":"setuptools/_vendor/packaging/version.py","digest":{"algorithm":"sha256","value":"OwGnxYfr2ghNzYx59qWIBkrK3SnB6n-Zfd1XaLpnnM0"},"size":"11556"},{"path":"setuptools/command/__init__.py","digest":{"algorithm":"sha256","value":"NWzJ0A1BEengZpVeqUyWLNm2bk4P3F4iL5QUErHy7kA"},"size":"594"},{"path":"setuptools/command/alias.py","digest":{"algorithm":"sha256","value":"KjpE0sz_SDIHv3fpZcIQK-sCkJz-SrC6Gmug6b9Nkc8"},"size":"2426"},{"path":"setuptools/command/bdist_egg.py","digest":{"algorithm":"sha256","value":"RQ9h8BmSVpXKJQST3i_b_sm093Z-aCXbfMBEM2IrI-Q"},"size":"18185"},{"path":"setuptools/command/bdist_rpm.py","digest":{"algorithm":"sha256","value":"B7l0TnzCGb-0nLlm6rS00jWLkojASwVmdhW2w5Qz_Ak"},"size":"1508"},{"path":"setuptools/command/bdist_wininst.py","digest":{"algorithm":"sha256","value":"_6dz3lpB1tY200LxKPLM7qgwTCceOMgaWFF-jW2-pm0"},"size":"637"},{"path":"setuptools/command/build_clib.py","digest":{"algorithm":"sha256","value":"bQ9aBr-5ZSO-9fGsGsDLz0mnnFteHUZnftVLkhvHDq0"},"size":"4484"},{"path":"setuptools/command/build_ext.py","digest":{"algorithm":"sha256","value":"PCRAZ2xYnqyEof7EFNtpKYl0sZzT0qdKUNTH3sUdPqk"},"size":"13173"},{"path":"setuptools/command/build_py.py","digest":{"algorithm":"sha256","value":"yWyYaaS9F3o9JbIczn064A5g1C5_UiKRDxGaTqYbtLE"},"size":"9596"},{"path":"setuptools/command/develop.py","digest":{"algorithm":"sha256","value":"wKbOw2_qUvcDti2lZmtxbDmYb54yAAibExzXIvToz-A"},"size":"8046"},{"path":"setuptools/command/dist_info.py","digest":{"algorithm":"sha256","value":"5t6kOfrdgALT-P3ogss6PF9k-Leyesueycuk3dUyZnI"},"size":"960"},{"path":"setuptools/command/easy_install.py","digest":{"algorithm":"sha256","value":"E-1Scx4SfCLLZM2e6k8A2T-bo5cDMXqLnig12kxgUy8"},"size":"87026"},{"path":"setuptools/command/egg_info.py","digest":{"algorithm":"sha256","value":"3b5Y3t_bl_zZRCkmlGi3igvRze9oOaxd-dVf2w1FBOc"},"size":"24800"},{"path":"setuptools/command/install.py","digest":{"algorithm":"sha256","value":"a0EZpL_A866KEdhicTGbuyD_TYl1sykfzdrri-zazT4"},"size":"4683"},{"path":"setuptools/command/install_egg_info.py","digest":{"algorithm":"sha256","value":"bMgeIeRiXzQ4DAGPV1328kcjwQjHjOWU4FngAWLV78Q"},"size":"2203"},{"path":"setuptools/command/install_lib.py","digest":{"algorithm":"sha256","value":"11mxf0Ch12NsuYwS8PHwXBRvyh671QAM4cTRh7epzG0"},"size":"3840"},{"path":"setuptools/command/install_scripts.py","digest":{"algorithm":"sha256","value":"UD0rEZ6861mTYhIdzcsqKnUl8PozocXWl9VBQ1VTWnc"},"size":"2439"},{"path":"setuptools/command/launcher manifest.xml","digest":{"algorithm":"sha256","value":"xlLbjWrB01tKC0-hlVkOKkiSPbzMml2eOPtJ_ucCnbE"},"size":"628"},{"path":"setuptools/command/py36compat.py","digest":{"algorithm":"sha256","value":"SzjZcOxF7zdFUT47Zv2n7AM3H8koDys_0OpS-n9gIfc"},"size":"4986"},{"path":"setuptools/command/register.py","digest":{"algorithm":"sha256","value":"bHlMm1qmBbSdahTOT8w6UhA-EgeQIz7p6cD-qOauaiI"},"size":"270"},{"path":"setuptools/command/rotate.py","digest":{"algorithm":"sha256","value":"co5C1EkI7P0GGT6Tqz-T2SIj2LBJTZXYELpmao6d4KQ"},"size":"2164"},{"path":"setuptools/command/saveopts.py","digest":{"algorithm":"sha256","value":"za7QCBcQimKKriWcoCcbhxPjUz30gSB74zuTL47xpP4"},"size":"658"},{"path":"setuptools/command/sdist.py","digest":{"algorithm":"sha256","value":"obDTe2BmWt2PlnFPZZh7e0LWvemEsbCCO9MzhrTZjm8"},"size":"6711"},{"path":"setuptools/command/setopt.py","digest":{"algorithm":"sha256","value":"NTWDyx-gjDF-txf4dO577s7LOzHVoKR0Mq33rFxaRr8"},"size":"5085"},{"path":"setuptools/command/test.py","digest":{"algorithm":"sha256","value":"MeBAcXUePGjPKqjz4zvTrHatLvNsjlPFcagt3XnFYdk"},"size":"9214"},{"path":"setuptools/command/upload.py","digest":{"algorithm":"sha256","value":"i1gfItZ3nQOn5FKXb8tLC2Kd7eKC8lWO4bdE6NqGpE4"},"size":"1172"},{"path":"setuptools/command/upload_docs.py","digest":{"algorithm":"sha256","value":"oXiGplM_cUKLwE4CWWw98RzCufAu8tBhMC97GegFcms"},"size":"7311"},{"path":"setuptools/extern/__init__.py","digest":{"algorithm":"sha256","value":"2eKMsBMwsZqolIcYBtLZU3t96s6xSTP4PTaNfM5P-I0"},"size":"2499"},{"path":"setuptools-39.2.0.dist-info/DESCRIPTION.rst","digest":{"algorithm":"sha256","value":"mOsk4uH4ma3S7RjGk8m4kEMQssSAZxI8Dj1Z8EZHkxA"},"size":"1547"},{"path":"setuptools-39.2.0.dist-info/LICENSE.txt","digest":{"algorithm":"sha256","value":"wyo6w5WvYyHv0ovnPQagDw22q4h9HCHU_sRhKNIFbVo"},"size":"1078"},{"path":"setuptools-39.2.0.dist-info/METADATA","digest":{"algorithm":"sha256","value":"gHeHu4S3oYwMrgCuSC88ChBAIaZOkzUWzKpg9Xomdro"},"size":"3028"},{"path":"setuptools-39.2.0.dist-info/RECORD"},{"path":"setuptools-39.2.0.dist-info/WHEEL","digest":{"algorithm":"sha256","value":"kdsN-5OJAZIiHN-iO4Rhl82KyS0bDWf4uBwMbkNafr8"},"size":"110"},{"path":"setuptools-39.2.0.dist-info/dependency_links.txt","digest":{"algorithm":"sha256","value":"HlkCFkoK5TbZ5EMLbLKYhLcY_E31kBWD8TqW2EgmatQ"},"size":"239"},{"path":"setuptools-39.2.0.dist-info/entry_points.txt","digest":{"algorithm":"sha256","value":"jBqCYDlVjl__sjYFGXo1JQGIMAYFJE-prYWUtnMZEew"},"size":"2990"},{"path":"setuptools-39.2.0.dist-info/metadata.json","digest":{"algorithm":"sha256","value":"20034ySWEQzNtb_Cyg6EYzoZfpYjyHsKleWelH--ROo"},"size":"4969"},{"path":"setuptools-39.2.0.dist-info/top_level.txt","digest":{"algorithm":"sha256","value":"2HUXVVwA4Pff1xgTFr3GsTXXKaPaO6vlG6oNJ_4u4Tg"},"size":"38"},{"path":"setuptools-39.2.0.dist-info/zip-safe","digest":{"algorithm":"sha256","value":"AbpHGcgLb-kRsJGnwFEktk7uzpZOCcBY74-YBdrKVGs"},"size":"1"},{"path":"../../../bin/easy_install","digest":{"algorithm":"sha256","value":"Gezk0fVCHeU4cjSAPY5QeEYRqYmWoPAKE8Edpwhp15U"},"size":"246"},{"path":"../../../bin/easy_install-3.6","digest":{"algorithm":"sha256","value":"Gezk0fVCHeU4cjSAPY5QeEYRqYmWoPAKE8Edpwhp15U"},"size":"246"},{"path":"setuptools-39.2.0.dist-info/INSTALLER","digest":{"algorithm":"sha256","value":"zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg"},"size":"4"},{"path":"__pycache__/easy_install.cpython-36.pyc"},{"path":"setuptools/extern/__pycache__/__init__.cpython-36.pyc"},{"path":"setuptools/__pycache__/namespaces.cpython-36.pyc"},{"path":"setuptools/__pycache__/sandbox.cpython-36.pyc"},{"path":"setuptools/__pycache__/config.cpython-36.pyc"},{"path":"setuptools/__pycache__/py33compat.cpython-36.pyc"},{"path":"setuptools/__pycache__/glob.cpython-36.pyc"},{"path":"setuptools/__pycache__/extension.cpython-36.pyc"},{"path":"setuptools/__pycache__/launch.cpython-36.pyc"},{"path":"setuptools/__pycache__/msvc.cpython-36.pyc"},{"path":"setuptools/__pycache__/dep_util.cpython-36.pyc"},{"path":"setuptools/__pycache__/dist.cpython-36.pyc"},{"path":"setuptools/__pycache__/__init__.cpython-36.pyc"},{"path":"setuptools/__pycache__/lib2to3_ex.cpython-36.pyc"},{"path":"setuptools/__pycache__/wheel.cpython-36.pyc"},{"path":"setuptools/__pycache__/package_index.cpython-36.pyc"},{"path":"setuptools/__pycache__/windows_support.cpython-36.pyc"},{"path":"setuptools/__pycache__/py27compat.cpython-36.pyc"},{"path":"setuptools/__pycache__/build_meta.cpython-36.pyc"},{"path":"setuptools/__pycache__/glibc.cpython-36.pyc"},{"path":"setuptools/__pycache__/monkey.cpython-36.pyc"},{"path":"setuptools/__pycache__/site-patch.cpython-36.pyc"},{"path":"setuptools/__pycache__/unicode_utils.cpython-36.pyc"},{"path":"setuptools/__pycache__/archive_util.cpython-36.pyc"},{"path":"setuptools/__pycache__/py31compat.cpython-36.pyc"},{"path":"setuptools/__pycache__/version.cpython-36.pyc"},{"path":"setuptools/__pycache__/pep425tags.cpython-36.pyc"},{"path":"setuptools/__pycache__/depends.cpython-36.pyc"},{"path":"setuptools/__pycache__/py36compat.cpython-36.pyc"},{"path":"setuptools/__pycache__/ssl_support.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/sdist.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/install.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/bdist_wininst.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/install_lib.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/build_py.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/bdist_rpm.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/egg_info.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/dist_info.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/upload.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/__init__.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/rotate.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/easy_install.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/install_egg_info.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/setopt.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/saveopts.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/build_clib.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/register.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/develop.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/alias.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/bdist_egg.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/install_scripts.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/upload_docs.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/py36compat.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/build_ext.cpython-36.pyc"},{"path":"setuptools/command/__pycache__/test.cpython-36.pyc"},{"path":"setuptools/_vendor/__pycache__/__init__.cpython-36.pyc"},{"path":"setuptools/_vendor/__pycache__/pyparsing.cpython-36.pyc"},{"path":"setuptools/_vendor/__pycache__/six.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/specifiers.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/__init__.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/requirements.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/_compat.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/_structures.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/markers.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/utils.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/version.cpython-36.pyc"},{"path":"setuptools/_vendor/packaging/__pycache__/__about__.cpython-36.pyc"},{"path":"pkg_resources/extern/__pycache__/__init__.cpython-36.pyc"},{"path":"pkg_resources/__pycache__/__init__.cpython-36.pyc"},{"path":"pkg_resources/__pycache__/py31compat.cpython-36.pyc"},{"path":"pkg_resources/_vendor/__pycache__/__init__.cpython-36.pyc"},{"path":"pkg_resources/_vendor/__pycache__/pyparsing.cpython-36.pyc"},{"path":"pkg_resources/_vendor/__pycache__/six.cpython-36.pyc"},{"path":"pkg_resources/_vendor/__pycache__/appdirs.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/specifiers.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/__init__.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/requirements.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/_compat.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/_structures.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/markers.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/utils.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/version.cpython-36.pyc"},{"path":"pkg_resources/_vendor/packaging/__pycache__/__about__.cpython-36.pyc"}],"sitePackagesRootPath":"/usr/lib/python3.6/site-packages","topLevelPackages":["easy_install","pkg_resources","setuptools"]}},{"name":"shadow-utils","version":"4.6-8.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:shadow-utils:shadow-utils:4.6-8.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:shadow-utils:4.6-8.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/shadow-utils@2:4.6-8.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"shadow-utils","version":"4.6","epoch":2,"architecture":"x86_64","release":"8.el8","sourceRpm":"shadow-utils-4.6-8.el8.src.rpm","size":5368080,"license":"BSD and GPLv2+","vendor":"CentOS","files":[{"path":"/etc/default/useradd","mode":33188,"size":119,"sha256":"b121fd1b90c1a2fb6081a137dd7b441c7e7fec61bc17ca60db401a952d7b8825"},{"path":"/etc/login.defs","mode":33188,"size":2027,"sha256":"6a0bdce3ba6298a5a7979d80b4a31ea1c68c22cc6736df3b6e1467997f5377c8"},{"path":"/usr/bin/chage","mode":35309,"size":133928,"sha256":"f910971c8fae948794bc7eaff5d16eb8845b38e828d8b06ebfbdcc1e06401292"},{"path":"/usr/bin/gpasswd","mode":35309,"size":156736,"sha256":"020afb8e19ae84988f4fe1524fc567d9ee60f32013e489e61dfd21404146a90e"},{"path":"/usr/bin/lastlog","mode":33261,"size":33408,"sha256":"5d983071a5058305fe852fcd28b2282acaaf96f9122c6d76db41ab304efca78a"},{"path":"/usr/bin/newgidmap","mode":33261,"size":79960,"sha256":"aff8e58247d7b96e628ec299b93c7dbcc361a9264c8106e164f1bcb58c52e207"},{"path":"/usr/bin/newgrp","mode":35309,"size":88488,"sha256":"07f388887471cd67ac3455b9b60a3e2571a2fec03d18ea011f28a986e8796152"},{"path":"/usr/bin/newuidmap","mode":33261,"size":75696,"sha256":"9d69ac486d94178851fd6a62ce65cafeb0a35ffc9dda0eeb56e82691e9870a81"},{"path":"/usr/bin/sg","mode":41471,"size":6,"sha256":""},{"path":"/usr/lib/.build-id/05/df9e2f797d790fe522e8b4014ea1dcdd08829e","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/07/a2352b2e8616d4d0e3477dbf376d86f9b83c31","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/08/2b8848923bb6f1e792cf4db1c2b74f9a5665fe","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/0a/d1adf0c35f6c0f3117b385de61da74b486dd38","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/0c/7ca5da1a1b2046ca9d7be1db2c2c93741666ef","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/0e/1b1a721013302dc9725d41c4388ba0d91536f6","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/13/f1858e2e5d5cd76e107271ec0bb4c45c9a0a9e","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/18/179f323315880dbbc8da91901eff591c7536bc","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/1f/6948ea93f14c706ad74f0abb8011593e890f76","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/2d/ed7720dc25121650e5c0a66bc51267aa56052d","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/34/c18eb00976e9b4525ce5a74f0fab4000c625ef","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/3a/a00a2588f5f6915145de3119bfcb011207b3fe","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/4f/72b2f4cf7ec41b475220313c082be662ef64d2","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/64/9e2c738a72a6faa844a34476231dff078caddf","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/68/787948c75c4e403d1f24501c1923d446d27623","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/98/34026430eaf639041e9bbc7370011370c9b47c","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/98/e9c6faad698e3593ae5edcb0c3436f148a9a22","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/a6/ce4cecc66c8921c0cefaa4bea2fc83c2a76c5c","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/b7/63426cfb81304f0f4b834d3c582e665d79149b","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/bc/1fdf9a489c820e5570276a7f0bb1b45703782d","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/d1/1522289a502dd16519e685e6af84ba0062ca4a","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/ee/9ffe079d7e5feebc7c98507f978e8ff977154f","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/fc/bae0d978e39671be398396a193fdb107b515bd","mode":41471,"size":30,"sha256":""},{"path":"/usr/sbin/adduser","mode":41471,"size":7,"sha256":""},{"path":"/usr/sbin/chgpasswd","mode":33261,"size":134432,"sha256":"a7d3edfb7f1531a26a5bc4acffb6bef487685ca6d403793f89e717fd21ea3df4"},{"path":"/usr/sbin/chpasswd","mode":33261,"size":115048,"sha256":"c17bcdc842ebfc0f895f2fbb95e6265bb769ba49cb744b66d8999f47e0ea6210"},{"path":"/usr/sbin/groupadd","mode":33261,"size":174200,"sha256":"5791b3002b9f5d9307f55a4e7e14ec93ea86aa6defad10bc3940f24aa78ebef7"},{"path":"/usr/sbin/groupdel","mode":33261,"size":165832,"sha256":"4375ca649752cb11b19fb3853f377a13383d28e394a947b4f7b50aa89ccc504a"},{"path":"/usr/sbin/groupmems","mode":33261,"size":111960,"sha256":"aa41fd92b8c9cf9f65b9df5a0bf9661efc147a278584ae0c446c7a6e496829ed"},{"path":"/usr/sbin/groupmod","mode":33261,"size":180752,"sha256":"8f727684d4b517d57c647cb8babd7537ccc4190a84cc2bba24c501e46eafc69f"},{"path":"/usr/sbin/grpck","mode":33261,"size":111792,"sha256":"049aac06716f2f22b3800b43491e8aa5ee5296774e70c70db5dcbc3ea7fa6ea6"},{"path":"/usr/sbin/grpconv","mode":33261,"size":103416,"sha256":"dd44a58cf0e4a4fc3ff1c656d6af79cc4498d4f2db5bd3d1fb9c1c52f9dbcda9"},{"path":"/usr/sbin/grpunconv","mode":33261,"size":103424,"sha256":"d8661d736f74b50d60163060b92ed02b79600ceb8ae3121c18f339e8a500bdfd"},{"path":"/usr/sbin/newusers","mode":33261,"size":191144,"sha256":"05d86fb0ffbf9e97974d1c69c6649a676aa243162d1ee8490e98fc7fcbf7a55f"},{"path":"/usr/sbin/pwck","mode":33261,"size":106504,"sha256":"602bcbd89ea28e3653eb541cbbbf2770e0d62052a88aba7282b99241a0ce4885"},{"path":"/usr/sbin/pwconv","mode":33261,"size":98336,"sha256":"5dc3e4135230709aac2aa47c235c4c552c50023a850531c63e8299d7d3811453"},{"path":"/usr/sbin/pwunconv","mode":33261,"size":94264,"sha256":"6a5c553c2ad946bbaea621b68acbeea89300417909a938e0608d70bd00ec7538"},{"path":"/usr/sbin/useradd","mode":33261,"size":241752,"sha256":"85c3ca8a5e86ffec554aacdadc42066d030301f0d169412518835982f5e09e4b"},{"path":"/usr/sbin/userdel","mode":33261,"size":185776,"sha256":"3fcab195a99871738274d6a0cacc6456feeed052447698506556a7ebf1157d30"},{"path":"/usr/sbin/usermod","mode":33261,"size":235808,"sha256":"2c68f771d34977daac8a10dcbefe55a9956688b9435b29626286783600c00f40"},{"path":"/usr/sbin/vigr","mode":41471,"size":4,"sha256":""},{"path":"/usr/sbin/vipw","mode":33261,"size":128888,"sha256":"e6dda01f83150b9a0f0b1f5a2ac40461825f08ec301f60c4275fae91c9a4729a"},{"path":"/usr/share/licenses/shadow-utils/gpl-2.0.txt","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/shadow-utils/shadow-bsd.txt","mode":33188,"size":1724,"sha256":"f062266d929e3157924e7a48dd77d8852b246d911ae382b1c06a0b35a724ac3b"}]}},{"name":"snappy","version":"1.1.7-5.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:snappy:snappy:1.1.7-5.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:snappy:1.1.7-5.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/snappy@0:1.1.7-5.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"snappy","version":"1.1.7","epoch":0,"architecture":"x86_64","release":"5.el8","sourceRpm":"snappy-1.1.7-5.el8.src.rpm","size":58789,"license":"BSD","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/62/5eba5035dfe3e50d03d13ddbe47e6a918bde47","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib64/libsnappy.so.1","mode":41471,"size":18,"sha256":""},{"path":"/usr/lib64/libsnappy.so.1.1.7","mode":33261,"size":44528,"sha256":"86be786aff5aee043a26e3bc78474f5c1a3ab3a668cffc5edc6f2e93071ba607"}]}},{"name":"sqlite-libs","version":"3.26.0-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:sqlite-libs:sqlite-libs:3.26.0-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:sqlite-libs:3.26.0-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/sqlite-libs@0:3.26.0-6.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"sqlite-libs","version":"3.26.0","epoch":0,"architecture":"x86_64","release":"6.el8","sourceRpm":"sqlite-3.26.0-6.el8.src.rpm","size":1162241,"license":"Public Domain","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/2c/98702528b8059450446d390a230c336e640163","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libsqlite3.so.0","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib64/libsqlite3.so.0.8.6","mode":33261,"size":1147456,"sha256":"d0c33576e1bc6fc9fda9e0d7de353c1ded79ea2e8bce5401a6d82758fbcfe144"}]}},{"name":"squashfs-tools","version":"4.3-19.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:squashfs-tools:squashfs-tools:4.3-19.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:squashfs-tools:4.3-19.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/squashfs-tools@0:4.3-19.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"squashfs-tools","version":"4.3","epoch":0,"architecture":"x86_64","release":"19.el8","sourceRpm":"squashfs-tools-4.3-19.el8.src.rpm","size":502829,"license":"GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/38/da38430e2efaee0dc82032496b79b86c95427e","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/74/e3c5e5e63b15526211db37d90b94c28473ade8","mode":41471,"size":31,"sha256":""},{"path":"/usr/sbin/mksquashfs","mode":33261,"size":250144,"sha256":"25c7d7baeb7f7a7497a55694806dba8712c8adddb7fd3bf96287363d9fa171b0"},{"path":"/usr/sbin/unsquashfs","mode":33261,"size":139088,"sha256":"96f0c9f0d8c9f8eb5c3d72678f5c3a89ad3273d7d73368a3db3c31bff4f3c0e4"}]}},{"name":"systemd","version":"239-30.el8_2","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:systemd:systemd:239-30.el8_2:*:*:*:*:*:*:*","cpe:2.3:a:*:systemd:239-30.el8_2:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/systemd@0:239-30.el8_2?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"systemd","version":"239","epoch":0,"architecture":"x86_64","release":"30.el8_2","sourceRpm":"systemd-239-30.el8_2.src.rpm","size":11073156,"license":"LGPLv2+ and MIT and GPLv2+","vendor":"CentOS","files":[{"path":"/etc/X11/xinit/xinitrc.d/50-systemd-user.sh","mode":33261,"size":203,"sha256":"8de4483a0c44a7719a66c4c86f6d6d3011feb4729b61b82015cd74cbce313cf3"},{"path":"/etc/crypttab","mode":33152,"size":0,"sha256":""},{"path":"/etc/dnf/protected.d/systemd.conf","mode":33188,"size":21,"sha256":"5a5aa0a6cdfb432f890351ebd1f62d05f9a04d5aa58f57d0758686afaa8d3617"},{"path":"/etc/hostname","mode":33188,"size":0,"sha256":""},{"path":"/etc/inittab","mode":33188,"size":490,"sha256":"1065b3ed2e54f8ec03162a2930b5063f1b30b00c16f28f303029a51ca0bd4470"},{"path":"/etc/locale.conf","mode":33188,"size":0,"sha256":""},{"path":"/etc/localtime","mode":33188,"size":0,"sha256":""},{"path":"/etc/machine-id","mode":33188,"size":0,"sha256":""},{"path":"/etc/pam.d/systemd-user","mode":33188,"size":248,"sha256":"5deae3d161c4dafbe39bdddf019f104b11a15d6576f15dd83f5554f313624fb6"},{"path":"/etc/rc.d/init.d/README","mode":33188,"size":1161,"sha256":"fef38973bf1224275f42ecb6f40b2976299112105426ab39dc7579ad7816ec78"},{"path":"/etc/rc.d/rc.local","mode":33188,"size":474,"sha256":"beda7ff45cad675e294455dbd5fb6662644d72888310556542a901e93aefed2e"},{"path":"/etc/rc.local","mode":41471,"size":13,"sha256":""},{"path":"/etc/sysctl.conf","mode":33188,"size":449,"sha256":"51d16ee2e7eef12dd42e924af6b835861e8b79d11921ba0418d7d0aec7a2a93b"},{"path":"/etc/sysctl.d/99-sysctl.conf","mode":41471,"size":14,"sha256":""},{"path":"/etc/systemd/coredump.conf","mode":33188,"size":615,"sha256":"4032348fa013bb5c24316549716d58619360c0bfbf257c233d767734f3bd6306"},{"path":"/etc/systemd/journald.conf","mode":33188,"size":1027,"sha256":"5665c17814395153b05370a06c1c6cd5b24060ab58b76883535296bac922f7e1"},{"path":"/etc/systemd/logind.conf","mode":33188,"size":1041,"sha256":"42ab0ff7f9cadf64f599d12cb73a74a782e0668f604c574eaf35f62d709d5863"},{"path":"/etc/systemd/resolved.conf","mode":33188,"size":631,"sha256":"eac03bf7ac4bdd7b58650617c3e189a085f700c7c8d656c007e84953e682dd75"},{"path":"/etc/systemd/system.conf","mode":33188,"size":1713,"sha256":"690f1d62077c450adc3888e07a757ba7f5f4417bac5a1aa8482349f4c24e3ae0"},{"path":"/etc/systemd/user.conf","mode":33188,"size":1130,"sha256":"a698d971bc314dff4fae66325e81e1723deb45cf3cd31a4402f1729e69c4a73e"},{"path":"/etc/xdg/systemd/user","mode":41471,"size":18,"sha256":""},{"path":"/usr/bin/busctl","mode":33261,"size":79024,"sha256":"7e8f7c188c9114c04b911e7c05cf0f714d5664e5b6ae440d665e1ccbd8e2fc33"},{"path":"/usr/bin/coredumpctl","mode":33261,"size":45872,"sha256":"9cdbb0f472be2010843897bbe1728232925f5bc81d2b2124d4f0ff26038cc0be"},{"path":"/usr/bin/hostnamectl","mode":33261,"size":21184,"sha256":"a1d214a544ba006c3f6197651274b3ea8811ba54db9f88a1fa4527d6d7e9f525"},{"path":"/usr/bin/journalctl","mode":33261,"size":78712,"sha256":"1bd859f7c0ed85317adee2596e0e79898859392a3cfef341f11684b777e573bd"},{"path":"/usr/bin/localectl","mode":33261,"size":29456,"sha256":"f28290f6e038ae8109dfe59e7684605a1edb07767cf7da3a75be7e30d80ab7f7"},{"path":"/usr/bin/loginctl","mode":33261,"size":58592,"sha256":"a96c91e701d7e76bd6fea0199750726bdff742cfcede32ff8b069dfd9f4a039f"},{"path":"/usr/bin/resolvectl","mode":33261,"size":200344,"sha256":"e37fecbe8d7d9ebaa3f0168fd4017cc91d0c23c05e027f273b70f35eaa443b75"},{"path":"/usr/bin/systemctl","mode":33261,"size":215336,"sha256":"fb9ff04d650edca8636200ddce16e41ef51d775e9a7299ad9c4d8e746f8481ef"},{"path":"/usr/bin/systemd-analyze","mode":33261,"size":1580448,"sha256":"4492b8deccc0c03663e7b06c6f0296dbe467e2b881e9e17b5714dc22b397b9a5"},{"path":"/usr/bin/systemd-ask-password","mode":33261,"size":12520,"sha256":"feefab6905639817db131a63b616aef49f3a27a9c743a90b2bab30ee90dfb1a8"},{"path":"/usr/bin/systemd-cat","mode":33261,"size":16608,"sha256":"3077a7337f9add538220cb9a969ca9f9559f3d758b9e0b60ad5c0fb9cc8b5ac1"},{"path":"/usr/bin/systemd-cgls","mode":33261,"size":16632,"sha256":"b594ce17eefd24c34f7d1f40044d2d751916ae2cc0667601d4f1188ca541d008"},{"path":"/usr/bin/systemd-cgtop","mode":33261,"size":33536,"sha256":"8a7e70fab7b9194882aa1628e344c5f6c275441ef7ad5c5b0a7a0d7f939d2ef9"},{"path":"/usr/bin/systemd-delta","mode":33261,"size":25176,"sha256":"596a43a4059c65f58cd28c8a32127356d4decb2b13d6c30f91f58356a4cfd962"},{"path":"/usr/bin/systemd-detect-virt","mode":33261,"size":12336,"sha256":"a5cf49cd2286b891bb957b1306b3118d4c54b6e10188c090e2c92c8965472803"},{"path":"/usr/bin/systemd-escape","mode":33261,"size":16608,"sha256":"7bccfff00ae117c85ced7b86cfa5375285576cc2fce1c0ad77f0f435449cf287"},{"path":"/usr/bin/systemd-firstboot","mode":33261,"size":37712,"sha256":"62f8e0f7fb194f2c7754bf75382f2f2075375fc0e288e9d86c3b0b29a7d6ea50"},{"path":"/usr/bin/systemd-inhibit","mode":33261,"size":16632,"sha256":"b1ed29471deaadc400d5544596a7026c3b8631e4337161cbee586797d8a24762"},{"path":"/usr/bin/systemd-machine-id-setup","mode":33261,"size":25256,"sha256":"32b7d3c448c389b2459905900f6f11b933a61c175f1dba8105feb212c80bfb6b"},{"path":"/usr/bin/systemd-mount","mode":33261,"size":54128,"sha256":"c734cd17fb0a2aea7710a04f6f87a3fc439df4e7fc9d3bbf8761f5aef91d6190"},{"path":"/usr/bin/systemd-notify","mode":33261,"size":16616,"sha256":"21af39769ffbc0c80f88db49a6cc94e063cbd51b2d337f93393485f380a9d734"},{"path":"/usr/bin/systemd-path","mode":33261,"size":16600,"sha256":"268ed2e6f6a6795e23c57b81bf464f62aa37340592fbb633f25f4224830205aa"},{"path":"/usr/bin/systemd-resolve","mode":41471,"size":10,"sha256":""},{"path":"/usr/bin/systemd-run","mode":33261,"size":49984,"sha256":"bc54cfb6cd0591ec54dd3ff9dc0e83de414964ffc97f561ace491be3f747fcef"},{"path":"/usr/bin/systemd-socket-activate","mode":33261,"size":25216,"sha256":"f86a7386e124c62a9f14245e82ae83c3600bbe6e60ff9b006290953a91bfd1c9"},{"path":"/usr/bin/systemd-stdio-bridge","mode":33261,"size":16616,"sha256":"0f4b49417b6e6e22a26ea0f8e5e6bc73930e8926a49287ee42620623e48542a5"},{"path":"/usr/bin/systemd-sysusers","mode":33261,"size":54216,"sha256":"d00101248c38e892c2bfd1ff6ad909b3fcafdddc3816e4445f68fd43528a5341"},{"path":"/usr/bin/systemd-tmpfiles","mode":33261,"size":74936,"sha256":"e3993919a0b3045aedcc77cdb4e097dfbcc2816948c079a7fa6eafcb10c4893f"},{"path":"/usr/bin/systemd-tty-ask-password-agent","mode":33261,"size":33488,"sha256":"60aa887bdab46defa1483b7f6e85e1b1b6ab0c3293189c64c45b7fefb3b1d97d"},{"path":"/usr/bin/systemd-umount","mode":41471,"size":13,"sha256":""},{"path":"/usr/bin/timedatectl","mode":33261,"size":37704,"sha256":"478860baa7de11a934f23623dc6a0971ca4661df8545672b4b4a1ab6a13ed3e7"},{"path":"/usr/lib/.build-id/03/98f82070aad9d5ffe7942f560be6fa0b91921f","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/0d/0fb03c6c4b048cee980bfe7989e425d355c998","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/0f/20352be26c0403c9a53aff1807844b8d49c7d9","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/14/6340f36549ec7b460c973254d140936d044b1f","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/15/f5635051c17cb72529fbe508128075eedf1e6a","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/1d/bae594dd8a428a96e70281ba4ee8adb3aaa502","mode":41471,"size":72,"sha256":""},{"path":"/usr/lib/.build-id/22/7c328016021258aedcda47a32f682dffd370e4","mode":41471,"size":69,"sha256":""},{"path":"/usr/lib/.build-id/24/9472c71d34a1500e7a4f1a24fd26f8d2dcc2ec","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/28/5807e9e01e21050a40d09449a5dcff386ee563","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/29/55e42029cc59725fa197c7539628436dd65e85","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/2b/8376f53bda320d63d5c1eaeec796e1e135f4d9","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/2c/97e6522e90838492f0aed4528e86cf872de655","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/34/a5a96f64436bae93b7915717d07e35f9453ee2","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/3b/e8765907711a2c0fbd2a578c99c226af1af2a7","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/3e/d20249c35fff60e7cffd1fd027cea28096edd5","mode":41471,"size":52,"sha256":""},{"path":"/usr/lib/.build-id/44/839dd85cd66947fe6d9dfa0fc2b00aa67f5514","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/49/660499b43d94cacde3ba8b47b81e2cf7f4a0b0","mode":41471,"size":69,"sha256":""},{"path":"/usr/lib/.build-id/50/7d4528eb74e14ddfb1f0d39d88649e9db7369c","mode":41471,"size":69,"sha256":""},{"path":"/usr/lib/.build-id/54/0db59acff4e4129738b0ea033cc41d76ecb5a9","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/54/f972605c536fd8738834aed3b96f1558e1fb4f","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/55/5eff5e6bbd19072d798e2775aaa0e2d1bd1921","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/56/36cac4d9621de604eadf88c319641123344cd7","mode":41471,"size":50,"sha256":""},{"path":"/usr/lib/.build-id/5a/3936864baa3439af32f11c614b42bd6f85a998","mode":41471,"size":77,"sha256":""},{"path":"/usr/lib/.build-id/5d/d5b7ef8818b4ee07683ed308ab5418fe0442e1","mode":41471,"size":90,"sha256":""},{"path":"/usr/lib/.build-id/5e/a225129ce1e172b82a3e68e9285fd461df379a","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/60/2020e1a2bcdaed75c197dd4a8f5ec902f15f3c","mode":41471,"size":49,"sha256":""},{"path":"/usr/lib/.build-id/61/58b557bc733d34c4512e9f5d8382e8dafa70df","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/64/271bff96623830e5b7202e751a81de9daa87ba","mode":41471,"size":49,"sha256":""},{"path":"/usr/lib/.build-id/66/62764c72dd167dfa4dc7d0ceb2157461d8bb70","mode":41471,"size":49,"sha256":""},{"path":"/usr/lib/.build-id/66/efb756798ec30ae167d50f5fc142a312baa946","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/6c/dcc9ee1605c1ef97aa66195a638bf28aa65cc6","mode":41471,"size":68,"sha256":""},{"path":"/usr/lib/.build-id/74/096f3b6e127110a1cc23fb4800d0dd2753354b","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/75/66439cd330629e0eae047c79d516d987699a73","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/75/d27884d9f38f13f23aa128a2af059181177c9f","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/76/356b361a3e34df401a4900a04c4afa03b535e5","mode":41471,"size":50,"sha256":""},{"path":"/usr/lib/.build-id/7b/af5fc997ca5df2259e2f1978415334057303f5","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/7b/dde8f4873ef2b0ca0e0945d8fe091b72038087","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/81/4036d6be9473c69a7430813d322ef379f1776f","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/82/3d698d65353d84d54bb5c1b465dc587dc20922","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/.build-id/82/934601746dc1f85e9734f81da0c475f1fb594e","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/86/bbfceaef0f6efed70de97925a2fadd5a404329","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/.build-id/91/ba1f5577fa73ebe09239d3c1de1fc1e883c082","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/9b/0da098b5d22e55644b68ba3851d82e9c85ac69","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/9f/d54addab9c2ec588922212fbdde863f10f7caf","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/a5/a096bb5ad9a0203ba4ec589a8b86997f9d2296","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/ab/23873577751644650a720e7790278283d2db94","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/ae/4f149afe2a69ed710efe95ba63cddd5bbee95c","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/b2/0cd68b5aeb39a709e0f377a158abadc2c35a42","mode":41471,"size":49,"sha256":""},{"path":"/usr/lib/.build-id/b7/7e04f7f1f5bbb18bc616336d4e4f66e0a1139f","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/.build-id/ba/d2ca930ec90b4ae87d6b96967cde0d76f027b3","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/c6/8b4c3d23dda9d118affd448a8aaaef4d488ca7","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/cb/dc66615a4ab07a8e3ce65c42d26570c8a952d1","mode":41471,"size":49,"sha256":""},{"path":"/usr/lib/.build-id/cc/a1b5bfeb612535add30c776f689a9843cebd05","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/d4/66282c2b1627974941b2b47fca921948068aaa","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/d5/174dc32c6b6789cfb5bc13f328f6dee8b262a2","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/d5/984a74728733d75491160dbba82faaead42c9e","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/.build-id/d8/2435725bda4d635c90f7addc06d1943a1198a5","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/de/5e108e9ade6cc5c845bfed7a507d6a76567c6a","mode":41471,"size":75,"sha256":""},{"path":"/usr/lib/.build-id/e0/56199cd77fdf7414a4e4a436bfc4cebcfbb324","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/e0/9fb5bb746250c0b43bf715f5385f02d41850dd","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/e3/94ca04f18bf3f21dcb5ccf24c9c852b7998a72","mode":41471,"size":43,"sha256":""},{"path":"/usr/lib/.build-id/e8/eeae3a4e46eb844c9056fcdb4f329f814de9bb","mode":41471,"size":35,"sha256":""},{"path":"/usr/lib/.build-id/eb/04c9b6d1ca31623536a8d867c898f27040c93b","mode":41471,"size":52,"sha256":""},{"path":"/usr/lib/.build-id/ec/3dc81ddbaf991b9af79c12aef603ae98abe766","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/ed/d94cbbf307c49989af8d9434c94af3fa7ab670","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/fc/afb1cd6cefef6cc9952ba5a74d93ca48b53e71","mode":41471,"size":40,"sha256":""},{"path":"/usr/lib/environment.d/99-environment.conf","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/rpm/macros.d/macros.systemd","mode":33188,"size":3951,"sha256":"fcd7792ed30d2106b3b1753aaf1e412447eb9cbe84a08b30897ebfdcc9008956"},{"path":"/usr/lib/sysctl.d/50-coredump.conf","mode":33188,"size":524,"sha256":"1070d896588f42827c48f2fb0dcc82871afbc3afb4e5523bb75428f9af18c6c4"},{"path":"/usr/lib/sysctl.d/50-default.conf","mode":33188,"size":1270,"sha256":"7b42e9bc26a796c61d76976f4dbb36a3d1e293c2812591888b7019bd94f6b6b8"},{"path":"/usr/lib/sysctl.d/50-pid-max.conf","mode":33188,"size":636,"sha256":"27127687d1d64f7427920347855bb515ca5cb57cc20cffa7f6e1010a502992f8"},{"path":"/usr/lib/systemd/catalog/systemd.be.catalog","mode":33188,"size":13121,"sha256":"303bed8a521fd40abc2fa3faf06a71f9ca16f6fee65801b128ff5083da8af831"},{"path":"/usr/lib/systemd/catalog/systemd.be@latin.catalog","mode":33188,"size":10130,"sha256":"e3ecf9ea1f3034056e82d0bdea652e8f1ad0e6204344d8537817541c7965f378"},{"path":"/usr/lib/systemd/catalog/systemd.bg.catalog","mode":33188,"size":14307,"sha256":"b4668be207f7b044cf18bee6430bcbec825d065e09cb3cc7130b5c0ccd48f9f4"},{"path":"/usr/lib/systemd/catalog/systemd.catalog","mode":33188,"size":12554,"sha256":"0d22471d7c0d8e13195c2aae4862fd3f459a8fa0b7ec383327729d084ee656dd"},{"path":"/usr/lib/systemd/catalog/systemd.de.catalog","mode":33188,"size":475,"sha256":"2b9739e79d7da863d0f82d31bf312c733f77ef14c6cc78077df78adfb1c6bdcf"},{"path":"/usr/lib/systemd/catalog/systemd.fr.catalog","mode":33188,"size":13370,"sha256":"75bd02aa248752652619c087feaf6ff22180e5e758fbe7f2461d31301b7d87c8"},{"path":"/usr/lib/systemd/catalog/systemd.it.catalog","mode":33188,"size":11363,"sha256":"d104b5c42c3542ac69ea9a08ae294630e3c13c8c9164f6565cda7a7caa4d31c3"},{"path":"/usr/lib/systemd/catalog/systemd.pl.catalog","mode":33188,"size":13061,"sha256":"ab6b4d0dc7eb10c01fa373fe01874910a4c8c5a8abe8164ab4c645fc8f656894"},{"path":"/usr/lib/systemd/catalog/systemd.pt_BR.catalog","mode":33188,"size":8388,"sha256":"ec509500db8da0afb3ca52584d8de5ab94717ec967cfb646a1b94da76583f17a"},{"path":"/usr/lib/systemd/catalog/systemd.ru.catalog","mode":33188,"size":20483,"sha256":"a30889a101b69e7f038a7f0c48edccf076bda60947297e3313968f53e92fde34"},{"path":"/usr/lib/systemd/catalog/systemd.zh_CN.catalog","mode":33188,"size":7372,"sha256":"b19ddfa8c118faf433cbc8dd387862ff3311f632e1e12d1e9a2966cc0208be41"},{"path":"/usr/lib/systemd/catalog/systemd.zh_TW.catalog","mode":33188,"size":7331,"sha256":"22ca83df7f68d3e7267a63e03afb7ff2d786f3f2a2f8b929d675dad352347069"},{"path":"/usr/lib/systemd/libsystemd-shared-239.so","mode":33261,"size":2707624,"sha256":"310bbcd229a9ffe5f15ea1f4f91f261c417ada6c07d94435a30db59ceecc45ed"},{"path":"/usr/lib/systemd/portable/profile/default/service.conf","mode":33188,"size":1101,"sha256":"d640d3b6c35e8cd64aabce9150b544e1b4888db0e2f6e5e70b033dfaf7b1e72a"},{"path":"/usr/lib/systemd/portable/profile/nonetwork/service.conf","mode":33188,"size":1038,"sha256":"29a5e013cbed86d700460ccad5a171a70f22e9112fcf22389eb77f2067eca075"},{"path":"/usr/lib/systemd/portable/profile/strict/service.conf","mode":33188,"size":775,"sha256":"1e8884086e11c70fda3c2f3b55d5dae579acf6c3b431711bca3c1877d37f37d1"},{"path":"/usr/lib/systemd/portable/profile/trusted/service.conf","mode":33188,"size":182,"sha256":"ac83f7cecde8f95d43f0e6794e9f3f95780d02b1e5e2e9b89d3f4e43791fe7f0"},{"path":"/usr/lib/systemd/portablectl","mode":33261,"size":37752,"sha256":"66a2475d283d1713ba4e023e2e5f7268835505848af403518c8b69be2da5fc90"},{"path":"/usr/lib/systemd/purge-nobody-user","mode":33261,"size":2351,"sha256":"2e11c81dcc7ad6ffac40750eb9d624065caf5a4a03da21f876310ab50140ad62"},{"path":"/usr/lib/systemd/resolv.conf","mode":33188,"size":678,"sha256":"d161d962da2e1e1efb4047c411ae4b70038b85530effd7601006dab92af188da"},{"path":"/usr/lib/systemd/system-generators/systemd-debug-generator","mode":33261,"size":16648,"sha256":"ed7613d7c9192412e18a6e394bc132ba55b030106ab350abf4c3e598b15c57f3"},{"path":"/usr/lib/systemd/system-generators/systemd-fstab-generator","mode":33261,"size":46080,"sha256":"080913e47b61306d0fca60f1029effb9d9f27fb7a23aa02eeb6124683d8903f1"},{"path":"/usr/lib/systemd/system-generators/systemd-getty-generator","mode":33261,"size":17048,"sha256":"cc7635f5e5deba9a41acc49584b574dfdcf94bf76fffe3ba9ec4b304caa62e4f"},{"path":"/usr/lib/systemd/system-generators/systemd-rc-local-generator","mode":33261,"size":12360,"sha256":"8191f690b63231dbf6935951c9d3756e8ed2b3854336bd0fe2d609a666a075c9"},{"path":"/usr/lib/systemd/system-generators/systemd-system-update-generator","mode":33261,"size":12392,"sha256":"b68d045ce94a30e5e3f3379cee162bf8ad744c1c2129d17ce6ba72b246fd2f34"},{"path":"/usr/lib/systemd/system-generators/systemd-sysv-generator","mode":33261,"size":33528,"sha256":"77c3446994404f097793a9b670941692e35a4d34767dc649c4e0a2484bce823e"},{"path":"/usr/lib/systemd/system-generators/systemd-veritysetup-generator","mode":33261,"size":17016,"sha256":"0f7d14951963a0958be69aa330f47af195f3d325d241e0e4f17527179ea05eb7"},{"path":"/usr/lib/systemd/system-preset/90-systemd.preset","mode":33188,"size":951,"sha256":"31da5a1f9b11b2cb9f6b5cf7aa2f87f7e5ed47219c3be2f067d6cc5edd6ef380"},{"path":"/usr/lib/systemd/system/autovt@.service","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib/systemd/system/basic.target","mode":33188,"size":956,"sha256":"72494b9ee3507c7c3c12e2983ed298409bdbaae2795be0d64b9456d869710b46"},{"path":"/usr/lib/systemd/system/bluetooth.target","mode":33188,"size":419,"sha256":"146797e480e9493163bff8f4df445279b49c30530054948d0da88eb1dafbaaf7"},{"path":"/usr/lib/systemd/system/console-getty.service","mode":33188,"size":1082,"sha256":"f6d4e052555d0f7261538b2ecef31857a3644bfbb55768257da58dd319d45f37"},{"path":"/usr/lib/systemd/system/container-getty@.service","mode":33188,"size":1263,"sha256":"28634acce233c35308cf6a19a18dc932ede7bae03f94db0017ac2f997a20fbab"},{"path":"/usr/lib/systemd/system/ctrl-alt-del.target","mode":41471,"size":13,"sha256":""},{"path":"/usr/lib/systemd/system/dbus-org.freedesktop.hostname1.service","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/dbus-org.freedesktop.locale1.service","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/systemd/system/dbus-org.freedesktop.login1.service","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/systemd/system/dbus-org.freedesktop.portable1.service","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/dbus-org.freedesktop.timedate1.service","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/debug-shell.service","mode":33188,"size":1084,"sha256":"e57bf4c34e2fe38eb29d7300abd84dbf7c8260fabd3ea54b0d1e4b583e7086c6"},{"path":"/usr/lib/systemd/system/default.target","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib/systemd/system/dev-hugepages.mount","mode":33188,"size":750,"sha256":"50abe4124ccc8e42471728a1ea1bc7e46da1b9db74d7be0ee76d52d117341eda"},{"path":"/usr/lib/systemd/system/dev-mqueue.mount","mode":33188,"size":665,"sha256":"f601c752b2df6fdda76b3355e6f6c441d8b3643514206220c5a14baf50aba329"},{"path":"/usr/lib/systemd/system/emergency.service","mode":33188,"size":801,"sha256":"809aed09c5931ca6a004fb863223ace0756a4e7b0dcb8c59186f18b7918b1347"},{"path":"/usr/lib/systemd/system/emergency.target","mode":33188,"size":471,"sha256":"92f51ecd53d6bc7380ed19349519872bc83ed102fe45ae3c0b80189762b06159"},{"path":"/usr/lib/systemd/system/exit.target","mode":33188,"size":541,"sha256":"0bfc7f59c7f88c4e8513a112447a4e3c01aeed858bc19109a169535ecc9c1231"},{"path":"/usr/lib/systemd/system/final.target","mode":33188,"size":480,"sha256":"e79c7f1a7f75116f99eacee0053a68bad270747fc267c2066c5b7f5ff8469e96"},{"path":"/usr/lib/systemd/system/getty-pre.target","mode":33188,"size":506,"sha256":"626128caae4a6c36b289d15a706524825e4817540de01dc748db158771aced59"},{"path":"/usr/lib/systemd/system/getty.target","mode":33188,"size":500,"sha256":"5064c0664818eaa20ffb783628ef614d8864984e499f25282ab7c1021781b1e8"},{"path":"/usr/lib/systemd/system/getty@.service","mode":33188,"size":1975,"sha256":"6482c9736abc490f697890a48dd4d9b7dee6ac4dc24f2f8199b7f9566f23dbe4"},{"path":"/usr/lib/systemd/system/graphical.target","mode":33188,"size":598,"sha256":"1365f20442f938a22d38de83d7de37947de190bb1190c87a4808880f76e59820"},{"path":"/usr/lib/systemd/system/graphical.target.wants/systemd-update-utmp-runlevel.service","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/systemd/system/halt-local.service","mode":33188,"size":605,"sha256":"edfc8e2c6d468e464356e4ce41b3c34695ffbfac9eb66836c60322030857fe3f"},{"path":"/usr/lib/systemd/system/halt.target","mode":33188,"size":527,"sha256":"3ba387ceeedfc6e9c1bb6e9ffbc0b2205313255aed815a658b31db2bf3ea2535"},{"path":"/usr/lib/systemd/system/initrd-cleanup.service","mode":33188,"size":674,"sha256":"788ae4a710602947ce2ce35d494195588baf800156793aa60b262eff98ca8dc9"},{"path":"/usr/lib/systemd/system/initrd-fs.target","mode":33188,"size":593,"sha256":"72415aee9209c7e0048124c6f788c255f445bfb175746e466d44c2a86099cbf8"},{"path":"/usr/lib/systemd/system/initrd-parse-etc.service","mode":33188,"size":842,"sha256":"4418bbb5b27ffa67cc8dda12609a4398b5b2353689db6e8a4269096f69de7fde"},{"path":"/usr/lib/systemd/system/initrd-root-device.target","mode":33188,"size":561,"sha256":"7b9983aee2506711736cc3352398e67aa117fe684a743664dab1b3c1cd6bb881"},{"path":"/usr/lib/systemd/system/initrd-root-fs.target","mode":33188,"size":566,"sha256":"8c22f7df97c927b64f6ef52fd7671cacbf15ff1fc5eaa1e7e7dfe09986f7de70"},{"path":"/usr/lib/systemd/system/initrd-switch-root.service","mode":33188,"size":593,"sha256":"e13304808fc5b93fa25517bb634558d939481d58393bbf110b7de359a038c5b7"},{"path":"/usr/lib/systemd/system/initrd-switch-root.target","mode":33188,"size":754,"sha256":"7c93c1380ff261ca759d5dd9a14539bcc6b52f7943aac3a8dfc24df4dce17945"},{"path":"/usr/lib/systemd/system/initrd.target","mode":33188,"size":763,"sha256":"cc9955c31dbf1368401fb766fdd510fab64ea66769e1bf9686d0ca71c29f06e3"},{"path":"/usr/lib/systemd/system/kexec.target","mode":33188,"size":541,"sha256":"b1d579ffe8471ee795e46708fb32f489153c07bb4917f41f73f9db790c212fdc"},{"path":"/usr/lib/systemd/system/ldconfig.service","mode":33188,"size":687,"sha256":"36eb19c4b96269fd6e2ff2c546b1f7074c3cfc0e24ff5b84c57ff1c84913bc8c"},{"path":"/usr/lib/systemd/system/local-fs-pre.target","mode":33188,"size":435,"sha256":"b36765b2105e045e90e400c0b5567a0d868d0060a1391a8e07c6f42d0e50d0db"},{"path":"/usr/lib/systemd/system/local-fs.target","mode":33188,"size":547,"sha256":"4c1126c9a006f29320337913cf0d1e6d108108bbdb1ecbcff984697a09255038"},{"path":"/usr/lib/systemd/system/multi-user.target","mode":33188,"size":532,"sha256":"e57f384474fa52248f912b11cce30dea793db7fa26a6cafea7213716eea18068"},{"path":"/usr/lib/systemd/system/multi-user.target.wants/getty.target","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib/systemd/system/multi-user.target.wants/systemd-ask-password-wall.path","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/systemd/system/multi-user.target.wants/systemd-logind.service","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/multi-user.target.wants/systemd-update-utmp-runlevel.service","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/systemd/system/multi-user.target.wants/systemd-user-sessions.service","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/systemd/system/network-online.target","mode":33188,"size":505,"sha256":"00d64f04ab86d078c0858f6c2d39df25941d0bff06a781adb1b9a519c44f1341"},{"path":"/usr/lib/systemd/system/network-pre.target","mode":33188,"size":502,"sha256":"b67c872776d34433a7fee8ee89c53615617b707424801110c4d5b22ece1884af"},{"path":"/usr/lib/systemd/system/network.target","mode":33188,"size":521,"sha256":"51a62bea8547cd74802c5f394be11196edad8a0f51b1aa0861ba356c781bcdac"},{"path":"/usr/lib/systemd/system/nss-lookup.target","mode":33188,"size":554,"sha256":"dfb73f79a2d30d6575dbcd091f66a6191918b5f19cdc894957763a098485f8b5"},{"path":"/usr/lib/systemd/system/nss-user-lookup.target","mode":33188,"size":513,"sha256":"d1456fe3ecfa3ae9c3e3bcaaf5a46a35f27fd3cda9e529a55000e4cf06425146"},{"path":"/usr/lib/systemd/system/paths.target","mode":33188,"size":394,"sha256":"4f699d02449375f392c61a85ba6f3a016a5784e8571e4897c07cf3011a3a87f1"},{"path":"/usr/lib/systemd/system/poweroff.target","mode":33188,"size":592,"sha256":"4eb6628a68ad5e7f393dcfffe3703dc5489b67138f83d4889e7efd89913e5325"},{"path":"/usr/lib/systemd/system/printer.target","mode":33188,"size":417,"sha256":"d1f01bb0c93148bd0a397d2d075b5a514e9d9ca33040d2e442cda724f9124c7b"},{"path":"/usr/lib/systemd/system/proc-sys-fs-binfmt_misc.automount","mode":33188,"size":745,"sha256":"1d9eff420aecdab1ee7162f2732105e07d8deccf5aa7d1d78ab6194cd7c2324a"},{"path":"/usr/lib/systemd/system/proc-sys-fs-binfmt_misc.mount","mode":33188,"size":655,"sha256":"61df1bf9d7d6980d6b03d2b573ec0c7751582e5df2a77121771c22dfa2bf780b"},{"path":"/usr/lib/systemd/system/rc-local.service","mode":33188,"size":736,"sha256":"79a99e41dff42be50a6736bcac10760f9f01cf80c145af89eaf361d15945ac36"},{"path":"/usr/lib/systemd/system/reboot.target","mode":33188,"size":583,"sha256":"48e25ebb9ef0c1a1a4a369948691d57ee6363bbfe124daadbf41a74e840ce9e5"},{"path":"/usr/lib/systemd/system/remote-fs-pre.target","mode":33188,"size":436,"sha256":"34088b1dc45071c7ca18f32a2c3954213496a99380571f9e8143d9a1fd9aed16"},{"path":"/usr/lib/systemd/system/remote-fs.target","mode":33188,"size":522,"sha256":"973827e5659568134a123af241085373b974f211a466939b4af081ee1317cfa2"},{"path":"/usr/lib/systemd/system/rescue.service","mode":33188,"size":792,"sha256":"ac7bb0fc0897c84198871afe2dc5c9e199cd02bd47701982c28a57ef6e92fae2"},{"path":"/usr/lib/systemd/system/rescue.target","mode":33188,"size":492,"sha256":"832fe8316cb92018636d70f6afc3ae63107064936dc71109b8bbd1ca0a5d2838"},{"path":"/usr/lib/systemd/system/rescue.target.wants/systemd-update-utmp-runlevel.service","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/systemd/system/rpcbind.target","mode":33188,"size":540,"sha256":"388f84fc7df2658eb221c1d076a62beb6c2061b80b061e1e36eb98c717ee3ff7"},{"path":"/usr/lib/systemd/system/runlevel0.target","mode":41471,"size":15,"sha256":""},{"path":"/usr/lib/systemd/system/runlevel1.target","mode":41471,"size":13,"sha256":""},{"path":"/usr/lib/systemd/system/runlevel2.target","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib/systemd/system/runlevel3.target","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib/systemd/system/runlevel4.target","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib/systemd/system/runlevel5.target","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib/systemd/system/runlevel6.target","mode":41471,"size":13,"sha256":""},{"path":"/usr/lib/systemd/system/serial-getty@.service","mode":33188,"size":1486,"sha256":"9505841714b6aee5806828c00211b52cd41a179acb65706dfb269b271a87e8cb"},{"path":"/usr/lib/systemd/system/shutdown.target","mode":33188,"size":442,"sha256":"75979a331adbecdddca10151c270a197187de1e396b9608558e4186dd4eadbdd"},{"path":"/usr/lib/systemd/system/sigpwr.target","mode":33188,"size":402,"sha256":"9e596bde57979d2b8ad1693ef89ebbd69061b522e335526196cd01a555da0bd6"},{"path":"/usr/lib/systemd/system/slices.target","mode":33188,"size":449,"sha256":"db8b99e38e60072fb7495482e4e18afb8804fa0c9bb8572355bc68311c653ece"},{"path":"/usr/lib/systemd/system/smartcard.target","mode":33188,"size":420,"sha256":"2ad5f8dae77603bbed92ea025553d38111c4af29f3a8b8b45a9303b0e4c54d44"},{"path":"/usr/lib/systemd/system/sockets.target","mode":33188,"size":396,"sha256":"f4362dd5140e8e476e88c4c556a595f780eb7b6d51240c2e4e0b838ae33d3b7b"},{"path":"/usr/lib/systemd/system/sockets.target.wants/systemd-coredump.socket","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/systemd/system/sockets.target.wants/systemd-initctl.socket","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/sockets.target.wants/systemd-journald-dev-log.socket","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/systemd/system/sockets.target.wants/systemd-journald.socket","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/systemd/system/sound.target","mode":33188,"size":420,"sha256":"bade0a1f0adec3fdba5c76b2b50b3b251c79a731851ebec592b6850a9710a3a8"},{"path":"/usr/lib/systemd/system/swap.target","mode":33188,"size":393,"sha256":"22f54205370b0595530d31f9b8fe8ccdf2b9aaf2dff9cf5853127ffa0e2c617b"},{"path":"/usr/lib/systemd/system/sys-fs-fuse-connections.mount","mode":33188,"size":795,"sha256":"8c9d956d93025097f5a592dd902b69cddd75e502c09cb3d87338bc7c058874b9"},{"path":"/usr/lib/systemd/system/sys-kernel-config.mount","mode":33188,"size":767,"sha256":"a103db1d19d884d4e1b26da15400da9bcd079739a5e1caaa0a5d9eb127345f20"},{"path":"/usr/lib/systemd/system/sys-kernel-debug.mount","mode":33188,"size":710,"sha256":"275b1616aaa81331c1de603ec3139999419b63651a97397d61b85804694eb2db"},{"path":"/usr/lib/systemd/system/sysinit.target","mode":33188,"size":558,"sha256":"f7526dec8fc845658e8d743c9659f8e37f439913acefa0b6671bb97ad4f41691"},{"path":"/usr/lib/systemd/system/sysinit.target.wants/dev-hugepages.mount","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/dev-mqueue.mount","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/ldconfig.service","mode":41471,"size":19,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/proc-sys-fs-binfmt_misc.automount","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/sys-fs-fuse-connections.mount","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/sys-kernel-config.mount","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/sys-kernel-debug.mount","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-ask-password-console.path","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-binfmt.service","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-firstboot.service","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-journal-catalog-update.service","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-journal-flush.service","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-journald.service","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-machine-id-commit.service","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-sysctl.service","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-sysusers.service","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-tmpfiles-setup.service","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-update-done.service","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-update-utmp.service","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/systemd/system/syslog.socket","mode":33188,"size":1407,"sha256":"ef7dfc4efe363eafa096dc7a327476f1f122b99c789147e908d9a75e8b0fdc8b"},{"path":"/usr/lib/systemd/system/system-update-cleanup.service","mode":33188,"size":1415,"sha256":"b33e93d9bbd59738d2d539f1fb6d973026974fedb2c263329d75d2923ed06788"},{"path":"/usr/lib/systemd/system/system-update-pre.target","mode":33188,"size":543,"sha256":"f66e26f876a730996762c0ef3f95c04a0e43c31e2766a8b8dbfb7cedfcac6d4c"},{"path":"/usr/lib/systemd/system/system-update.target","mode":33188,"size":617,"sha256":"a97ff01de17667f41c487336fc1dd78fcd6d33e667424e4bbcd5d4fab410f262"},{"path":"/usr/lib/systemd/system/systemd-ask-password-console.path","mode":33188,"size":704,"sha256":"5b7fcb0f383aeda6068b3f3a4edca1633983c02b9a25794903986eb5db94ceb2"},{"path":"/usr/lib/systemd/system/systemd-ask-password-console.service","mode":33188,"size":728,"sha256":"97bacb9c16ef16ee0835f66ede1e38a0921b723efe6cee954045741bcf0d1c72"},{"path":"/usr/lib/systemd/system/systemd-ask-password-wall.path","mode":33188,"size":632,"sha256":"3ac6c24c6c0a06e68876f95576d5cd0d66e386de60ae6ad97a4c53324352b286"},{"path":"/usr/lib/systemd/system/systemd-ask-password-wall.service","mode":33188,"size":760,"sha256":"516653a242d074a49e383e50b61fc6e96a61b5e41f6d5d4508e6a667e03eb6bd"},{"path":"/usr/lib/systemd/system/systemd-binfmt.service","mode":33188,"size":1093,"sha256":"9d76a773f37baec117c84de3dce32a3d308216786480f9ffa9030a388806099e"},{"path":"/usr/lib/systemd/system/systemd-coredump.socket","mode":33188,"size":537,"sha256":"f99f6436b837da77625219765d31572a9809126e824d48895eefb3e083c5e42d"},{"path":"/usr/lib/systemd/system/systemd-coredump@.service","mode":33188,"size":1104,"sha256":"ea9611f3107b752900067aaabe2e4c91d13d0a9ff73d7c3b974e366ae4b71bd6"},{"path":"/usr/lib/systemd/system/systemd-exit.service","mode":33188,"size":541,"sha256":"5d63a4e4d4287f747dd1fc0df5f2e18071383defb6619bc1c9c039dca4f36a2e"},{"path":"/usr/lib/systemd/system/systemd-firstboot.service","mode":33188,"size":799,"sha256":"242952c9ecba70f52207276a94c819886a92b3b4daa23a58efafdf7f26a8876b"},{"path":"/usr/lib/systemd/system/systemd-fsck-root.service","mode":33188,"size":618,"sha256":"74d4c2c396cdf31b94bab95238bbb4ba5133f21fc5c3d30f608ba14ed3d0866e"},{"path":"/usr/lib/systemd/system/systemd-fsck@.service","mode":33188,"size":671,"sha256":"c17b8807c3fdcbaff326b45601cd1a078f6434517cc72b686eb8e19de91e285c"},{"path":"/usr/lib/systemd/system/systemd-halt.service","mode":33188,"size":588,"sha256":"9dd9744c3ef2fd3d1a820fc138cab2710a281ff1375387371ccad314b9401d43"},{"path":"/usr/lib/systemd/system/systemd-hostnamed.service","mode":33188,"size":1102,"sha256":"88e790a114ac4eb009211ffe32e433d092872ad6c49378ef1df241cabbada09d"},{"path":"/usr/lib/systemd/system/systemd-initctl.service","mode":33188,"size":550,"sha256":"f91f67210f873979a14eed1876c3212c2944d280d00993a7d3a2bb99ee453380"},{"path":"/usr/lib/systemd/system/systemd-initctl.socket","mode":33188,"size":546,"sha256":"f9c2768d30d48c1fccfd7b3d63e6bdd48c70cc0f6506a2962f38843a7b766fa3"},{"path":"/usr/lib/systemd/system/systemd-journal-catalog-update.service","mode":33188,"size":711,"sha256":"38b5d8f96fdbf1b273465c41cc8d79a34d1e06c207c00f264a98d874d6bfa443"},{"path":"/usr/lib/systemd/system/systemd-journal-flush.service","mode":33188,"size":775,"sha256":"0e71b84bcefa6a262fd9edb6bc4aa3cdb4dcc940816b0a495a37502681c6c984"},{"path":"/usr/lib/systemd/system/systemd-journald-audit.socket","mode":33188,"size":647,"sha256":"eeb49674fe3702c2db92e0800be30815e2a24666d375c70ee7804fd87c13a866"},{"path":"/usr/lib/systemd/system/systemd-journald-dev-log.socket","mode":33188,"size":1130,"sha256":"19e96a3bb9c841df0ba3343877f9b54e847a9b2597cf651e3342d0167a6e5b5f"},{"path":"/usr/lib/systemd/system/systemd-journald.service","mode":33188,"size":1537,"sha256":"215301b24566adf55884688431d1867f79d21e7c7d0aad9033d93ea8088dbf91"},{"path":"/usr/lib/systemd/system/systemd-journald.socket","mode":33188,"size":882,"sha256":"e25372a9939122f28ee10d3384fe23fd948d6344c157e447dfe97c3e0bcd041b"},{"path":"/usr/lib/systemd/system/systemd-kexec.service","mode":33188,"size":601,"sha256":"97b8281382cb424528b806f17167a759277268f28724bac5d653140ba84019c0"},{"path":"/usr/lib/systemd/system/systemd-localed.service","mode":33188,"size":1071,"sha256":"a6fddac70f34abde65d1ef3900a94ab42e42a5cce017e0b451b71f861290090d"},{"path":"/usr/lib/systemd/system/systemd-logind.service","mode":33188,"size":1383,"sha256":"659f4b4714c404264729e5696b55301913b9c4e91919b37d5fb13a398a8a9927"},{"path":"/usr/lib/systemd/system/systemd-machine-id-commit.service","mode":33188,"size":737,"sha256":"ae5ee3759d7a8164b1747f4cf02587417e1109cf73f1cfab98e0d776113dd3f5"},{"path":"/usr/lib/systemd/system/systemd-portabled.service","mode":33188,"size":987,"sha256":"2cac2a419e27e92d747d413d31866eff12a6cf260cee43b048f83bc126c29831"},{"path":"/usr/lib/systemd/system/systemd-poweroff.service","mode":33188,"size":597,"sha256":"b86e8b94442160791c56ebdb311b4bdd55c37d26ca912f73651a2bf9d1956771"},{"path":"/usr/lib/systemd/system/systemd-reboot.service","mode":33188,"size":592,"sha256":"1b900ec8a72b79d5d31e605d455f7199355838bd36dc841ec08cd1b7d385c5eb"},{"path":"/usr/lib/systemd/system/systemd-resolved.service","mode":33188,"size":1632,"sha256":"0577e61ab8c8253b3695f034a0fc0c60e89bfa38c8d79551a848ebeb882ea859"},{"path":"/usr/lib/systemd/system/systemd-sysctl.service","mode":33188,"size":697,"sha256":"9de1bdb24c46e27aeb148f97bdbfb85661c8cacddc8a249b392ef08379a27487"},{"path":"/usr/lib/systemd/system/systemd-sysusers.service","mode":33188,"size":704,"sha256":"d0fe442b6fc529311021d01ce93db513494ce5cd8e77a4bf4df2f76a0e7bbca1"},{"path":"/usr/lib/systemd/system/systemd-timedated.service","mode":33188,"size":1042,"sha256":"adbc9dfc1054e2c60fe2336374e469dfc0ffb7a920c144a8e70d547000227f43"},{"path":"/usr/lib/systemd/system/systemd-tmpfiles-clean.service","mode":33188,"size":663,"sha256":"933c6d6d51f679ff34a88a9e76adcb029475db210291782fd5d2a1bbc34aab9f"},{"path":"/usr/lib/systemd/system/systemd-tmpfiles-clean.timer","mode":33188,"size":490,"sha256":"7acece4969ecf8e1d7c9ff022fc1b2f9340b9e88f387dab9d8f007b38224b280"},{"path":"/usr/lib/systemd/system/systemd-tmpfiles-setup.service","mode":33188,"size":751,"sha256":"56e0d34c07b4a014cb298483cbe37bd624aacd602377ea0e56f27edd97d1f783"},{"path":"/usr/lib/systemd/system/systemd-update-done.service","mode":33188,"size":674,"sha256":"189e670826c89de0efff4e560e2c8fd0f53d727ad0e21b89ffeafbfc313d8dc0"},{"path":"/usr/lib/systemd/system/systemd-update-utmp-runlevel.service","mode":33188,"size":801,"sha256":"0de8362695352cb86db387517c9e77b061efaab8c365fdfa8ed1a7911820d82a"},{"path":"/usr/lib/systemd/system/systemd-update-utmp.service","mode":33188,"size":802,"sha256":"9b2f746cb2a5ed40e8f4b514b5e2bca7fa2e3c864cb20e94b15a0f63e1531061"},{"path":"/usr/lib/systemd/system/systemd-user-sessions.service","mode":33188,"size":636,"sha256":"2b3895d0ba5cb485ea54275606948a725c76b5899d985b7502d0b8234264bdaf"},{"path":"/usr/lib/systemd/system/systemd-volatile-root.service","mode":33188,"size":694,"sha256":"d1173d5bf10f31ba84ce5e24eb731d1618426d70a1971b9ed85be7a26ed9aa30"},{"path":"/usr/lib/systemd/system/time-sync.target","mode":33188,"size":435,"sha256":"f863f602a84d5a90e137a3baf78701c8708cb7ea4722c046cebe366739c83e9e"},{"path":"/usr/lib/systemd/system/timers.target","mode":33188,"size":445,"sha256":"62be3bb5b62f2f89c5c34000381bcaf6d0852c2707a1e9749439a7ab7bd2f27b"},{"path":"/usr/lib/systemd/system/timers.target.wants/systemd-tmpfiles-clean.timer","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/systemd/system/tmp.mount","mode":33188,"size":782,"sha256":"3b10e252821630155d037d6188543a12ef4c163492b80cdccb4a1a3147a068a5"},{"path":"/usr/lib/systemd/system/umount.target","mode":33188,"size":457,"sha256":"58a67857d05529e62965bdca1f52b425d28c0ef97b94922acef0cce5d9c25af6"},{"path":"/usr/lib/systemd/system/user-.slice.d/10-defaults.conf","mode":33188,"size":430,"sha256":"91d97c13e362b10876c54fb5bd1bf53886a9698f6845a54d9d751414d89ecf1d"},{"path":"/usr/lib/systemd/system/user-runtime-dir@.service","mode":33188,"size":551,"sha256":"1b4504e989c24dbf2dc6830e1a6131aeb95b3e55196f29895ada67d7c046240f"},{"path":"/usr/lib/systemd/system/user.slice","mode":33188,"size":432,"sha256":"b68a1743e480b7d5d2eedba7231b5f675bca587558760f04e23b4e3003eef26b"},{"path":"/usr/lib/systemd/system/user@.service","mode":33188,"size":671,"sha256":"be3ece47e5ae33d73b92add4a193dae74dc7510ff4b7823da71647721aa11c26"},{"path":"/usr/lib/systemd/systemd","mode":33261,"size":1559672,"sha256":"8e03dd9cd427f02abb7e65a00d8442296b14c80e935d4e10a0d94dd8c136bdc3"},{"path":"/usr/lib/systemd/systemd-ac-power","mode":33261,"size":12320,"sha256":"18af6e492d86edd92cca896efb0467fc3150b1d9f4354b1be95643774491defa"},{"path":"/usr/lib/systemd/systemd-binfmt","mode":33261,"size":16632,"sha256":"ed5a6a4c6f94433c5f56da64395e1dcf8658ce9db7676815e05bc041725ef03e"},{"path":"/usr/lib/systemd/systemd-cgroups-agent","mode":33261,"size":12504,"sha256":"53899ab34093eb34852af433d5091e0140d1f2f3a32499a09609f7c9548799d8"},{"path":"/usr/lib/systemd/systemd-coredump","mode":33261,"size":62488,"sha256":"88b1351532622cbab2882a402267aa8ae7d220c5d12c14b645046e6b7bf93419"},{"path":"/usr/lib/systemd/systemd-dissect","mode":33261,"size":16608,"sha256":"b7fd30384aa13933bb541d0ba0fe3eef52ec4c3565b661e3542b125d7df36234"},{"path":"/usr/lib/systemd/systemd-export","mode":33261,"size":42032,"sha256":"9b792a48463eee74ff6ba9f20feab831896d1c5ff30ac5a8363794c727101681"},{"path":"/usr/lib/systemd/systemd-fsck","mode":33261,"size":25192,"sha256":"1f8868572a618863b65153923d1aaa356dad6910b90b96f12ea3acaf0f129a1c"},{"path":"/usr/lib/systemd/systemd-hostnamed","mode":33261,"size":29456,"sha256":"6964cefbac08d6b175fd464c97eedb04e9564ed275c321a2c4d438b9eba26797"},{"path":"/usr/lib/systemd/systemd-initctl","mode":33261,"size":21096,"sha256":"197c9e67e0be09efefbb574ba11bd3903174920077d91064a9ed6164fbbb1b9e"},{"path":"/usr/lib/systemd/systemd-journald","mode":33261,"size":153912,"sha256":"20574ca732cea97d63bb814723de39c4b191e46c3f9a0c699ea6354aced952d4"},{"path":"/usr/lib/systemd/systemd-localed","mode":33261,"size":46128,"sha256":"1debd004277af8c5feefab361342e582ec72c5b6a92de827c6fb0623f42a77bd"},{"path":"/usr/lib/systemd/systemd-logind","mode":33261,"size":250944,"sha256":"67984cea4bd907759388f892d8a113c944fd84fee9bdf2250171ebf0f3c388be"},{"path":"/usr/lib/systemd/systemd-portabled","mode":33261,"size":87840,"sha256":"147fb7cc49c91e77a792dfae144838dafffbc457042e0a197f81501e07956dd8"},{"path":"/usr/lib/systemd/systemd-reply-password","mode":33261,"size":12512,"sha256":"cd72bdc293e629361090e0acae1e0cb3d6f2b2fd02f7d9cfa86fce5ae6bf8fdf"},{"path":"/usr/lib/systemd/systemd-resolved","mode":33261,"size":455600,"sha256":"5c206b920654d29f465e520ed5f0547cd5ce5e9613ab0356ddd353632f28d544"},{"path":"/usr/lib/systemd/systemd-shutdown","mode":33261,"size":62504,"sha256":"df0f45934d0599e12889b78bd1db16560490ccfc2ae7758514d1d33fcc8d4c03"},{"path":"/usr/lib/systemd/systemd-socket-proxyd","mode":33261,"size":25304,"sha256":"68780154e826ed348e8704a78407580fed72979b60ae0117f889648755a02bcb"},{"path":"/usr/lib/systemd/systemd-sulogin-shell","mode":33261,"size":12512,"sha256":"9630f10376ff6e842e34c34924403be3039d6877547855d200c7ad7e985e797b"},{"path":"/usr/lib/systemd/systemd-sysctl","mode":33261,"size":16640,"sha256":"989642be3a632fd3411d00725546ed3c7478a32d2e703b0bbdab549f6898ee74"},{"path":"/usr/lib/systemd/systemd-timedated","mode":33261,"size":37712,"sha256":"90f6e8df03904dfd279602910d50746d52aa9ca1dad2965ac41fc5952296fd29"},{"path":"/usr/lib/systemd/systemd-update-done","mode":33261,"size":12864,"sha256":"3e23800b50a69825131248d64b4c35edb8ea8fd39e61132635c11286b745ccc9"},{"path":"/usr/lib/systemd/systemd-update-utmp","mode":33261,"size":16608,"sha256":"b77a1df847b9c492af06aef47ed82a54c646d6abbbc2dc82f3602f7e5b830279"},{"path":"/usr/lib/systemd/systemd-user-runtime-dir","mode":33261,"size":230264,"sha256":"c9f80acbea1dc353339775c3a989461395d5532f1f8a80c957a851e35d8b23b5"},{"path":"/usr/lib/systemd/systemd-user-sessions","mode":33261,"size":12312,"sha256":"3b50605adf3f8b315652ab307efe2f1d414f57371c5956e49dbb5dd33b823c27"},{"path":"/usr/lib/systemd/systemd-veritysetup","mode":33261,"size":12504,"sha256":"ec513a12fdb9ef18664f5f9b54259509195f1c405f73fc281b4b746a6d4b0468"},{"path":"/usr/lib/systemd/systemd-volatile-root","mode":33261,"size":12512,"sha256":"072124016544d165bcf469834a4d7eae624dcc32ffb752d15174500a429fb1f7"},{"path":"/usr/lib/systemd/user-environment-generators/30-systemd-environment-d-generator","mode":33261,"size":12528,"sha256":"9c812e76ee392e7abeac4d515c8c7019b856723dd30ceaeecb53603b3b2d5b0a"},{"path":"/usr/lib/systemd/user-preset/90-systemd.preset","mode":33188,"size":513,"sha256":"c279d3a049b6d26aab8838dc0b9da2c72f39470044e65592dba0615c7b26ddd5"},{"path":"/usr/lib/systemd/user/basic.target","mode":33188,"size":497,"sha256":"c8b9a76e1f28581d40d2a443fce804b493e3d60f619dc16e8edf6dd71d684c1e"},{"path":"/usr/lib/systemd/user/bluetooth.target","mode":33188,"size":419,"sha256":"146797e480e9493163bff8f4df445279b49c30530054948d0da88eb1dafbaaf7"},{"path":"/usr/lib/systemd/user/default.target","mode":33188,"size":454,"sha256":"22ce53f9bb4390e4e5e5b0c3d4e82c13eed8168da2d4d2bb62c65b1b5493493e"},{"path":"/usr/lib/systemd/user/exit.target","mode":33188,"size":502,"sha256":"ca26638ba3227bff746e9d58c68d77eb4efd904ddc76ecc98dd0de397c860825"},{"path":"/usr/lib/systemd/user/graphical-session-pre.target","mode":33188,"size":568,"sha256":"b4b3a15f32d9de7391f001bf5813c0f0dbd9bdee9bd3c2273e572972c2fbe5fa"},{"path":"/usr/lib/systemd/user/graphical-session.target","mode":33188,"size":484,"sha256":"1fef42486250c523257387fafbdc0f30126c75a7f9d9dbd7a89a79e328239a18"},{"path":"/usr/lib/systemd/user/paths.target","mode":33188,"size":394,"sha256":"4f699d02449375f392c61a85ba6f3a016a5784e8571e4897c07cf3011a3a87f1"},{"path":"/usr/lib/systemd/user/printer.target","mode":33188,"size":417,"sha256":"d1f01bb0c93148bd0a397d2d075b5a514e9d9ca33040d2e442cda724f9124c7b"},{"path":"/usr/lib/systemd/user/shutdown.target","mode":33188,"size":442,"sha256":"75979a331adbecdddca10151c270a197187de1e396b9608558e4186dd4eadbdd"},{"path":"/usr/lib/systemd/user/smartcard.target","mode":33188,"size":420,"sha256":"2ad5f8dae77603bbed92ea025553d38111c4af29f3a8b8b45a9303b0e4c54d44"},{"path":"/usr/lib/systemd/user/sockets.target","mode":33188,"size":396,"sha256":"f4362dd5140e8e476e88c4c556a595f780eb7b6d51240c2e4e0b838ae33d3b7b"},{"path":"/usr/lib/systemd/user/sound.target","mode":33188,"size":420,"sha256":"bade0a1f0adec3fdba5c76b2b50b3b251c79a731851ebec592b6850a9710a3a8"},{"path":"/usr/lib/systemd/user/systemd-exit.service","mode":33188,"size":548,"sha256":"ff44dc1047b4c11b23076de841c8cd3dd1300f2c62e919170d78adb03faa6ec1"},{"path":"/usr/lib/systemd/user/systemd-tmpfiles-clean.service","mode":33188,"size":661,"sha256":"b05000646dee7a3974cbad2f8d0d94cf40440d27ef3f891d329795f36c1563f2"},{"path":"/usr/lib/systemd/user/systemd-tmpfiles-clean.timer","mode":33188,"size":533,"sha256":"261ee4679bc17b5ada1fdabafb47bdac85fa5def307e1ca38b50b25f65b38c87"},{"path":"/usr/lib/systemd/user/systemd-tmpfiles-setup.service","mode":33188,"size":724,"sha256":"ef18b6f3cda42ab906eea155f6f7f3445afb9773e864424686a563eaed351187"},{"path":"/usr/lib/systemd/user/timers.target","mode":33188,"size":445,"sha256":"62be3bb5b62f2f89c5c34000381bcaf6d0852c2707a1e9749439a7ab7bd2f27b"},{"path":"/usr/lib/sysusers.d/basic.conf","mode":33188,"size":1138,"sha256":"78c4d8cad685876304839a10cc62555ba91acd6f55f5872195e534f605e86c90"},{"path":"/usr/lib/sysusers.d/systemd.conf","mode":33188,"size":360,"sha256":"e828ac3ce0116c45b546e18630702992c5a2f8f2f8578eb4615736c73093e61f"},{"path":"/usr/lib/tmpfiles.d/etc.conf","mode":33188,"size":515,"sha256":"7f4b7b20e6e522a1345735854b32d9b96af21c0be4c45442d194e4a71dd0d33a"},{"path":"/usr/lib/tmpfiles.d/home.conf","mode":33188,"size":362,"sha256":"135d4d63b7a841a921f5c2ddc0c2c38b72286070097883196bd58375bd1674e2"},{"path":"/usr/lib/tmpfiles.d/journal-nocow.conf","mode":33188,"size":1096,"sha256":"c53a809900502c8cce9a2dd1a37318aad2a3988592c4493f2c0c2bfd49c2b656"},{"path":"/usr/lib/tmpfiles.d/legacy.conf","mode":33188,"size":841,"sha256":"65e88a322e23dea7937e9d436a6988b0244764b63648c152c62e2308e5e1c0ac"},{"path":"/usr/lib/tmpfiles.d/portables.conf","mode":33188,"size":96,"sha256":"c88363428b9c406eb2be1983ddf455180d13f9a76190b47cd5674b4eedc79157"},{"path":"/usr/lib/tmpfiles.d/systemd-nologin.conf","mode":33188,"size":596,"sha256":"922494a4a3b0fc2fb3e3d22eeb23255258a27ed38e48cc42a11af80f5ec2f5b8"},{"path":"/usr/lib/tmpfiles.d/systemd.conf","mode":33188,"size":1676,"sha256":"359727425de169e5dc857207629c838857172b7181ab385b003d86aac2b6243d"},{"path":"/usr/lib/tmpfiles.d/tmp.conf","mode":33188,"size":757,"sha256":"450881ccdc4835a895f643be397d9eeb8bf49da25146f6fab8c3e5e1cbe2f256"},{"path":"/usr/lib/tmpfiles.d/var.conf","mode":33188,"size":568,"sha256":"285585556332d5f014914358d1053d8af48617e01eccab9c49666e14459e6306"},{"path":"/usr/lib/tmpfiles.d/x11.conf","mode":33188,"size":655,"sha256":"fbd4bbec65eafdd27eea4725c1254cd2955285f2d441238f18451e9c285b72ab"},{"path":"/usr/sbin/halt","mode":41471,"size":16,"sha256":""},{"path":"/usr/sbin/init","mode":41471,"size":22,"sha256":""},{"path":"/usr/sbin/poweroff","mode":41471,"size":16,"sha256":""},{"path":"/usr/sbin/reboot","mode":41471,"size":16,"sha256":""},{"path":"/usr/sbin/resolvconf","mode":41471,"size":17,"sha256":""},{"path":"/usr/sbin/runlevel","mode":41471,"size":16,"sha256":""},{"path":"/usr/sbin/shutdown","mode":41471,"size":16,"sha256":""},{"path":"/usr/sbin/telinit","mode":41471,"size":16,"sha256":""},{"path":"/usr/share/bash-completion/completions/busctl","mode":33188,"size":8015,"sha256":"cd516ef4d2bf46f8b63829b840de99f26cadb26488cf140d7407565b8bcfde47"},{"path":"/usr/share/bash-completion/completions/coredumpctl","mode":33188,"size":3715,"sha256":"a4858c055334462cc53386dc21a2ca14bafdd057f0882273146c33f190207e32"},{"path":"/usr/share/bash-completion/completions/hostnamectl","mode":33188,"size":2281,"sha256":"b341f8d15c5e9d293ebe2e293c99ecf68c0780d238a76de775e10386d09d6051"},{"path":"/usr/share/bash-completion/completions/journalctl","mode":33188,"size":5892,"sha256":"bd2569e8f1b21ee12d320b283f95781bd98de321438cb619c0f7abcf4005ac11"},{"path":"/usr/share/bash-completion/completions/localectl","mode":33188,"size":3739,"sha256":"29dd0be803ef31a41ac114b510d4b25d17c7a5064611c647963b502d2a3776be"},{"path":"/usr/share/bash-completion/completions/loginctl","mode":33188,"size":4251,"sha256":"fe50347975deb0574578d3c354fc3f18d260d9affe87750000476ff84b1150a6"},{"path":"/usr/share/bash-completion/completions/portablectl","mode":33188,"size":3986,"sha256":"6d9a8e7c526adb3b675c914814e26ad4be0f1cb1240071090ec370c68f6d9aec"},{"path":"/usr/share/bash-completion/completions/resolvectl","mode":33188,"size":7066,"sha256":"335b564abd249a2dbbc4af43be328f8628cc443a718a112c5b5a700813948e73"},{"path":"/usr/share/bash-completion/completions/systemctl","mode":33188,"size":13456,"sha256":"974f79b35044c3c8bd0e55981c14463d7dd318c11c8c5fdf1e8a6a2b8c5db803"},{"path":"/usr/share/bash-completion/completions/systemd-analyze","mode":33188,"size":6788,"sha256":"d7701026ba2baa8ecdc4554fc6452990e018a824da7c429529e444160894a0d7"},{"path":"/usr/share/bash-completion/completions/systemd-cat","mode":33188,"size":1911,"sha256":"d1818b640140ffe4709e2269c271eb876a7c6487df738a56d4decd3ad477d7eb"},{"path":"/usr/share/bash-completion/completions/systemd-cgls","mode":33188,"size":2344,"sha256":"c87cbc9016e3cb8b619b155fd59368892cbfe0fb0a85f2463e66665a60d255ea"},{"path":"/usr/share/bash-completion/completions/systemd-cgtop","mode":33188,"size":2096,"sha256":"095eff0ee4d512aee9cc2300923d0cdb26c0201ac9ad8293c3264a311421395b"},{"path":"/usr/share/bash-completion/completions/systemd-delta","mode":33188,"size":1951,"sha256":"ca07a28f1a01f1dbb926dc5e713b9e7f5e6c6fa53fbe2f6a2c6df53d37123b0c"},{"path":"/usr/share/bash-completion/completions/systemd-detect-virt","mode":33188,"size":1361,"sha256":"a5346fed4a895eac394d17c5bf4b2f5291008af3258552f7d5ebab6cd2fb0755"},{"path":"/usr/share/bash-completion/completions/systemd-path","mode":33188,"size":1901,"sha256":"ef8bdf909c85b884672cf1d090781e4da3d5ec4e9836e41c757b0f0485e999a3"},{"path":"/usr/share/bash-completion/completions/systemd-resolve","mode":33188,"size":3189,"sha256":"7d5ebfe15aecc179330011370f1cadff9dee48f5f694aec6346cc44db1cfa989"},{"path":"/usr/share/bash-completion/completions/systemd-run","mode":33188,"size":4869,"sha256":"7b9564f51fc08ec3ba46dd9853269c0308275f7d7ebbde8ceedfb4dfe62a582a"},{"path":"/usr/share/bash-completion/completions/timedatectl","mode":33188,"size":2984,"sha256":"66fff48537803a46c6eddc007d1ffa5fc98bf75ef3801ac6f55a7f72dc7e90ce"},{"path":"/usr/share/dbus-1/services/org.freedesktop.systemd1.service","mode":41471,"size":51,"sha256":""},{"path":"/usr/share/dbus-1/system-services/org.freedesktop.hostname1.service","mode":33188,"size":424,"sha256":"9c3d7752da25a7b03e3a7b12d268116cf78d09f9ba77072198f70fe970f1f112"},{"path":"/usr/share/dbus-1/system-services/org.freedesktop.locale1.service","mode":33188,"size":455,"sha256":"5514402b3ecb006a365ae9a643873d06a4e6e3b8120e0a62781e99a42aa9a0b4"},{"path":"/usr/share/dbus-1/system-services/org.freedesktop.login1.service","mode":33188,"size":453,"sha256":"b7045bf9eb1f6887f1edefc1b27e8bfe252d0794479a9c3d333cf40356bb2eb9"},{"path":"/usr/share/dbus-1/system-services/org.freedesktop.portable1.service","mode":33188,"size":165,"sha256":"c5f3c9e9261eb05131fece487dbbfdbf590fa9797a5ea90024259f4689e0b45f"},{"path":"/usr/share/dbus-1/system-services/org.freedesktop.resolve1.service","mode":33188,"size":457,"sha256":"5278c12d256d55c762d79c7d60d2f672e6612cecc9babd994acfe7bc55d1eb1b"},{"path":"/usr/share/dbus-1/system-services/org.freedesktop.systemd1.service","mode":33188,"size":404,"sha256":"37a68d852e39114b9691001fc91c9db098e506e077a324329c46159020ab3f39"},{"path":"/usr/share/dbus-1/system-services/org.freedesktop.timedate1.service","mode":33188,"size":459,"sha256":"b35ec4d91382655caad10cee4309b848e1ab6062b18558e7f2e5f5b868830459"},{"path":"/usr/share/dbus-1/system.d/org.freedesktop.hostname1.conf","mode":33188,"size":985,"sha256":"d0d00f7a7d92133c7e3a12d2397a8a460730630b015aa2b37331834e3c73ed08"},{"path":"/usr/share/dbus-1/system.d/org.freedesktop.locale1.conf","mode":33188,"size":975,"sha256":"f4520acc3be8066d1505d1c45cdf3a469f695bc7a12e50ba35c3e2bc2125cb08"},{"path":"/usr/share/dbus-1/system.d/org.freedesktop.login1.conf","mode":33188,"size":13299,"sha256":"f50377cead43623f8dc64f7056f2211db4db33e73657fef4300bf386633812b2"},{"path":"/usr/share/dbus-1/system.d/org.freedesktop.portable1.conf","mode":33188,"size":5153,"sha256":"c7637fad7c1fd19317deba97ae60a4521624a543b432807472f028c4d6d64933"},{"path":"/usr/share/dbus-1/system.d/org.freedesktop.resolve1.conf","mode":33188,"size":953,"sha256":"b20cfd5f3de6a4f65b184a04e5dce4525075eeb609b1806ce8bde5d0f55cdb09"},{"path":"/usr/share/dbus-1/system.d/org.freedesktop.systemd1.conf","mode":33188,"size":18807,"sha256":"6e1b2d3569818cf4cd164568388b5d9502f2fa5b4d2d558ce11325b0b47c42b3"},{"path":"/usr/share/dbus-1/system.d/org.freedesktop.timedate1.conf","mode":33188,"size":985,"sha256":"68313a0b0f119cd79d59d65726bf0e317a5fee43322afe4debcddcff3a92d986"},{"path":"/usr/share/factory/etc/nsswitch.conf","mode":33188,"size":119,"sha256":"d286ca1d2cf43cc031fedef889572e49a1c53e61e7fe96d0e24b6d548b8f10ee"},{"path":"/usr/share/factory/etc/pam.d/other","mode":33188,"size":149,"sha256":"73fa71815a900524c896d5594639f28d24e9f2ec987d2a7a6fde3989a6c94148"},{"path":"/usr/share/factory/etc/pam.d/system-auth","mode":33188,"size":340,"sha256":"dd9a25cbcb3724a7872dbffc225d1995268389088d075539d80ca6fb420f2368"},{"path":"/usr/share/licenses/systemd/LICENSE.GPL2","mode":33188,"size":17987,"sha256":"ab15fd526bd8dd18a9e77ebc139656bf4d33e97fc7238cd11bf60e2b9b8666c6"},{"path":"/usr/share/licenses/systemd/LICENSE.LGPL2.1","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"},{"path":"/usr/share/pkgconfig/systemd.pc","mode":33188,"size":1706,"sha256":"c03ab744b4c3de5d262d6471372491c5ca61bb0671a27354d322d8682f9b9cf4"},{"path":"/usr/share/pkgconfig/udev.pc","mode":33188,"size":65,"sha256":"90d37b745587e1d76e83bb6d1b960e6cce665918027a1d4c9fe1382297fe506a"},{"path":"/usr/share/polkit-1/actions/org.freedesktop.hostname1.policy","mode":33188,"size":2541,"sha256":"15ff3d0f23ca80849dac6a69b41ec3917579642797c973bba282664b25003949"},{"path":"/usr/share/polkit-1/actions/org.freedesktop.locale1.policy","mode":33188,"size":1923,"sha256":"fe59aca9b10e8d9d46c5200748996c50dfaf31f87804c6f6e86fd09821563d19"},{"path":"/usr/share/polkit-1/actions/org.freedesktop.login1.policy","mode":33188,"size":21681,"sha256":"e6dbb8b23ae343c66b5b1d9e3a186c8af247d12e45da2959c3039337e430f247"},{"path":"/usr/share/polkit-1/actions/org.freedesktop.portable1.policy","mode":33188,"size":2246,"sha256":"85e729da4f5cbcf77dbc24b9e7e69cf71e64339fbfb1d43293eae567b7a9ec5b"},{"path":"/usr/share/polkit-1/actions/org.freedesktop.resolve1.policy","mode":33188,"size":7765,"sha256":"97811de8298c9bca4b4da100e7541d14a794cdd72862a1939d00353f67735b2f"},{"path":"/usr/share/polkit-1/actions/org.freedesktop.systemd1.policy","mode":33188,"size":3823,"sha256":"b90a48db31839a1e939c7bbe5922b3af41a1aabbe3d8fb0bcc7b78d526f09846"},{"path":"/usr/share/polkit-1/actions/org.freedesktop.timedate1.policy","mode":33188,"size":3125,"sha256":"2a6bd7c61a16ef4c949ab5fdf05b1372f602003f83e50dc9bd73ef805c8888ac"},{"path":"/usr/share/systemd/kbd-model-map","mode":33188,"size":3564,"sha256":"6894385e86b4bce5d60d262688d657548192069df8546e70fb032a02e025c094"},{"path":"/usr/share/systemd/language-fallback-map","mode":33188,"size":218,"sha256":"df256be45479f419f5671ad5fd99a647017f31a6319b670c72fc2660d5f78c9d"},{"path":"/usr/share/zsh/site-functions/_busctl","mode":33188,"size":3057,"sha256":"4665180a06392af82a3295a6f27157e769f4df1e0a8e58287aa9c2a1b8cd2698"},{"path":"/usr/share/zsh/site-functions/_coredumpctl","mode":33188,"size":1582,"sha256":"26b48b7782553c8f1db818c5e49e4f3dc8a61efa2e2ea0097e4a0984ad7cfeb2"},{"path":"/usr/share/zsh/site-functions/_hostnamectl","mode":33188,"size":2270,"sha256":"93d2e9754bd27af30fb2c58d4fde48dc65181539bc29e92688f2b445ae76e6b6"},{"path":"/usr/share/zsh/site-functions/_journalctl","mode":33188,"size":5975,"sha256":"ba1a9fa9b41bc07f9bfa782ec8422e3d5c6454b0d6960d1eb31b1c9b884c95df"},{"path":"/usr/share/zsh/site-functions/_localectl","mode":33188,"size":3585,"sha256":"01d8288104d03243107c33dd4b96e8467237021cf8bbaa82d282ee869fb55b7e"},{"path":"/usr/share/zsh/site-functions/_loginctl","mode":33188,"size":5804,"sha256":"809e6504b37171c5d02ee54b000199382d8b005f3c00abc31f9d7984d199e054"},{"path":"/usr/share/zsh/site-functions/_sd_hosts_or_user_at_host","mode":33188,"size":116,"sha256":"682ab3401aef40f32bcab567ee9806b8ec89fa6e1a188a56959c00398af07d9c"},{"path":"/usr/share/zsh/site-functions/_sd_machines","mode":33188,"size":355,"sha256":"04ea5ebda956096e6d871b1cdd1c34ad5e78e77179ebeee0f6e28f758c1f24b4"},{"path":"/usr/share/zsh/site-functions/_sd_outputmodes","mode":33188,"size":289,"sha256":"ad4875ecc149ba84f43e08bc1a3c701b3744b564e195c1cd44fd6ee10bc1538b"},{"path":"/usr/share/zsh/site-functions/_sd_unit_files","mode":33188,"size":255,"sha256":"5c8a298c899d264746794244edd83334a5c3fb7f18e34ac6202ea39f14dee9ea"},{"path":"/usr/share/zsh/site-functions/_systemctl","mode":33188,"size":15404,"sha256":"4a150bc7568450f4b12f7aa58c0e50ead2ad2599f41caa42cc7a542740d3ee25"},{"path":"/usr/share/zsh/site-functions/_systemd","mode":33188,"size":3839,"sha256":"c388d87578f3be915d6591f7ee920ab7896bf5507d7357d5f705bf869c8c06a4"},{"path":"/usr/share/zsh/site-functions/_systemd-analyze","mode":33188,"size":3065,"sha256":"3049412ebb9b846ba51aa87c2c816fa65f37056b8d63b03d4f7084eeb257ec75"},{"path":"/usr/share/zsh/site-functions/_systemd-delta","mode":33188,"size":564,"sha256":"e2ea6c00e54519c36cfd44acab78125323e2b0355633f218db85bffb46cbcf36"},{"path":"/usr/share/zsh/site-functions/_systemd-inhibit","mode":33188,"size":1061,"sha256":"dfbec214825717b88557af0d9ffb3c18fb20d7c9010bd1d2ec8559211db8f7cf"},{"path":"/usr/share/zsh/site-functions/_systemd-resolve","mode":33188,"size":2330,"sha256":"1c8fec53bc50988c40b054277d536acb9ec1c6b632b0908a8ab433ee948c8695"},{"path":"/usr/share/zsh/site-functions/_systemd-run","mode":33188,"size":3136,"sha256":"fc930de2b2ceddd44fd42713cb9a9c3a9c35de712245b36046908344873a60ef"},{"path":"/usr/share/zsh/site-functions/_systemd-tmpfiles","mode":33188,"size":736,"sha256":"775980852687224585d9dc054eef4069c031c68d3a9886b966c4b07091a34fcb"},{"path":"/usr/share/zsh/site-functions/_timedatectl","mode":33188,"size":2042,"sha256":"9b0d1c4e9483e560a09dcd44fdeefe265890a23ea17ba2e12c64b2379bb1e95a"},{"path":"/var/lib/systemd/catalog/database","mode":33188,"size":0,"sha256":""},{"path":"/var/log/btmp","mode":33152,"size":0,"sha256":""},{"path":"/var/log/wtmp","mode":33204,"size":0,"sha256":""}]}},{"name":"systemd-libs","version":"239-30.el8_2","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:systemd-libs:systemd-libs:239-30.el8_2:*:*:*:*:*:*:*","cpe:2.3:a:*:systemd-libs:239-30.el8_2:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/systemd-libs@0:239-30.el8_2?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"systemd-libs","version":"239","epoch":0,"architecture":"x86_64","release":"30.el8_2","sourceRpm":"systemd-239-30.el8_2.src.rpm","size":4497918,"license":"LGPLv2+ and MIT","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/0c/fd4a5ffe0710162ee03537f5e68b8d07f2cd58","mode":41471,"size":44,"sha256":""},{"path":"/usr/lib/.build-id/7b/47e2c31332c8e2647ada2ce71347b344362c5c","mode":41471,"size":39,"sha256":""},{"path":"/usr/lib/.build-id/82/bdd19f76436533bd13001e054b4709d49edfb7","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/99/cec779f5a2920526b4040dba6e35906c2c2ebf","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/f6/55ec87d1c6127fa81176fc38393b99b81e9c91","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib64/libnss_myhostname.so.2","mode":33261,"size":678656,"sha256":"bb114843aeb938ce96e54b61b23047b3361a6ef006621443aac419df8afa2e1c"},{"path":"/usr/lib64/libnss_resolve.so.2","mode":33261,"size":902464,"sha256":"7be8712274ad51716abacd912a6ca2871ce7430e36d311687d2fcc7f8ae09459"},{"path":"/usr/lib64/libnss_systemd.so.2","mode":33261,"size":906648,"sha256":"eeb617507d350993db4d060b0a138f4c2da685bf9f9c0270d1508b102e123141"},{"path":"/usr/lib64/libsystemd.so.0","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib64/libsystemd.so.0.23.0","mode":33261,"size":1354792,"sha256":"7eee984c41184a878e1ae580e4156632829d3658e74ce28970fb24006f4170fb"},{"path":"/usr/lib64/libudev.so.1","mode":41471,"size":17,"sha256":""},{"path":"/usr/lib64/libudev.so.1.6.11","mode":33261,"size":628696,"sha256":"d7a36b650f263d80072ced920489f73e0b4695479c5242c86e44488e6d3f94a1"},{"path":"/usr/share/licenses/systemd/LICENSE.LGPL2.1","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"}]}},{"name":"systemd-pam","version":"239-30.el8_2","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:systemd-pam:systemd-pam:239-30.el8_2:*:*:*:*:*:*:*","cpe:2.3:a:*:systemd-pam:239-30.el8_2:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/systemd-pam@0:239-30.el8_2?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"systemd-pam","version":"239","epoch":0,"architecture":"x86_64","release":"30.el8_2","sourceRpm":"systemd-239-30.el8_2.src.rpm","size":902496,"license":"LGPLv2+ and MIT and GPLv2+","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/83/e454ae4b6a0d22f3204c7d93730de67db19b2d","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib64/security/pam_systemd.so","mode":33261,"size":902496,"sha256":"1f9eabdb613ecc6d7618a1bbaea37d47ed55edb68430d0b1bcf808e3a859c7bc"}]}},{"name":"systemd-udev","version":"239-30.el8_2","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:systemd-udev:systemd-udev:239-30.el8_2:*:*:*:*:*:*:*","cpe:2.3:a:*:systemd-udev:239-30.el8_2:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/systemd-udev@0:239-30.el8_2?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"systemd-udev","version":"239","epoch":0,"architecture":"x86_64","release":"30.el8_2","sourceRpm":"systemd-239-30.el8_2.src.rpm","size":7939885,"license":"LGPLv2+","vendor":"CentOS","files":[{"path":"/etc/udev/udev.conf","mode":33188,"size":215,"sha256":"96d43c3414fcdd70cf114c9f1290f2f9240b42b03a077de7e89b4fa2b7d4aa14"},{"path":"/etc/vconsole.conf","mode":33188,"size":0,"sha256":""},{"path":"/usr/bin/bootctl","mode":33261,"size":46136,"sha256":"467800cce34b3d6ac4b98a0453dcccafd287656cf02010d29ad5abf421c0bde4"},{"path":"/usr/bin/kernel-install","mode":33261,"size":4511,"sha256":"dc00218c274338607161e666b2e717b63b13c86031dabc8ba0e56d9e9cae93dd"},{"path":"/usr/bin/systemd-hwdb","mode":33261,"size":29456,"sha256":"4487e4591961fa81bf5e2a9a0c7d450532bbbf3d4010159eb186cd7c82845f89"},{"path":"/usr/bin/udevadm","mode":33261,"size":434592,"sha256":"34209b9a63fd86cecd1c5a52b99a04fcde8ccd2d0d81ac4d99c9c2487548d072"},{"path":"/usr/lib/.build-id/00/8918dc961ab81f2666db61c74176cc03b437c6","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/0d/7502c6561b0765ee2f638a243e31e838bf1716","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/2a/1c2e4ad1fbabf822e724e9639fe5bf4fcbcc2e","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/2f/d9f531e4c96310381e96aec4325718aeb686d1","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/36/cf26e36f06c7ea7150f13a946891540007e57c","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/55/77f47baaa2d4338a29ff58ec08a973b62a3a52","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/5d/926c3ad701ebd77bed2c00a2644267daaee382","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/75/460b07fb48fd0e924572795a2ebe5583a2a969","mode":41471,"size":41,"sha256":""},{"path":"/usr/lib/.build-id/75/e9b205e0d79cfd76498dbd5c81b53062340b8e","mode":41471,"size":72,"sha256":""},{"path":"/usr/lib/.build-id/7c/17b2c497c34b0171d8656834badcea527bdf6d","mode":41471,"size":80,"sha256":""},{"path":"/usr/lib/.build-id/84/8bf36d0838dc0a71f8f5db76386393b916a8e9","mode":41471,"size":52,"sha256":""},{"path":"/usr/lib/.build-id/92/f6e4394d0a27c5109cb105aae3920771b93bab","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/96/abd7713f18ffa0f73d9d6ecd9f8a79570ff9e6","mode":41471,"size":45,"sha256":""},{"path":"/usr/lib/.build-id/9c/3e3c790981e06d74bc8d1058c6dca51cfabe94","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/9e/eff3dd8644afb42df21af19d0f716b4969848a","mode":41471,"size":46,"sha256":""},{"path":"/usr/lib/.build-id/aa/6a462a2337233089228f25b5875408fcb3678a","mode":41471,"size":47,"sha256":""},{"path":"/usr/lib/.build-id/be/1e6e65c4be06866eadc0b62e1abdd89e2c2ecf","mode":41471,"size":42,"sha256":""},{"path":"/usr/lib/.build-id/de/f7a03b97e5d62e2a06670774eb5c9ff7cead3a","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/e1/a09c23b65f81557a469ea3a5471bde300b005c","mode":41471,"size":34,"sha256":""},{"path":"/usr/lib/.build-id/e2/8546b6bdc3b031b15d15b1e93beed2a3018cc8","mode":41471,"size":48,"sha256":""},{"path":"/usr/lib/.build-id/e3/dee9c3a3da1f51a318116579b32423f6935264","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/eb/fa07d21c0d69214e04a95454d088665c86a724","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/ec/5b8a79f33b35d7ee616a51e812c1414eb974c0","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/f6/224056a511368ea7f7f4143600e21a01553726","mode":41471,"size":74,"sha256":""},{"path":"/usr/lib/.build-id/fe/b47c999c99ef74ea48d6f073b7c309176fc5a8","mode":41471,"size":50,"sha256":""},{"path":"/usr/lib/.build-id/fe/f62e373df45e377331315cb2be9bfebb4f8b7a","mode":41471,"size":33,"sha256":""},{"path":"/usr/lib/kernel/install.d/20-grubby.install","mode":33261,"size":2252,"sha256":"1be846c5b4e2840cb6cfc5786b66cde04006c871cb0552e60d867803a2d4fbb1"},{"path":"/usr/lib/kernel/install.d/50-depmod.install","mode":33261,"size":368,"sha256":"336f8c7e2e9d28d6b454ee0509d300848709e1dc0d0553532776abf5650cdaf6"},{"path":"/usr/lib/kernel/install.d/90-loaderentry.install","mode":33261,"size":1975,"sha256":"6803e6820e161d82f6c4fe37a3edbcc672a0d9c5e50c6cdc2fa347a887abcd2f"},{"path":"/usr/lib/modprobe.d/systemd.conf","mode":33188,"size":765,"sha256":"9b559ca107858d342b24d08802e5f8013edb36c8f297e4e59a8f1ecc26246c9a"},{"path":"/usr/lib/systemd/boot/efi/linuxx64.efi.stub","mode":33261,"size":59770,"sha256":"86d537560470ca9ff49d92b87bbfa1ed876f52b67f4c5e299099c606d6802a80"},{"path":"/usr/lib/systemd/boot/efi/systemd-bootx64.efi","mode":33261,"size":87426,"sha256":"c02b7af5e6dc38353315feb8ddb3db908d5e86bbb685e363df031db418a2c1f7"},{"path":"/usr/lib/systemd/network/99-default.link","mode":33188,"size":412,"sha256":"b2a9507eb20fc264a7746ad625756e787d5b7f48a689598ed3e6b04be0aaf8c1"},{"path":"/usr/lib/systemd/system-generators/systemd-cryptsetup-generator","mode":33261,"size":33488,"sha256":"023ea0e4af06276b5f4661065fc1f3880228d358f532e2a840327f8cc5bb7a6d"},{"path":"/usr/lib/systemd/system-generators/systemd-gpt-auto-generator","mode":33261,"size":29424,"sha256":"0e5e9a6ffeaf11eeb58f3e31e58ee7fd928d57cada32ba4ed66541778cb3a5ef"},{"path":"/usr/lib/systemd/system-generators/systemd-hibernate-resume-generator","mode":33261,"size":12552,"sha256":"f0ef6261f0bcbdffb720651e3e6eafc09f2c2424800ac815765b55860ef34cd9"},{"path":"/usr/lib/systemd/system/cryptsetup-pre.target","mode":33188,"size":465,"sha256":"64e93c4634edf6e7b4e133e7069a4a3999ba563c269833bf17e3fd69ac431d18"},{"path":"/usr/lib/systemd/system/cryptsetup.target","mode":33188,"size":412,"sha256":"42782abe6eea495e1e9d590562c48c5ba48ba0fe8912d7ca7ecbd157d4e5c33e"},{"path":"/usr/lib/systemd/system/hibernate.target","mode":33188,"size":509,"sha256":"acdb33dfe236b0bce0e3a7883d4faa3d51a75b047031b0aca82c86df602b43d3"},{"path":"/usr/lib/systemd/system/hybrid-sleep.target","mode":33188,"size":530,"sha256":"2bace034b2984afde547bdfcbef419b707e577095faceb87e3928185341d06c8"},{"path":"/usr/lib/systemd/system/initrd-udevadm-cleanup-db.service","mode":33188,"size":708,"sha256":"a123ea9615f3b1c73cd1de5414735c2f383d7d4fcb4ba7a85f6800881dd73abd"},{"path":"/usr/lib/systemd/system/kmod-static-nodes.service","mode":33188,"size":721,"sha256":"489638758f825d591d358e5e83c8c0769ad73d23a5f462924873082992d59eb9"},{"path":"/usr/lib/systemd/system/local-fs.target.wants/systemd-remount-fs.service","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/systemd/system/quotaon.service","mode":33188,"size":617,"sha256":"955f4128db5c87920bf9d77943a21d9db5baed19e7660d5df9027d42edca2511"},{"path":"/usr/lib/systemd/system/remote-cryptsetup.target","mode":33188,"size":549,"sha256":"86d9439857b2d5e306805a4a9d83e35cf9cde9e31c5305557c321c3254cc8909"},{"path":"/usr/lib/systemd/system/sleep.target","mode":33188,"size":460,"sha256":"17af014aaa018d21da85d642f9f15979fa699ed315b3268c3c0b460c7a81a046"},{"path":"/usr/lib/systemd/system/sockets.target.wants/systemd-udevd-control.socket","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/systemd/system/sockets.target.wants/systemd-udevd-kernel.socket","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/systemd/system/suspend-then-hibernate.target","mode":33188,"size":577,"sha256":"21aefd75fe9dacae47e9b75ae813b33d9890b64879a1b2c5fa1175d259da1bc8"},{"path":"/usr/lib/systemd/system/suspend.target","mode":33188,"size":503,"sha256":"acec592c25438d9199a7b1180b960d98b08b711e0b95f040444cd1e892106c3e"},{"path":"/usr/lib/systemd/system/sysinit.target.wants/cryptsetup.target","mode":41471,"size":20,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/kmod-static-nodes.service","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-hwdb-update.service","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-modules-load.service","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-random-seed.service","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-tmpfiles-setup-dev.service","mode":41471,"size":37,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-udev-trigger.service","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/systemd/system/sysinit.target.wants/systemd-udevd.service","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/systemd/system/systemd-backlight@.service","mode":33188,"size":760,"sha256":"7521d5ed7c75cd704e3d296ed83e14a38ae67bbf72aebdd5f60e8d082008498f"},{"path":"/usr/lib/systemd/system/systemd-hibernate-resume@.service","mode":33188,"size":675,"sha256":"00f5923f767325bc3c22314d81cb61c4138df6762c1542b46abe46ba95ee0d72"},{"path":"/usr/lib/systemd/system/systemd-hibernate.service","mode":33188,"size":545,"sha256":"4e71814ddc5962ade792e6ac0c316282c4236d9c27b57ea5baeae05e324a874a"},{"path":"/usr/lib/systemd/system/systemd-hwdb-update.service","mode":33188,"size":826,"sha256":"e0a495fd8e75e4b792f797fd1107611e06b19e7815bf16fd52eeb7b538b54b91"},{"path":"/usr/lib/systemd/system/systemd-hybrid-sleep.service","mode":33188,"size":563,"sha256":"b736d5b251aeeb20e8ffb49da45e6cbf7723a56e6e44f087fef614a664312c9e"},{"path":"/usr/lib/systemd/system/systemd-modules-load.service","mode":33188,"size":1011,"sha256":"10eb25cd5fd820074584c879fd225a58040fa4378185ec7ac89a5841e3f86aa6"},{"path":"/usr/lib/systemd/system/systemd-quotacheck.service","mode":33188,"size":663,"sha256":"869552aebcc4c69d8c062bfa395e9f8b90f6865527bcc0993cdc449c5f282e32"},{"path":"/usr/lib/systemd/system/systemd-random-seed.service","mode":33188,"size":800,"sha256":"fdf8f520cd2c466db4230a90c8d6a81aea3472a432c4bc17316dcd9e57947627"},{"path":"/usr/lib/systemd/system/systemd-remount-fs.service","mode":33188,"size":802,"sha256":"c8d37b2289b7b3cc498243e4c25910226fb167e78b15c1967b006c6dc7d1b2fa"},{"path":"/usr/lib/systemd/system/systemd-rfkill.service","mode":33188,"size":728,"sha256":"c75e2589203b17fd344b2e6903f40eabe2a01ca941a4f249db37a8cf254ae782"},{"path":"/usr/lib/systemd/system/systemd-rfkill.socket","mode":33188,"size":657,"sha256":"36c337d16f62fc2ce6bac474a407218b060152cc2399011969a4cab7875f3d30"},{"path":"/usr/lib/systemd/system/systemd-suspend-then-hibernate.service","mode":33188,"size":600,"sha256":"b20557747035e866a7b731562c142a4d84d981642feb59d7ec1fdf0b11bf932f"},{"path":"/usr/lib/systemd/system/systemd-suspend.service","mode":33188,"size":541,"sha256":"0f6fd2d33dab70c75716d9578af498d4fe503ae3317a9d0e9ee9091126462d79"},{"path":"/usr/lib/systemd/system/systemd-tmpfiles-setup-dev.service","mode":33188,"size":771,"sha256":"5476126ae6a3537277871facca0bbc54eb2f944678d8dd99d51a5853529bfc47"},{"path":"/usr/lib/systemd/system/systemd-udev-settle.service","mode":33188,"size":867,"sha256":"987bfbfe9d0331ae48c8405bdf0c17a891abfc941ed048f95fc18ad75411f513"},{"path":"/usr/lib/systemd/system/systemd-udev-trigger.service","mode":33188,"size":771,"sha256":"918ff2478f103dded4f21c931e76e76b7d68db373e1a5aee1ce419aa6895f516"},{"path":"/usr/lib/systemd/system/systemd-udev-trigger.service.d/systemd-udev-trigger-no-reload.conf","mode":33188,"size":87,"sha256":"e22c23fb4618a2021322c5b68fc16b872a27fe8a3edb42e8abec83896eba835a"},{"path":"/usr/lib/systemd/system/systemd-udevd-control.socket","mode":33188,"size":635,"sha256":"6446db490b349b87d129f5172aa834784bb2116949bf9c52b316daa65c1ac675"},{"path":"/usr/lib/systemd/system/systemd-udevd-kernel.socket","mode":33188,"size":610,"sha256":"2b62ddf05c5441eb41ac7cbb187064065da3aab366e2bced9d9b9d8c0cd7b982"},{"path":"/usr/lib/systemd/system/systemd-udevd.service","mode":33188,"size":1070,"sha256":"aea3d3ccb744697e48ffa1409012445d84238dc356590b49dd130e5072c67518"},{"path":"/usr/lib/systemd/system/systemd-vconsole-setup.service","mode":33188,"size":622,"sha256":"824cd3de4787f503cca06d5354dd40c6db1e00a0a4f2fa351661fafad299bb2d"},{"path":"/usr/lib/systemd/systemd-backlight","mode":33261,"size":21136,"sha256":"25bf0fc01abfc79f199f026eb3e6ee3533b1b1620c7d63c9cd91d8ad488e3609"},{"path":"/usr/lib/systemd/systemd-cryptsetup","mode":33261,"size":29336,"sha256":"79e8ee68e865f07f0eab83798b3a248d44c9a97e7224eeccd9ffeb22a146a2cd"},{"path":"/usr/lib/systemd/systemd-growfs","mode":33261,"size":20728,"sha256":"55d61ad2acbae9e8278639ba9cfb36eee13e21fe21ba70e31cedf3152777df7a"},{"path":"/usr/lib/systemd/systemd-hibernate-resume","mode":33261,"size":12512,"sha256":"53328d3d39cfea5f3aa72ed6c8da4efa804e9205631675b2838af3931011d5e0"},{"path":"/usr/lib/systemd/systemd-makefs","mode":33261,"size":12512,"sha256":"fd790329473d94e7ed20f377a8918f9e1d94ce528b48a70783340a2ca18b014a"},{"path":"/usr/lib/systemd/systemd-modules-load","mode":33261,"size":21192,"sha256":"e7f600a12c2f37e50d0edbd6357a2cb7f658509e6bc521c41c1c10c5a57b66be"},{"path":"/usr/lib/systemd/systemd-quotacheck","mode":33261,"size":12352,"sha256":"6e8e1e4934b15ded88587243b921616a5911d5e531c32245531c0ffa98631b5d"},{"path":"/usr/lib/systemd/systemd-random-seed","mode":33261,"size":16608,"sha256":"fd0262188360f5e270271b4c5cbd04048442a23cf97c335ab929373b2212760f"},{"path":"/usr/lib/systemd/systemd-remount-fs","mode":33261,"size":25280,"sha256":"d913bb9cbba51082172fbef2d267083d4ee42ec440b41bf8e42617fbc9018be6"},{"path":"/usr/lib/systemd/systemd-rfkill","mode":33261,"size":25208,"sha256":"513fac3789d7e3a29d1b4b12da5bb6babae769c5f5eabc519c52d3a93a672efd"},{"path":"/usr/lib/systemd/systemd-sleep","mode":33261,"size":21112,"sha256":"f598aa9b57f1cc8541bc6070cc6a89cd489d73a271b87784e30fc30a4852b040"},{"path":"/usr/lib/systemd/systemd-udevd","mode":33261,"size":418112,"sha256":"083814fc249388c8ee652ee336b1bdfb9e3bb9a3ce33985b948330e572bce6a8"},{"path":"/usr/lib/systemd/systemd-vconsole-setup","mode":33261,"size":21104,"sha256":"236a1e45b7f5d5d020d0709a6f5dfd972adb1a463a02f5a25bb870ef6ebaf19d"},{"path":"/usr/lib/udev/ata_id","mode":33261,"size":16592,"sha256":"fd00d470422d409d7af12cc995bf989078815b2626116767ff43885e54858e74"},{"path":"/usr/lib/udev/cdrom_id","mode":33261,"size":33312,"sha256":"c03b1ff5acaadefb95900c3aac953f942d4894159b73a665280c33580ac71005"},{"path":"/usr/lib/udev/collect","mode":33261,"size":17000,"sha256":"97b2b5b881b25044f038788dcb43f60ef67b1b39293e22b98109c0218a926008"},{"path":"/usr/lib/udev/fido_id","mode":33261,"size":16960,"sha256":"61742bea83b08240d94240a5f8cf810b96884e1b2be11a1a7123c61d9ee4dbbd"},{"path":"/usr/lib/udev/mtd_probe","mode":33261,"size":12888,"sha256":"373e95563336fd07ac0be6af6b4dab7f60d639bb743865f9626caa20b87e2ceb"},{"path":"/usr/lib/udev/rules.d/40-elevator.rules","mode":33188,"size":728,"sha256":"7803b00e7f50bfaaae03369bd81a460cdd35212f99b0e5fe11ad12836f8ca8ba"},{"path":"/usr/lib/udev/rules.d/40-redhat.rules","mode":33188,"size":1834,"sha256":"777a211e63c3df00e2cf2cacd22469de0202e21a0b72fa61c76ab5482e68f2eb"},{"path":"/usr/lib/udev/rules.d/50-udev-default.rules","mode":33188,"size":3679,"sha256":"76f92132993612a5333bdfbd0d0107fec44601f58d7e376efbaaf7c13e16effe"},{"path":"/usr/lib/udev/rules.d/60-alias-kmsg.rules","mode":33188,"size":357,"sha256":"0ce4498487b2ce4070a7ce8d3254580d5357fcdfa8382fa9755315c838517901"},{"path":"/usr/lib/udev/rules.d/60-block.rules","mode":33188,"size":626,"sha256":"ae679724ba5e7a78db8710387a55213f5040fdbd86684beef65515d162de2c2e"},{"path":"/usr/lib/udev/rules.d/60-cdrom_id.rules","mode":33188,"size":1071,"sha256":"16f44dc355a6b5ada3a0706b2f84c95b25ed6c2a09e4e201da94885c93d1a4d2"},{"path":"/usr/lib/udev/rules.d/60-drm.rules","mode":33188,"size":413,"sha256":"9045c45062fdb03abd55cdec32fb13fe6f196290b52b5c4c9fc350406bf094ce"},{"path":"/usr/lib/udev/rules.d/60-evdev.rules","mode":33188,"size":974,"sha256":"137101a59e56390f956d81f0cc35c73316cc899b05dda63b51fab4197f77dc8b"},{"path":"/usr/lib/udev/rules.d/60-fido-id.rules","mode":33188,"size":165,"sha256":"a838eccc8764876f756bee4b624b9b7681161b0801f2859d0a47a24c53eb5308"},{"path":"/usr/lib/udev/rules.d/60-input-id.rules","mode":33188,"size":282,"sha256":"2983389654fbf42eca6b703543f76867dbf53eeec9288c2c88d0fcb338a2c265"},{"path":"/usr/lib/udev/rules.d/60-persistent-alsa.rules","mode":33188,"size":616,"sha256":"36767245b64ae515fc073c21bc78769f41188140e1d7b9576ec8dee34d585172"},{"path":"/usr/lib/udev/rules.d/60-persistent-input.rules","mode":33188,"size":2710,"sha256":"84e1eb2d66e10a06fc2b8f4c00a3295283806b1a335eab27f3cd7f45acf26834"},{"path":"/usr/lib/udev/rules.d/60-persistent-storage-tape.rules","mode":33188,"size":1509,"sha256":"94085d6906b307d54f519a684c26a087937a4bf4d661f37b4b51c3d63dd20783"},{"path":"/usr/lib/udev/rules.d/60-persistent-storage.rules","mode":33188,"size":6528,"sha256":"17bd433c3f36b5bff512d7e4c95af93ab31673f2b43274a8d97c6dffba55e929"},{"path":"/usr/lib/udev/rules.d/60-persistent-v4l.rules","mode":33188,"size":769,"sha256":"219eb6b4c0df4d8701cc5a316b2ddf63797d4c1b689bc0b289d5cb8063a7034e"},{"path":"/usr/lib/udev/rules.d/60-sensor.rules","mode":33188,"size":727,"sha256":"8683a63aa8962c4028700ce61752a788d9393297222440a8a186b051befab2ee"},{"path":"/usr/lib/udev/rules.d/60-serial.rules","mode":33188,"size":1190,"sha256":"54367e1335266de43edb6451534c9e69c317075212b216cedf1d3b6896f14ee0"},{"path":"/usr/lib/udev/rules.d/64-btrfs.rules","mode":33188,"size":616,"sha256":"a4bc67740cd0988415907b0fdb5e9cd955be2626b5095b55c7eed4aa4e99bb53"},{"path":"/usr/lib/udev/rules.d/70-joystick.rules","mode":33188,"size":432,"sha256":"199e72c162185b62c0888791c9b3cde2c8b180fae4e4ae3a29564f933d0adffd"},{"path":"/usr/lib/udev/rules.d/70-mouse.rules","mode":33188,"size":734,"sha256":"d495d2b8523e7f8175a9b06704f168e14ab97a8a333d4a52ec9501bc0c509ecb"},{"path":"/usr/lib/udev/rules.d/70-power-switch.rules","mode":33188,"size":568,"sha256":"ce83c43f9e2f20810b2a0fa4db7b769ed6b9a19095e354878b731c5c15254526"},{"path":"/usr/lib/udev/rules.d/70-touchpad.rules","mode":33188,"size":473,"sha256":"8d81de6a6d5b5703098518f977c3b984bdf179238402a8ca0205f85cde798a27"},{"path":"/usr/lib/udev/rules.d/70-uaccess.rules","mode":33188,"size":2671,"sha256":"baf20471b356a030c52114a90776ca9fb94536ff333a174ed38eb38945a18cec"},{"path":"/usr/lib/udev/rules.d/71-seat.rules","mode":33188,"size":2758,"sha256":"257cd0b0502c5963957e785a18c751a445250f421a04d24bff5e9eb3603e842f"},{"path":"/usr/lib/udev/rules.d/73-idrac.rules","mode":33188,"size":316,"sha256":"165488bae675977be8f0b9c4e7510c740c02d41dbab7f142037d0467ee1f4940"},{"path":"/usr/lib/udev/rules.d/73-seat-late.rules","mode":33188,"size":636,"sha256":"dcabfab6c5ca6e76d994fa183cb26b72a4f43912a071a61e1657716a15cfa7e0"},{"path":"/usr/lib/udev/rules.d/75-net-description.rules","mode":33188,"size":452,"sha256":"5b8da22a593f2aaffd4697e4cbfb14cb7eb1d52b96f03d9a60c82eeec920e925"},{"path":"/usr/lib/udev/rules.d/75-probe_mtd.rules","mode":33188,"size":174,"sha256":"54256aa2ca91172cbce3ea805ccf2cd52de8acbbc2db88d209de84655fa997c5"},{"path":"/usr/lib/udev/rules.d/78-sound-card.rules","mode":33188,"size":4816,"sha256":"ec291608292fe2de555e8a1e5ce574acf315fe65268c469872614073d5e36cae"},{"path":"/usr/lib/udev/rules.d/80-drivers.rules","mode":33188,"size":615,"sha256":"2938670ed8d66eed02c9447f018f07482ff23c36793587c80059561b4c58fa83"},{"path":"/usr/lib/udev/rules.d/80-net-setup-link.rules","mode":33188,"size":292,"sha256":"e2cb34f4b9e1be5c5016f928c06eb7d9370650361d791ef682a00a3108d2d832"},{"path":"/usr/lib/udev/rules.d/90-vconsole.rules","mode":33188,"size":510,"sha256":"7b6fb1a5dfa30fef49b403e9905e8a06f21a2475b44c5ad1cc29306596433289"},{"path":"/usr/lib/udev/rules.d/99-systemd.rules","mode":33188,"size":4367,"sha256":"a3e6c7b7e5a944b58e5b44b6c71f4979d12f3d2f57b8849c8cf0fd403a127a51"},{"path":"/usr/lib/udev/scsi_id","mode":33261,"size":34072,"sha256":"cce5256be7ad0c0c0afdfaa8d85f46e0aa388dc55d5f9fada97906b07f498cea"},{"path":"/usr/lib/udev/v4l_id","mode":33261,"size":12496,"sha256":"b506a6a673286f8a549608c8185fad5cf0929bdbc3e48e8e0ea8437383856eca"},{"path":"/usr/sbin/udevadm","mode":41471,"size":14,"sha256":""},{"path":"/usr/share/bash-completion/completions/bootctl","mode":33188,"size":1937,"sha256":"3ab3bd4f0e655be7f517845c4abd0ea266fca2eb7f6943708b184a645aae11fc"},{"path":"/usr/share/bash-completion/completions/kernel-install","mode":33188,"size":1810,"sha256":"300fa55e4a06cf8a162f0a7d030f9920041d22506c3f001f9c86d452f8a470cb"},{"path":"/usr/share/bash-completion/completions/udevadm","mode":33188,"size":3766,"sha256":"48545540326c7eba22883d8d469f336c861d8ad26b7e8a34116943162a3d7e5f"},{"path":"/usr/share/zsh/site-functions/_bootctl","mode":33188,"size":1101,"sha256":"00baf8fb7134bf9c163005037d9c936bbfb24f2744c4701f9a8a51d47e7a413a"},{"path":"/usr/share/zsh/site-functions/_kernel-install","mode":33188,"size":651,"sha256":"438f8319164bac0a22ffadd7ed33e10a796015d018a91196e7f1d32a549993cc"},{"path":"/usr/share/zsh/site-functions/_udevadm","mode":33188,"size":5997,"sha256":"f6aaa0dcc6d651e6e4e12dcd6943c2c161e852eef115be38ff83fe3b88cb6cf8"},{"path":"/var/lib/systemd/random-seed","mode":33188,"size":0,"sha256":""}]}},{"name":"tar","version":"1.30-4.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:tar:tar:1.30-4.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:tar:1.30-4.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/tar@2:1.30-4.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"tar","version":"1.30","epoch":2,"architecture":"x86_64","release":"4.el8","sourceRpm":"tar-1.30-4.el8.src.rpm","size":2914728,"license":"GPLv3+","vendor":"CentOS","files":[{"path":"/usr/bin/gtar","mode":41471,"size":3,"sha256":""},{"path":"/usr/bin/tar","mode":33261,"size":497912,"sha256":"75b6c10cea371e95c8c1e315f76852aaa01a0cc31b878621cf0d1670e5a7ac70"},{"path":"/usr/lib/.build-id/e7/a78cae1d85ad11ac18ae07efe26553a4d8ae5a","mode":41471,"size":23,"sha256":""},{"path":"/usr/share/licenses/tar/COPYING","mode":33188,"size":35147,"sha256":"8ceb4b9ee5adedde47b31e975c1d90c73ad27b6b165a1dcd80c7c545eb65b903"}]}},{"name":"tzdata","version":"2020a-1.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:tzdata:tzdata:2020a-1.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:tzdata:2020a-1.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/tzdata@0:2020a-1.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"tzdata","version":"2020a","epoch":0,"architecture":"noarch","release":"1.el8","sourceRpm":"tzdata-2020a-1.el8.src.rpm","size":1904256,"license":"Public Domain","vendor":"CentOS","files":[{"path":"/usr/share/licenses/tzdata/LICENSE","mode":33188,"size":252,"sha256":"0613408568889f5739e5ae252b722a2659c02002839ad970a63dc5e9174b27cf"},{"path":"/usr/share/zoneinfo/Africa/Abidjan","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Accra","mode":33188,"size":842,"sha256":"ea0a89ec3c253390f746107c3ea69392270d8df0dc2d2aed6f23f4cff852bf91"},{"path":"/usr/share/zoneinfo/Africa/Addis_Ababa","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Africa/Algiers","mode":33188,"size":760,"sha256":"d777e8eecb9ebe269692349daa6b45b2463e4a3c2d107ccd139b6206c4fa73cc"},{"path":"/usr/share/zoneinfo/Africa/Asmara","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Africa/Asmera","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Africa/Bamako","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Bangui","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Banjul","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Bissau","mode":33188,"size":208,"sha256":"8ddad13adc33cdee8eaf55cfa31efcafd79305ae8dfcc3be06ff78299f29f1d8"},{"path":"/usr/share/zoneinfo/Africa/Blantyre","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/Africa/Brazzaville","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Bujumbura","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/Africa/Cairo","mode":33188,"size":1972,"sha256":"279bbe1fa62da67387c63593b60bb655252ef5c8f189cf43469087740af2b4fc"},{"path":"/usr/share/zoneinfo/Africa/Casablanca","mode":33188,"size":2465,"sha256":"ffa6b8924f65caa075abd3d790fcca99faf59b66cef9531dda52544ee1d5d673"},{"path":"/usr/share/zoneinfo/Africa/Ceuta","mode":33188,"size":2059,"sha256":"387d2c354117fe2a22f6f3b429e4193a331d3e93d7007a55c50b3b9eedee63de"},{"path":"/usr/share/zoneinfo/Africa/Conakry","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Dakar","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Dar_es_Salaam","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Africa/Djibouti","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Africa/Douala","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/El_Aaiun","mode":33188,"size":2303,"sha256":"8bd0b2fbcc4c1c23746fc012be63f88a543bfcaa3f6d464cdf32c014c7bde110"},{"path":"/usr/share/zoneinfo/Africa/Freetown","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Gaborone","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/Africa/Harare","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/Africa/Johannesburg","mode":33188,"size":271,"sha256":"fcec4247091905d88a0b869e8e5c7ee6bcfba7db6c310165baa95078b0be31af"},{"path":"/usr/share/zoneinfo/Africa/Juba","mode":33188,"size":683,"sha256":"73d986c70173c763e9b262dbf367120bc2a4f63f006c1d412ea9adab77e09da3"},{"path":"/usr/share/zoneinfo/Africa/Kampala","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Africa/Khartoum","mode":33188,"size":713,"sha256":"5256a96f78382e82db80ad8591240c3886fc58f9a83fe94506e3a192fbcf2f4e"},{"path":"/usr/share/zoneinfo/Africa/Kigali","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/Africa/Kinshasa","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Lagos","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Libreville","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Lome","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Luanda","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Lubumbashi","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/Africa/Lusaka","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/Africa/Malabo","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Maputo","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/Africa/Maseru","mode":33188,"size":271,"sha256":"fcec4247091905d88a0b869e8e5c7ee6bcfba7db6c310165baa95078b0be31af"},{"path":"/usr/share/zoneinfo/Africa/Mbabane","mode":33188,"size":271,"sha256":"fcec4247091905d88a0b869e8e5c7ee6bcfba7db6c310165baa95078b0be31af"},{"path":"/usr/share/zoneinfo/Africa/Mogadishu","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Africa/Monrovia","mode":33188,"size":233,"sha256":"3f9672c98983af595b3c6274cf8135728c8815a4f9c98ffba043707609e5d122"},{"path":"/usr/share/zoneinfo/Africa/Nairobi","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Africa/Ndjamena","mode":33188,"size":225,"sha256":"b1391c8edd23b3f73e0bfacf8b878801c58206ca42349c30b22fcb7e8d13de3a"},{"path":"/usr/share/zoneinfo/Africa/Niamey","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Nouakchott","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Ouagadougou","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Porto-Novo","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/Africa/Sao_Tome","mode":33188,"size":263,"sha256":"1c04b1866beb73b69104997850cce075376d62716f8d01156e796d878b160545"},{"path":"/usr/share/zoneinfo/Africa/Timbuktu","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Africa/Tripoli","mode":33188,"size":655,"sha256":"8ff53f7072863fb56f1e71339392b6de7e50675efa4333b9e032b677c9c9a527"},{"path":"/usr/share/zoneinfo/Africa/Tunis","mode":33188,"size":710,"sha256":"eecc34436d1dd96c49d6b671ed61bc594548d280a967537a9653841b537a9a92"},{"path":"/usr/share/zoneinfo/Africa/Windhoek","mode":33188,"size":1034,"sha256":"3f032165bd2520eb45848e2d059f61185331ba6faa263861c70ec2becf30fa9d"},{"path":"/usr/share/zoneinfo/America/Adak","mode":33188,"size":2365,"sha256":"c45c94d316413c8f666aff65ed1f837a7e2d392262de31ce59fac2e96a1edc81"},{"path":"/usr/share/zoneinfo/America/Anchorage","mode":33188,"size":2380,"sha256":"f5df0a6f7f9d43cbbd3e74d33a23fe686080eb55965f5d9246b6e859b3db9d18"},{"path":"/usr/share/zoneinfo/America/Anguilla","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Antigua","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Araguaina","mode":33188,"size":910,"sha256":"fb7fe2d06e8ee5c5d9a8a568c8cb37efbb0086824f38d1bc4d8505f963b5970d"},{"path":"/usr/share/zoneinfo/America/Argentina/Buenos_Aires","mode":33188,"size":1109,"sha256":"841b9bca947f2acd9adc6cb5c10171204eecec1e46e6042654f355c89debc43f"},{"path":"/usr/share/zoneinfo/America/Argentina/Catamarca","mode":33188,"size":1109,"sha256":"e844a8f34c71c2d04bfdac6b11e913b5f20ea9fddb5d145433d0831087f1c5d6"},{"path":"/usr/share/zoneinfo/America/Argentina/ComodRivadavia","mode":33188,"size":1109,"sha256":"e844a8f34c71c2d04bfdac6b11e913b5f20ea9fddb5d145433d0831087f1c5d6"},{"path":"/usr/share/zoneinfo/America/Argentina/Cordoba","mode":33188,"size":1109,"sha256":"254a30f9b9b00558350d0c1f40a1d9c8738045bb7fe88e56c81bbb9fbd161026"},{"path":"/usr/share/zoneinfo/America/Argentina/Jujuy","mode":33188,"size":1081,"sha256":"233f43f895b08f21cd28918fbdb9c22892511c0996ac6212e019c3e866aca455"},{"path":"/usr/share/zoneinfo/America/Argentina/La_Rioja","mode":33188,"size":1123,"sha256":"edc82d9225b8ae3ca911eab14f8201a8916928cfab233e182f807e715cf18435"},{"path":"/usr/share/zoneinfo/America/Argentina/Mendoza","mode":33188,"size":1109,"sha256":"d50f245cf1eeb3650dbbdd45720ddc6b1c5e22aede7981f20b9efe2c7ac68c4d"},{"path":"/usr/share/zoneinfo/America/Argentina/Rio_Gallegos","mode":33188,"size":1109,"sha256":"f762067b25cc7e6141b06a6eae77764caccccbfe8716f1370c33e169ec2e1723"},{"path":"/usr/share/zoneinfo/America/Argentina/Salta","mode":33188,"size":1081,"sha256":"1deede9c14ed0b4dc6e5a40110c7056083c8fed557b84aadc0fa2a045411e560"},{"path":"/usr/share/zoneinfo/America/Argentina/San_Juan","mode":33188,"size":1123,"sha256":"100c000b03b9a0e19c778d9e81ad8e5c2c34db4b7da24c55d67c0ad8050a67c5"},{"path":"/usr/share/zoneinfo/America/Argentina/San_Luis","mode":33188,"size":1139,"sha256":"ab15b1141b87b1381e5cad386fc374b5a9a2ca922504da5b848074fab91e9abc"},{"path":"/usr/share/zoneinfo/America/Argentina/Tucuman","mode":33188,"size":1137,"sha256":"6a623bbcd2144f1e43892777084bde4e2613ae6f22bf92dedf6e1dc6e68248b3"},{"path":"/usr/share/zoneinfo/America/Argentina/Ushuaia","mode":33188,"size":1109,"sha256":"02f9a96426823c7bf25ff15a1f241069e2cb15969d48d0c6cc31aad13a7d0f49"},{"path":"/usr/share/zoneinfo/America/Aruba","mode":33188,"size":212,"sha256":"023d877932f35d889772f561f79e266c8541b984e0ce2bd257723aafc7d883c1"},{"path":"/usr/share/zoneinfo/America/Asuncion","mode":33188,"size":2077,"sha256":"1e29f7cdc530419ad31e4afc8fc2adf40d9577f55e2174a3a82358a027780ca2"},{"path":"/usr/share/zoneinfo/America/Atikokan","mode":33188,"size":345,"sha256":"c30226b472b507b5a30b69557d56f24fcc8e9467110e4d3ec15c2c51de5d245c"},{"path":"/usr/share/zoneinfo/America/Atka","mode":33188,"size":2365,"sha256":"c45c94d316413c8f666aff65ed1f837a7e2d392262de31ce59fac2e96a1edc81"},{"path":"/usr/share/zoneinfo/America/Bahia","mode":33188,"size":1050,"sha256":"2e1c1b5e2579e15a623bfd3774db703a49b937790e68b44a6b99a308c6ecba66"},{"path":"/usr/share/zoneinfo/America/Bahia_Banderas","mode":33188,"size":1588,"sha256":"9d0e0d9f6168635a5f98550a170d423854ff5b662ce0d874c3cba77199bf1cbd"},{"path":"/usr/share/zoneinfo/America/Barbados","mode":33188,"size":344,"sha256":"9b1a7857a01ae2a3ae9a51e0b40cfbed91bac468579ed3c08b54466276bbb1fa"},{"path":"/usr/share/zoneinfo/America/Belem","mode":33188,"size":602,"sha256":"84749f6075de59dc62bd69343194806cfd552641b912a6f8e96c83c99914a187"},{"path":"/usr/share/zoneinfo/America/Belize","mode":33188,"size":978,"sha256":"eb4e57a8c657d0c253ef4e0a5af118c928e6e5875564081a714563addfd4b31a"},{"path":"/usr/share/zoneinfo/America/Blanc-Sablon","mode":33188,"size":307,"sha256":"c7d383bfb7e85331030f8091a9055a5f424e3674407ca0c76cce06b5a0316fdb"},{"path":"/usr/share/zoneinfo/America/Boa_Vista","mode":33188,"size":658,"sha256":"c57a63f22280c2c46587414956efc8fcaadc36ed422589b48929dcc7ab4f6680"},{"path":"/usr/share/zoneinfo/America/Bogota","mode":33188,"size":271,"sha256":"3611de34f765f2d65ec0593e79c678de36092549898680dc4639b8c68f7137ba"},{"path":"/usr/share/zoneinfo/America/Boise","mode":33188,"size":2403,"sha256":"33353ef05ccdda7debe757cf865ee7bd78031f38c6797b8fbfc11f9010f55a10"},{"path":"/usr/share/zoneinfo/America/Buenos_Aires","mode":33188,"size":1109,"sha256":"841b9bca947f2acd9adc6cb5c10171204eecec1e46e6042654f355c89debc43f"},{"path":"/usr/share/zoneinfo/America/Cambridge_Bay","mode":33188,"size":2098,"sha256":"0aeaed5b104ee99ab13a9f5b5a7aaf7f6c9a7f59bdefd15d3c9951551c7b5f6f"},{"path":"/usr/share/zoneinfo/America/Campo_Grande","mode":33188,"size":1470,"sha256":"e670b40a7dd3adf79f66ea43382a70e60caee6ffb59ae92c4c9ee081d16259d2"},{"path":"/usr/share/zoneinfo/America/Cancun","mode":33188,"size":816,"sha256":"d22316873f309799c6f97fefb8a0a8897d0df4eb376f84bb0b71602ec240d04f"},{"path":"/usr/share/zoneinfo/America/Caracas","mode":33188,"size":289,"sha256":"94e8efae88e096d6dd0abda2661d826c004f0c587f97782cb2f911ed7c942f1a"},{"path":"/usr/share/zoneinfo/America/Catamarca","mode":33188,"size":1109,"sha256":"e844a8f34c71c2d04bfdac6b11e913b5f20ea9fddb5d145433d0831087f1c5d6"},{"path":"/usr/share/zoneinfo/America/Cayenne","mode":33188,"size":224,"sha256":"af8de87447f7093759a595cc3d403e5fa7b51fc3520959c4da54956ffbac856a"},{"path":"/usr/share/zoneinfo/America/Cayman","mode":33188,"size":203,"sha256":"fc4fbba14653a3186f3c5b719f7b9bf7d8a5824401064cf6d508205592e55a9f"},{"path":"/usr/share/zoneinfo/America/Chicago","mode":33188,"size":3585,"sha256":"143f29b957173a46008187230a38125bd3a03b3dbcba0dc1d1b8661331f71693"},{"path":"/usr/share/zoneinfo/America/Chihuahua","mode":33188,"size":1522,"sha256":"a7d150e716db5b1c96bb0e50252b80306e1d9e8bcc2bf90a3ae7071906e71513"},{"path":"/usr/share/zoneinfo/America/Coral_Harbour","mode":33188,"size":345,"sha256":"c30226b472b507b5a30b69557d56f24fcc8e9467110e4d3ec15c2c51de5d245c"},{"path":"/usr/share/zoneinfo/America/Cordoba","mode":33188,"size":1109,"sha256":"254a30f9b9b00558350d0c1f40a1d9c8738045bb7fe88e56c81bbb9fbd161026"},{"path":"/usr/share/zoneinfo/America/Costa_Rica","mode":33188,"size":341,"sha256":"4e6ff29a776e053226bf590ebe734896f9150d69074f22a16a1c7199a1484ec5"},{"path":"/usr/share/zoneinfo/America/Creston","mode":33188,"size":233,"sha256":"97b74beec3714be518219f24533cc21edf9b53d01f4ab792a6fe0f88973449eb"},{"path":"/usr/share/zoneinfo/America/Cuiaba","mode":33188,"size":1442,"sha256":"309f877286fad7d01fbbae6bb1a64e23227688e1687a90b6ce67faaef5b0cb67"},{"path":"/usr/share/zoneinfo/America/Curacao","mode":33188,"size":212,"sha256":"023d877932f35d889772f561f79e266c8541b984e0ce2bd257723aafc7d883c1"},{"path":"/usr/share/zoneinfo/America/Danmarkshavn","mode":33188,"size":712,"sha256":"087e39cd6f10b6944b68b1de557289ef33769467f1b29806b96a16cf8e438e6e"},{"path":"/usr/share/zoneinfo/America/Dawson","mode":33188,"size":1609,"sha256":"c379fb9517c07d4df5cbd6aaa2ec4561cbe893ba0e8552d377947fe2b1ff9bf3"},{"path":"/usr/share/zoneinfo/America/Dawson_Creek","mode":33188,"size":1059,"sha256":"29d0245bc04dadcbb196a3b6a81bace1696451166a7417d5bb2a8610f37ec5ba"},{"path":"/usr/share/zoneinfo/America/Denver","mode":33188,"size":2453,"sha256":"f4df3cc74c79d070a25a7927744d3a422a05d862a9a234a12105c5c964efb22d"},{"path":"/usr/share/zoneinfo/America/Detroit","mode":33188,"size":2244,"sha256":"e668e3859786c92f462769f87d5bc4ef31b5d6646bbd1635b91007e2a03dbc6c"},{"path":"/usr/share/zoneinfo/America/Dominica","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Edmonton","mode":33188,"size":2346,"sha256":"92ac6208f1ef357787fcfce6a334990252189eb0b427b28bc60e21ab5e792b3c"},{"path":"/usr/share/zoneinfo/America/Eirunepe","mode":33188,"size":690,"sha256":"07761278f5c58867c645625c9b819ea09e4703d76564e231979e48d6d2e0881a"},{"path":"/usr/share/zoneinfo/America/El_Salvador","mode":33188,"size":250,"sha256":"63215b213a31505bfd545fd52b11214cb614f13f0f55911f414edb44286e7f8a"},{"path":"/usr/share/zoneinfo/America/Ensenada","mode":33188,"size":2356,"sha256":"d827b95b4fa16b8c56d9a1636341c9112657e567ae84b37a9bfca133ae31babb"},{"path":"/usr/share/zoneinfo/America/Fort_Nelson","mode":33188,"size":2249,"sha256":"e7ce9a01cdd313d20352112430341c262e1b90182de490fc95c132daac118ce7"},{"path":"/usr/share/zoneinfo/America/Fort_Wayne","mode":33188,"size":1675,"sha256":"55c2f3feb241f88435e9876e76e2c69ddfd0dfd36a273b551ff480e2cfad99fe"},{"path":"/usr/share/zoneinfo/America/Fortaleza","mode":33188,"size":742,"sha256":"ca3cd6cdd4ec5f945742cd72a91e539756e0ad2eac3dfa62afc21397061eea99"},{"path":"/usr/share/zoneinfo/America/Glace_Bay","mode":33188,"size":2206,"sha256":"e6af24e3b9f1240abb8618fac326ee3a1ecccd25d2fa4936b2a28b0b0880e550"},{"path":"/usr/share/zoneinfo/America/Godthab","mode":33188,"size":1892,"sha256":"356cd2d4e74c958622b77385ae0509b5ea87e691f21207230f6fe1fa67e220af"},{"path":"/usr/share/zoneinfo/America/Goose_Bay","mode":33188,"size":3219,"sha256":"f0c06c6a1841cdc37bfb311c11caba1c974d0d6c27725c04b69657e7ca112a49"},{"path":"/usr/share/zoneinfo/America/Grand_Turk","mode":33188,"size":1881,"sha256":"90848fabb8bcfdbb4e66f5a624c4e7fa88962f16f8b6005f527cd84abebfa574"},{"path":"/usr/share/zoneinfo/America/Grenada","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Guadeloupe","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Guatemala","mode":33188,"size":306,"sha256":"795cc25e5ffe825a8b3d86eed98ad5f9bb9f6d152df2b624f0e2a63b17f0ee43"},{"path":"/usr/share/zoneinfo/America/Guayaquil","mode":33188,"size":271,"sha256":"6f52c0cff32100d797e64032c4ce19fa5a94b75b7678f1beb3c0cb549cdc00f7"},{"path":"/usr/share/zoneinfo/America/Guyana","mode":33188,"size":266,"sha256":"ffa4db9ef9c8a2902355de59b3693aa3dabd21e7a06054772bfcd754902e9342"},{"path":"/usr/share/zoneinfo/America/Halifax","mode":33188,"size":3438,"sha256":"627e18218c6f3c3f446c4970abe8164672e2a7ba94bcf841b1e06af5089b94ea"},{"path":"/usr/share/zoneinfo/America/Havana","mode":33188,"size":2437,"sha256":"7871f875a8819f415c292519db1590556a0dc1a6ce691bf4f7af55e6716fb894"},{"path":"/usr/share/zoneinfo/America/Hermosillo","mode":33188,"size":454,"sha256":"ec6eb21d068f1ca8e80a9e825206ad1b5a04b1e8abb2dd981c6c90b7686b8820"},{"path":"/usr/share/zoneinfo/America/Indiana/Indianapolis","mode":33188,"size":1675,"sha256":"55c2f3feb241f88435e9876e76e2c69ddfd0dfd36a273b551ff480e2cfad99fe"},{"path":"/usr/share/zoneinfo/America/Indiana/Knox","mode":33188,"size":2437,"sha256":"9e75dd6c52c5339c8e2b195ff8ac6a7212e2c5e84b2be3023cc355972c20d856"},{"path":"/usr/share/zoneinfo/America/Indiana/Marengo","mode":33188,"size":1731,"sha256":"64bb87669a7c161454b283e5855e28de7655450680cc403eea0572e580eb2625"},{"path":"/usr/share/zoneinfo/America/Indiana/Petersburg","mode":33188,"size":1913,"sha256":"3eb5dd510d677f9118ec4bca7892db4ed181722fbaf94ef9cb1a441718400321"},{"path":"/usr/share/zoneinfo/America/Indiana/Tell_City","mode":33188,"size":1693,"sha256":"6814c2b71389711819f44b98c880caf317c03a42064b2217103795114781a80f"},{"path":"/usr/share/zoneinfo/America/Indiana/Vevay","mode":33188,"size":1423,"sha256":"5cf728ac267cce51bddf1875219bf0e800d5aaa17794dc2c7408293773f516e5"},{"path":"/usr/share/zoneinfo/America/Indiana/Vincennes","mode":33188,"size":1703,"sha256":"8a9db38f7575f9e2a624c9466128927caef0eea7e9a3841679cd6eb129b019d3"},{"path":"/usr/share/zoneinfo/America/Indiana/Winamac","mode":33188,"size":1787,"sha256":"d2dc919207b8db95bd82aff68b8a498a6d3bec2c33220ba5381ebca171dcc095"},{"path":"/usr/share/zoneinfo/America/Indianapolis","mode":33188,"size":1675,"sha256":"55c2f3feb241f88435e9876e76e2c69ddfd0dfd36a273b551ff480e2cfad99fe"},{"path":"/usr/share/zoneinfo/America/Inuvik","mode":33188,"size":1928,"sha256":"ea64cbc0bf92cf88c8917222f11db8838f42e2d41360cd81bb93f669a2bc685b"},{"path":"/usr/share/zoneinfo/America/Iqaluit","mode":33188,"size":2046,"sha256":"eb8797250b8bd8c3d09893b4f261ffb1bedd668869a051c8e2c80f6c0d63408c"},{"path":"/usr/share/zoneinfo/America/Jamaica","mode":33188,"size":507,"sha256":"addb98caf3459bb75d6e14ed76aa66e642bead2d067e7fe81814a4f02cf13503"},{"path":"/usr/share/zoneinfo/America/Jujuy","mode":33188,"size":1081,"sha256":"233f43f895b08f21cd28918fbdb9c22892511c0996ac6212e019c3e866aca455"},{"path":"/usr/share/zoneinfo/America/Juneau","mode":33188,"size":2362,"sha256":"8185913ee68f7ec72cd98efcee68d1b6bd0c304e303a2dc613b06cd97e6333c8"},{"path":"/usr/share/zoneinfo/America/Kentucky/Louisville","mode":33188,"size":2781,"sha256":"31e1152a8de9463bcef2b5db10415965b96b83a93bd940609bc390bab963f384"},{"path":"/usr/share/zoneinfo/America/Kentucky/Monticello","mode":33188,"size":2361,"sha256":"b87081e46bbe688816a7e03cfdc5b4efe10bd6b92cb5a780df6b0c86af4c1a37"},{"path":"/usr/share/zoneinfo/America/Knox_IN","mode":33188,"size":2437,"sha256":"9e75dd6c52c5339c8e2b195ff8ac6a7212e2c5e84b2be3023cc355972c20d856"},{"path":"/usr/share/zoneinfo/America/Kralendijk","mode":33188,"size":212,"sha256":"023d877932f35d889772f561f79e266c8541b984e0ce2bd257723aafc7d883c1"},{"path":"/usr/share/zoneinfo/America/La_Paz","mode":33188,"size":257,"sha256":"1f10b013aea85ad55c3b3f65d68fa09bba4abe7fb5311018698823f0ab909a88"},{"path":"/usr/share/zoneinfo/America/Lima","mode":33188,"size":431,"sha256":"5f514d5245abb9de7c35fabed4c4cc86f6c027548cd1be04cc84b122878e1ad3"},{"path":"/usr/share/zoneinfo/America/Los_Angeles","mode":33188,"size":2845,"sha256":"fea9d66ff6522e69d22073dc4e84179b7cac2e372b398dc2fafdfdb61a9eb2e1"},{"path":"/usr/share/zoneinfo/America/Louisville","mode":33188,"size":2781,"sha256":"31e1152a8de9463bcef2b5db10415965b96b83a93bd940609bc390bab963f384"},{"path":"/usr/share/zoneinfo/America/Lower_Princes","mode":33188,"size":212,"sha256":"023d877932f35d889772f561f79e266c8541b984e0ce2bd257723aafc7d883c1"},{"path":"/usr/share/zoneinfo/America/Maceio","mode":33188,"size":770,"sha256":"3241ce8df0004a0cb5db2eb3800a3dfe770cc1d24d144fee27862c4dd7400840"},{"path":"/usr/share/zoneinfo/America/Managua","mode":33188,"size":463,"sha256":"a3c1f00bc879ee84e623d25252f1fb8ffd8cf43cd9c8b8bf12b6b5eda8045683"},{"path":"/usr/share/zoneinfo/America/Manaus","mode":33188,"size":630,"sha256":"e1213e7b97cfa580b4f9c728c34ffa64a6ab277b06b558893b299c20d3528e6c"},{"path":"/usr/share/zoneinfo/America/Marigot","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Martinique","mode":33188,"size":257,"sha256":"e087c3e4ae20234a08667adcf6ab4cd03ab3aeee7e035278f271ddb0b65cfff2"},{"path":"/usr/share/zoneinfo/America/Matamoros","mode":33188,"size":1416,"sha256":"4398d831df4bfcfd9bafa22ac35cd55dbb7dfd5f25c138452e8adf275ea11735"},{"path":"/usr/share/zoneinfo/America/Mazatlan","mode":33188,"size":1564,"sha256":"9340b719b250773262cec62e771d121105aed168836723dfc305e30bb04cfbb1"},{"path":"/usr/share/zoneinfo/America/Mendoza","mode":33188,"size":1109,"sha256":"d50f245cf1eeb3650dbbdd45720ddc6b1c5e22aede7981f20b9efe2c7ac68c4d"},{"path":"/usr/share/zoneinfo/America/Menominee","mode":33188,"size":2283,"sha256":"46ced580e74834d2c68a80a60ae05a0b715014bb2b4dad67cf994ac20ce2ac22"},{"path":"/usr/share/zoneinfo/America/Merida","mode":33188,"size":1456,"sha256":"ecdcf4b29f7b439152b9e9b559f04d7d4ba759dd942c2fd685a4ee36798fc8d1"},{"path":"/usr/share/zoneinfo/America/Metlakatla","mode":33188,"size":1432,"sha256":"9d091e1f411ccec6f2274317c53cc3ca45d6895f2c7497583e71ffca496716f3"},{"path":"/usr/share/zoneinfo/America/Mexico_City","mode":33188,"size":1618,"sha256":"88bc3fcb1a92ef053e0af4af9053ecbf12855fdf18f859b2a54d826dbfacb655"},{"path":"/usr/share/zoneinfo/America/Miquelon","mode":33188,"size":1696,"sha256":"21fabc9c2cafd8eef46af9126040cced6ef27d648d73d48951178143e6bb006b"},{"path":"/usr/share/zoneinfo/America/Moncton","mode":33188,"size":3163,"sha256":"1300d5a93bb376cbf23a890a23ea05fa2b229486e7eb7d5959c7834260fbb7b7"},{"path":"/usr/share/zoneinfo/America/Monterrey","mode":33188,"size":1416,"sha256":"89dadca852ebf52e4405c958132255c25fb195604d7df9b844bf50b48a0865d8"},{"path":"/usr/share/zoneinfo/America/Montevideo","mode":33188,"size":1564,"sha256":"550efc39d3e1c9e6909aa80a9d067f9355c47a874fcaf4f59302407ef6f968e1"},{"path":"/usr/share/zoneinfo/America/Montreal","mode":33188,"size":3503,"sha256":"842f7a103dfac9c0c2c33c9cc392a113d266ac064c5c7497883ab41b797ce194"},{"path":"/usr/share/zoneinfo/America/Montserrat","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Nassau","mode":33188,"size":2284,"sha256":"4c999dbcc6c6045acbedf6fd48f5b70b20eb8d8b0bd9612d2bea88dc03aa9f4d"},{"path":"/usr/share/zoneinfo/America/New_York","mode":33188,"size":3545,"sha256":"5fa6dccc303352e1195c4348b189f3085014d8a56a1976c8e8a32bd4fedb69fd"},{"path":"/usr/share/zoneinfo/America/Nipigon","mode":33188,"size":2131,"sha256":"7100ca4bf3044211ff8e770dade20b683880f3965f146ebbdd72c644aaec7c37"},{"path":"/usr/share/zoneinfo/America/Nome","mode":33188,"size":2376,"sha256":"d312bc797eb1b384ccfba0c40822d50b2e0abf37d5daa43dd3e255fdc7573b00"},{"path":"/usr/share/zoneinfo/America/Noronha","mode":33188,"size":742,"sha256":"cb4e968f415ed53e769108c9d5f9710e898716af74536d39b7077b0426f3960d"},{"path":"/usr/share/zoneinfo/America/North_Dakota/Beulah","mode":33188,"size":2389,"sha256":"f604eb42f0197f5edefcd6d43051a0b64e6e1327dbd2d3cfa94d0348b23e1fa8"},{"path":"/usr/share/zoneinfo/America/North_Dakota/Center","mode":33188,"size":2389,"sha256":"08efea4af9a2b6a5ab25e86116cfcf4b93c16ba9b7b22f762d9cb3481ecf3ac8"},{"path":"/usr/share/zoneinfo/America/North_Dakota/New_Salem","mode":33188,"size":2389,"sha256":"c5a43eb6776c326b1250f914f00e9e00e121b9b51f63665f90f245376da2017a"},{"path":"/usr/share/zoneinfo/America/Nuuk","mode":33188,"size":1892,"sha256":"356cd2d4e74c958622b77385ae0509b5ea87e691f21207230f6fe1fa67e220af"},{"path":"/usr/share/zoneinfo/America/Ojinaga","mode":33188,"size":1522,"sha256":"a07ff8fe3ee3531f866afca0f7937d86acec1826fb3eaa655d54300ec22dc713"},{"path":"/usr/share/zoneinfo/America/Panama","mode":33188,"size":203,"sha256":"fc4fbba14653a3186f3c5b719f7b9bf7d8a5824401064cf6d508205592e55a9f"},{"path":"/usr/share/zoneinfo/America/Pangnirtung","mode":33188,"size":2108,"sha256":"1b6a497653df9220c30a022d87ec2aa1320af9e51bb3cdc48756e72d770a6738"},{"path":"/usr/share/zoneinfo/America/Paramaribo","mode":33188,"size":296,"sha256":"57039b31a68b30ba0731916cffa7b9a1bbb52bf7650f7aa62052e89a8fc9edf6"},{"path":"/usr/share/zoneinfo/America/Phoenix","mode":33188,"size":353,"sha256":"9c013ecf82b6ed1dde235b5fc983fe9d23c8d56d610323f7c94c6ba3cd7b4564"},{"path":"/usr/share/zoneinfo/America/Port-au-Prince","mode":33188,"size":1455,"sha256":"b0b60ad1c557c41596e0fcc7fc8b9b39444c78295b147cee495e29985a225da6"},{"path":"/usr/share/zoneinfo/America/Port_of_Spain","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Porto_Acre","mode":33188,"size":662,"sha256":"16c86cccc93c7ebfeffae880e439ce848055e421578982d5cabef8aaec15f802"},{"path":"/usr/share/zoneinfo/America/Porto_Velho","mode":33188,"size":602,"sha256":"29f8daaa8fdca090df7145e69ecdc936cd3fedacea0b723f5c93da2a8c80f976"},{"path":"/usr/share/zoneinfo/America/Puerto_Rico","mode":33188,"size":255,"sha256":"7eee44e1cb7ac885fdd5042815c548bcb6ca84cff8de007e52b53c0b9ad53f19"},{"path":"/usr/share/zoneinfo/America/Punta_Arenas","mode":33188,"size":1911,"sha256":"33e26b3c8bf3dd7100151d3c1842ae9aa8ef69b15f961aa2eee2e1dc3508c6e5"},{"path":"/usr/share/zoneinfo/America/Rainy_River","mode":33188,"size":2131,"sha256":"9a7b8dd4c968de31fe35fd9fe075fad8afc15892067119f638b5aef0d2288d83"},{"path":"/usr/share/zoneinfo/America/Rankin_Inlet","mode":33188,"size":1930,"sha256":"b3ae38ccfa3091ebd8037fd5e1fd2715a72008932f94526a15fb1aa7fae722dc"},{"path":"/usr/share/zoneinfo/America/Recife","mode":33188,"size":742,"sha256":"cebb6d30c20b00bc437d4e0a8c6a0c91db120a3aef2c28bc56960f682b3fc30c"},{"path":"/usr/share/zoneinfo/America/Regina","mode":33188,"size":994,"sha256":"929d07457407529637626d09f5ca975b4f05801f35d0bfac4e3b0027efee6776"},{"path":"/usr/share/zoneinfo/America/Resolute","mode":33188,"size":1930,"sha256":"c529141807704725b059187b9f458080f911b6dd4313e74139d2c7dac287c901"},{"path":"/usr/share/zoneinfo/America/Rio_Branco","mode":33188,"size":662,"sha256":"16c86cccc93c7ebfeffae880e439ce848055e421578982d5cabef8aaec15f802"},{"path":"/usr/share/zoneinfo/America/Rosario","mode":33188,"size":1109,"sha256":"254a30f9b9b00558350d0c1f40a1d9c8738045bb7fe88e56c81bbb9fbd161026"},{"path":"/usr/share/zoneinfo/America/Santa_Isabel","mode":33188,"size":2356,"sha256":"d827b95b4fa16b8c56d9a1636341c9112657e567ae84b37a9bfca133ae31babb"},{"path":"/usr/share/zoneinfo/America/Santarem","mode":33188,"size":632,"sha256":"78440d01f4c5b7c13d1dbe6500ba71188efdcf90069979c80a224d831c8bd97b"},{"path":"/usr/share/zoneinfo/America/Santiago","mode":33188,"size":2538,"sha256":"b83e4129763ef7a22be3fba68029b4ecb6f14a360112498446d8c89640f420b5"},{"path":"/usr/share/zoneinfo/America/Santo_Domingo","mode":33188,"size":491,"sha256":"adf349e4c7314aaa699c4893c589b077f6dfa7d9a54ea9eae459658f9af41dc7"},{"path":"/usr/share/zoneinfo/America/Sao_Paulo","mode":33188,"size":1470,"sha256":"a4090cbdfa5168012d460585f7eab9302f8848cca0419d73cf03993ef12c08c4"},{"path":"/usr/share/zoneinfo/America/Scoresbysund","mode":33188,"size":1930,"sha256":"c668772d49326cde3798d158089d2f9ced43788f904360a6dc67a53868b28f96"},{"path":"/usr/share/zoneinfo/America/Shiprock","mode":33188,"size":2453,"sha256":"f4df3cc74c79d070a25a7927744d3a422a05d862a9a234a12105c5c964efb22d"},{"path":"/usr/share/zoneinfo/America/Sitka","mode":33188,"size":2350,"sha256":"ba79b89ecd8e64dba4119f2c5af2373167557c4bc71b7b134ab252e0b7485fdb"},{"path":"/usr/share/zoneinfo/America/St_Barthelemy","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/St_Johns","mode":33188,"size":3664,"sha256":"2b960a58d6d3f6a272707f941f55b15b8ba3fd0fd55f8680ea84af6b1e98bae0"},{"path":"/usr/share/zoneinfo/America/St_Kitts","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/St_Lucia","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/St_Thomas","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/St_Vincent","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Swift_Current","mode":33188,"size":574,"sha256":"6b6029f04ac07c382e20d315da7a72d9204d813ef83585f042562e7f6788a78f"},{"path":"/usr/share/zoneinfo/America/Tegucigalpa","mode":33188,"size":278,"sha256":"fd295a9cc689a966786b6e0ec9d0f101796ac8b4f04a6f529b192937df3a2115"},{"path":"/usr/share/zoneinfo/America/Thule","mode":33188,"size":1528,"sha256":"9a474a1fc764343470d310369cdbf6d7007ea611116e25bea68f60ddf5a6cd68"},{"path":"/usr/share/zoneinfo/America/Thunder_Bay","mode":33188,"size":2211,"sha256":"aef45e1474369f52e1afb1cd7f312e9f035ca13686092cf2351a353133e1cee6"},{"path":"/usr/share/zoneinfo/America/Tijuana","mode":33188,"size":2356,"sha256":"d827b95b4fa16b8c56d9a1636341c9112657e567ae84b37a9bfca133ae31babb"},{"path":"/usr/share/zoneinfo/America/Toronto","mode":33188,"size":3503,"sha256":"842f7a103dfac9c0c2c33c9cc392a113d266ac064c5c7497883ab41b797ce194"},{"path":"/usr/share/zoneinfo/America/Tortola","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Vancouver","mode":33188,"size":2901,"sha256":"460182c93960fd636820b1b43cfec871da4f0197556bb6bdb2fa527b637a4332"},{"path":"/usr/share/zoneinfo/America/Virgin","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/America/Whitehorse","mode":33188,"size":1609,"sha256":"e4afd69d844499d8bf3bb276d3ecab98ac10cddb21c180b6717e5635485ccf38"},{"path":"/usr/share/zoneinfo/America/Winnipeg","mode":33188,"size":2891,"sha256":"77be5c08f6f8ebe5330fb86a60c4447ea2549620609f4ef6a7a7a68d1a12d9d6"},{"path":"/usr/share/zoneinfo/America/Yakutat","mode":33188,"size":2314,"sha256":"07f189f49873b1392989ecbde19d19d33cd6c16953bf7e6b927ca2f1040f7106"},{"path":"/usr/share/zoneinfo/America/Yellowknife","mode":33188,"size":1980,"sha256":"3140de7fe4136fb4920e8bb8ed8d707256e78c672edfce1657ae22672de68768"},{"path":"/usr/share/zoneinfo/Antarctica/Casey","mode":33188,"size":311,"sha256":"008325b0ed1b879047cfd030ccd24cb2fdaaeecdeaedc273f77aaa888ade3136"},{"path":"/usr/share/zoneinfo/Antarctica/Davis","mode":33188,"size":311,"sha256":"8dec77b2a23389d30c680a6fb0241cae32f1c0c71bf28fde1679bdb035a2939b"},{"path":"/usr/share/zoneinfo/Antarctica/DumontDUrville","mode":33188,"size":216,"sha256":"86d1e72a7cad1d9817f57d456e39184b749436a02783a272f2109994addfbd55"},{"path":"/usr/share/zoneinfo/Antarctica/Macquarie","mode":33188,"size":1543,"sha256":"edccaab42adcfc7fa4872ff22b63fdc128a3354fa7d443f895b8f7068ced788f"},{"path":"/usr/share/zoneinfo/Antarctica/Mawson","mode":33188,"size":225,"sha256":"afa4aec36d9ff91992970b4c645e038810f25d8e58118a56568dbc9226704543"},{"path":"/usr/share/zoneinfo/Antarctica/McMurdo","mode":33188,"size":2460,"sha256":"d7b5175387ac78e29f7b9021e411512756be283ed3d1819942ef5d45ecf338e4"},{"path":"/usr/share/zoneinfo/Antarctica/Palmer","mode":33188,"size":1432,"sha256":"aa3fc7dd1b1f1599bf71ed328ae5dba81e09ac3e3a914689e7ea5ff3adc28183"},{"path":"/usr/share/zoneinfo/Antarctica/Rothera","mode":33188,"size":186,"sha256":"e67d9eb78b53d3a415865402758eca495c69c347ed0ca7d5a0238c5f7ac01d8b"},{"path":"/usr/share/zoneinfo/Antarctica/South_Pole","mode":33188,"size":2460,"sha256":"d7b5175387ac78e29f7b9021e411512756be283ed3d1819942ef5d45ecf338e4"},{"path":"/usr/share/zoneinfo/Antarctica/Syowa","mode":33188,"size":187,"sha256":"aef765ec9b3fae2cedbbaf2b525505008aa24f2f4e06abae3f770a9677387879"},{"path":"/usr/share/zoneinfo/Antarctica/Troll","mode":33188,"size":1176,"sha256":"1d8bdfe767292729981993a64fd8a2f745b24058c8bcbcf21bf3b0b6d5075c2d"},{"path":"/usr/share/zoneinfo/Antarctica/Vostok","mode":33188,"size":187,"sha256":"903d2010d8a06be20cd57000e89d92e6f8307dca3810294215a58cd7c7c863e2"},{"path":"/usr/share/zoneinfo/Arctic/Longyearbyen","mode":33188,"size":2251,"sha256":"0fa4e635da2b178fa3ea13ff3829c702844cf8bd69e16bca8e1d34dbd9249d01"},{"path":"/usr/share/zoneinfo/Asia/Aden","mode":33188,"size":187,"sha256":"3102c1755d9a64b2e2b363381bbf52d6a01eb866a4d2cdfd0cf7e0832517094d"},{"path":"/usr/share/zoneinfo/Asia/Almaty","mode":33188,"size":1031,"sha256":"4401628c6d2a36430efdddec3d9aeb9ff091e85daa21d0783298cddfe70c38c4"},{"path":"/usr/share/zoneinfo/Asia/Amman","mode":33188,"size":1877,"sha256":"ba18a1f823f77e478e7030eeb82ddd71a5f3fae6efdf56325b7776304912da08"},{"path":"/usr/share/zoneinfo/Asia/Anadyr","mode":33188,"size":1222,"sha256":"b4b88045d6624e21cb233c7c6226edee88afb63e0ca8d4e3df580d74a6c8a34c"},{"path":"/usr/share/zoneinfo/Asia/Aqtau","mode":33188,"size":1017,"sha256":"e2e79c79371b0c8601cc8da9dc613145b60721e9c574310ed4b7fa9ae9baa30b"},{"path":"/usr/share/zoneinfo/Asia/Aqtobe","mode":33188,"size":1047,"sha256":"ccd2ab0718fc8a637bb44576e4ca3ff267151cc4081dc697e69ebd426dbe4c1d"},{"path":"/usr/share/zoneinfo/Asia/Ashgabat","mode":33188,"size":651,"sha256":"46284acf00fcee991886ee879f507f970bef4105a05d5e330736a02b329d3375"},{"path":"/usr/share/zoneinfo/Asia/Ashkhabad","mode":33188,"size":651,"sha256":"46284acf00fcee991886ee879f507f970bef4105a05d5e330736a02b329d3375"},{"path":"/usr/share/zoneinfo/Asia/Atyrau","mode":33188,"size":1025,"sha256":"44812ada1ccc49ab42dd04e3c5ebe8f9f592682765b0e400972662c34ef6e931"},{"path":"/usr/share/zoneinfo/Asia/Baghdad","mode":33188,"size":1004,"sha256":"942ba9632d564f1e29f60e75a7edf598d3b001515ecdd7d403b147e5bf703cb1"},{"path":"/usr/share/zoneinfo/Asia/Bahrain","mode":33188,"size":225,"sha256":"f15d455b503a1d9b99a9bc15f27e0d87d9bf3cac8100709f6a3140e63bab56bd"},{"path":"/usr/share/zoneinfo/Asia/Baku","mode":33188,"size":1269,"sha256":"8efffa197f6ee0747d60f4b37db8823d2f712f3df7350bfb40461641d9e7ca31"},{"path":"/usr/share/zoneinfo/Asia/Bangkok","mode":33188,"size":220,"sha256":"cf866703a05b067069db05f87584d5c8a3489bcaad3e41bb012609904915c11b"},{"path":"/usr/share/zoneinfo/Asia/Barnaul","mode":33188,"size":1255,"sha256":"b556552d881c7729f21a4fb10c5e75e3885afc08e539461d40d6e4e359dcdd7f"},{"path":"/usr/share/zoneinfo/Asia/Beirut","mode":33188,"size":2175,"sha256":"abdfa509ed982455873c1035962d8642ae8b88ab75f7f1a9a4cf7eea5ce120ef"},{"path":"/usr/share/zoneinfo/Asia/Bishkek","mode":33188,"size":1045,"sha256":"8b449cf64ad7d46bae4196787f47012bfd0899aafd7cac77f8794dd7730b41ee"},{"path":"/usr/share/zoneinfo/Asia/Brunei","mode":33188,"size":229,"sha256":"cd14c89f40eaece7f87f9679ebd6fdc23356c1ee31da031400c59806044ca4d1"},{"path":"/usr/share/zoneinfo/Asia/Calcutta","mode":33188,"size":312,"sha256":"c71d7bc10d52c64f59eae8eac701c1b156bbec3fd9fe750970bed15e9b408fa5"},{"path":"/usr/share/zoneinfo/Asia/Chita","mode":33188,"size":1257,"sha256":"3bc537b6c3f62fbcd134ce4c8e58c351a5770b9216f2483f1e36d8ec9035b3bc"},{"path":"/usr/share/zoneinfo/Asia/Choibalsan","mode":33188,"size":991,"sha256":"6ea08272fe78ef15058b5821d053e907ea937db9bb6ca8f71cb9997a44c64315"},{"path":"/usr/share/zoneinfo/Asia/Chongqing","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/Asia/Chungking","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/Asia/Colombo","mode":33188,"size":413,"sha256":"60108a5aec08236b5e9132d33de72649cdf01f854c86d01a8bd609d820b569ba"},{"path":"/usr/share/zoneinfo/Asia/Dacca","mode":33188,"size":370,"sha256":"b17631c1fb3033ffde15391d2fbec4e3d29b846fd2cfb089898c6b61308eb7b2"},{"path":"/usr/share/zoneinfo/Asia/Damascus","mode":33188,"size":2320,"sha256":"0f42d5702ee52944dde43071569de645a5d668a385c4a2e0cd8aa43d39d2ea21"},{"path":"/usr/share/zoneinfo/Asia/Dhaka","mode":33188,"size":370,"sha256":"b17631c1fb3033ffde15391d2fbec4e3d29b846fd2cfb089898c6b61308eb7b2"},{"path":"/usr/share/zoneinfo/Asia/Dili","mode":33188,"size":253,"sha256":"1f691df244d73613de758975adca5454ee9a91821b3f4382ea9b793ef04b1fc4"},{"path":"/usr/share/zoneinfo/Asia/Dubai","mode":33188,"size":187,"sha256":"52c19684fb4943773d86c43f78c7ad7b46ae7557a8ae9ed16508342bd319678a"},{"path":"/usr/share/zoneinfo/Asia/Dushanbe","mode":33188,"size":621,"sha256":"e832524a0d020a34015e423182bec05920c1e73b4149aab1bb31b7479a0a8f4c"},{"path":"/usr/share/zoneinfo/Asia/Famagusta","mode":33188,"size":2042,"sha256":"4a3e66759c060ff5d9e338169781678161df5b9acd9aec6146f1d4d3cfd9030b"},{"path":"/usr/share/zoneinfo/Asia/Gaza","mode":33188,"size":2351,"sha256":"9c1013e60b7005b6909a9ed2eac9490f682ed99367023eb7f324f73f4958b66b"},{"path":"/usr/share/zoneinfo/Asia/Harbin","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/Asia/Hebron","mode":33188,"size":2379,"sha256":"c591e178b7f704a365468e6e933004b798303e100142f6d940bd8e45a061903d"},{"path":"/usr/share/zoneinfo/Asia/Ho_Chi_Minh","mode":33188,"size":389,"sha256":"013ffccf1a05a9e7b509b55f6b949569dd9e676bfcce10c886fffe59745440e5"},{"path":"/usr/share/zoneinfo/Asia/Hong_Kong","mode":33188,"size":1231,"sha256":"680a46ee9866bd0c8435fef70694663c1e8ca2ba1e50ff2979ad62f27295707a"},{"path":"/usr/share/zoneinfo/Asia/Hovd","mode":33188,"size":921,"sha256":"cdc65f913f2b67cd1d23286944546c42fabb64720b78aaf32f88605a1943689a"},{"path":"/usr/share/zoneinfo/Asia/Irkutsk","mode":33188,"size":1276,"sha256":"77ed8a38a9f3e4a65a5ded6a846089c4c8a60eb245c476f7ee20d62780303eef"},{"path":"/usr/share/zoneinfo/Asia/Istanbul","mode":33188,"size":1970,"sha256":"2f24f072fa325c0a9bbecc48ea2782317c459a6cad941a37f7e305238443c45a"},{"path":"/usr/share/zoneinfo/Asia/Jakarta","mode":33188,"size":392,"sha256":"7ea1c3e53a0d3f40cb6d7724f1bacb4fca1cf0ae96d9ab42f00f2d30dc0dee3a"},{"path":"/usr/share/zoneinfo/Asia/Jayapura","mode":33188,"size":251,"sha256":"c6fa24de2e83f471878b8e10ecd68828eb3aba1f49ce462dac7721661386eb0c"},{"path":"/usr/share/zoneinfo/Asia/Jerusalem","mode":33188,"size":2321,"sha256":"1e61da0baf4d2d8f149ed84b8694cc5d4aadbee78d2014771417a67622e653fa"},{"path":"/usr/share/zoneinfo/Asia/Kabul","mode":33188,"size":229,"sha256":"386b98b95b19bbec52c6d8f334e04a178f4f99f2b8a1cea33c142375668d7227"},{"path":"/usr/share/zoneinfo/Asia/Kamchatka","mode":33188,"size":1198,"sha256":"a45d587c7134607cb6feade6af9a04203c38b1ed481f7c7ce8eb10e7cd972cac"},{"path":"/usr/share/zoneinfo/Asia/Karachi","mode":33188,"size":417,"sha256":"fc4b2a68ad79efadecf52f333fa19cbaa5dd084cdc9bf96ab8b65a75c559a370"},{"path":"/usr/share/zoneinfo/Asia/Kashgar","mode":33188,"size":187,"sha256":"9ae8868df5441ce4ac33aaed777f5ea6883eb95050b7d66d1e5ec5648c9e3fcc"},{"path":"/usr/share/zoneinfo/Asia/Kathmandu","mode":33188,"size":238,"sha256":"5c557b86c5f0fdd19d105afbd38bd9daaad1cd075e9efdbe80547ddca85ae5ae"},{"path":"/usr/share/zoneinfo/Asia/Katmandu","mode":33188,"size":238,"sha256":"5c557b86c5f0fdd19d105afbd38bd9daaad1cd075e9efdbe80547ddca85ae5ae"},{"path":"/usr/share/zoneinfo/Asia/Khandyga","mode":33188,"size":1311,"sha256":"0169f2ad82832f6466984cad9cc673fb4098ee15e14b21521ce54f37a3fa6de3"},{"path":"/usr/share/zoneinfo/Asia/Kolkata","mode":33188,"size":312,"sha256":"c71d7bc10d52c64f59eae8eac701c1b156bbec3fd9fe750970bed15e9b408fa5"},{"path":"/usr/share/zoneinfo/Asia/Krasnoyarsk","mode":33188,"size":1243,"sha256":"9122ec3df9d2f1e1767edfbc9cce49e7cff95491cb9de234c4588f985eb361c8"},{"path":"/usr/share/zoneinfo/Asia/Kuala_Lumpur","mode":33188,"size":424,"sha256":"268d3cc29dae9854fea1b9109da2873602c48806994d3f3df0b9ca9863fcf59b"},{"path":"/usr/share/zoneinfo/Asia/Kuching","mode":33188,"size":521,"sha256":"0d0c68d2cddcf9431056b27b884c89951de456a484fdf96a2b10c78faf195bd8"},{"path":"/usr/share/zoneinfo/Asia/Kuwait","mode":33188,"size":187,"sha256":"3102c1755d9a64b2e2b363381bbf52d6a01eb866a4d2cdfd0cf7e0832517094d"},{"path":"/usr/share/zoneinfo/Asia/Macao","mode":33188,"size":1255,"sha256":"bc423d28d8ba83fb0ba6984472c46dc83c014dd4876b59f6c8e2a4d8761fc585"},{"path":"/usr/share/zoneinfo/Asia/Macau","mode":33188,"size":1255,"sha256":"bc423d28d8ba83fb0ba6984472c46dc83c014dd4876b59f6c8e2a4d8761fc585"},{"path":"/usr/share/zoneinfo/Asia/Magadan","mode":33188,"size":1258,"sha256":"a32f022b2aa9b370f41866047c28b6d96007bec7e7f05e4fd1a2f06111057e8b"},{"path":"/usr/share/zoneinfo/Asia/Makassar","mode":33188,"size":288,"sha256":"24fac901695ef43b73fa8b3cd9e4bf893ceb757c5200b6628ae6a0fc70f01956"},{"path":"/usr/share/zoneinfo/Asia/Manila","mode":33188,"size":359,"sha256":"01cb854c5033bef7324b3102f4362206e1a792d703a478fe090135943b180392"},{"path":"/usr/share/zoneinfo/Asia/Muscat","mode":33188,"size":187,"sha256":"52c19684fb4943773d86c43f78c7ad7b46ae7557a8ae9ed16508342bd319678a"},{"path":"/usr/share/zoneinfo/Asia/Nicosia","mode":33188,"size":2016,"sha256":"f2aa2a3f77a43b7558a7508a6cd6c50fdf7d991f9d64da5948fd9003923b1d72"},{"path":"/usr/share/zoneinfo/Asia/Novokuznetsk","mode":33188,"size":1197,"sha256":"45df208266ce41dccdae6a47b6b78235a2e70c4eeb69b28e30125e03e7b9e0d3"},{"path":"/usr/share/zoneinfo/Asia/Novosibirsk","mode":33188,"size":1255,"sha256":"53f555c078378d726db6d203c96bee7efc9b138c10cfd634f750b28cb6212ba5"},{"path":"/usr/share/zoneinfo/Asia/Omsk","mode":33188,"size":1243,"sha256":"e32bfb976274657a892f5918b3f42e56c838dac040e06ac60c2d36318c80fd49"},{"path":"/usr/share/zoneinfo/Asia/Oral","mode":33188,"size":1039,"sha256":"4ddd665f81f9ffe7fa3c7540f5065ddad72274da22913885eefe86951a857998"},{"path":"/usr/share/zoneinfo/Asia/Phnom_Penh","mode":33188,"size":220,"sha256":"cf866703a05b067069db05f87584d5c8a3489bcaad3e41bb012609904915c11b"},{"path":"/usr/share/zoneinfo/Asia/Pontianak","mode":33188,"size":395,"sha256":"2516ac2bc84fe6498a50bc8865ec00e3499b38f2f485403cd5028578a98d1fd8"},{"path":"/usr/share/zoneinfo/Asia/Pyongyang","mode":33188,"size":267,"sha256":"a108bfd54c6c22fbc67177c281c1058dfb1f00f40803ffc04fda5f41d4ba6505"},{"path":"/usr/share/zoneinfo/Asia/Qatar","mode":33188,"size":225,"sha256":"f15d455b503a1d9b99a9bc15f27e0d87d9bf3cac8100709f6a3140e63bab56bd"},{"path":"/usr/share/zoneinfo/Asia/Qostanay","mode":33188,"size":1047,"sha256":"b763af98dc579384866d60e3541d7f87c10b492310a4bdd3f927d28d091edeca"},{"path":"/usr/share/zoneinfo/Asia/Qyzylorda","mode":33188,"size":1077,"sha256":"e116692a053d3b100258a742dd5577df8ae1e262d0f23830606c87b80031d4a2"},{"path":"/usr/share/zoneinfo/Asia/Rangoon","mode":33188,"size":297,"sha256":"1b4605825adbae3c7136f3f055d7cbac76faad62703516eaf94fc8d10e1df3ad"},{"path":"/usr/share/zoneinfo/Asia/Riyadh","mode":33188,"size":187,"sha256":"3102c1755d9a64b2e2b363381bbf52d6a01eb866a4d2cdfd0cf7e0832517094d"},{"path":"/usr/share/zoneinfo/Asia/Saigon","mode":33188,"size":389,"sha256":"013ffccf1a05a9e7b509b55f6b949569dd9e676bfcce10c886fffe59745440e5"},{"path":"/usr/share/zoneinfo/Asia/Sakhalin","mode":33188,"size":1234,"sha256":"d6af67dd853ea20ec92aa39fdd647b70ec329606e7565536030dbdd70f062148"},{"path":"/usr/share/zoneinfo/Asia/Samarkand","mode":33188,"size":619,"sha256":"fd928b56ff2b6fdf1e28c198d8871e87979473109dfc395a51d8aaed0efb5924"},{"path":"/usr/share/zoneinfo/Asia/Seoul","mode":33188,"size":659,"sha256":"3673a9439d49ea97b47c9fb28433c6d41c469ca03ad320768f1514d075647c26"},{"path":"/usr/share/zoneinfo/Asia/Shanghai","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/Asia/Singapore","mode":33188,"size":424,"sha256":"e6929fde43ffc48bbac4081b31bbf7fd42643b3c26fadf322bdeadeb23cfc748"},{"path":"/usr/share/zoneinfo/Asia/Srednekolymsk","mode":33188,"size":1244,"sha256":"35c545e24d61a31f5fd4fa712d8b6cc09ecbdfddee10e5b859d6b29e57d98806"},{"path":"/usr/share/zoneinfo/Asia/Taipei","mode":33188,"size":790,"sha256":"25cfd02bc847bdcb11e586445ba886a76315f1f9be86f7e74944a6e8e8644543"},{"path":"/usr/share/zoneinfo/Asia/Tashkent","mode":33188,"size":635,"sha256":"8674eb501cd25c540258e94006ce151f91f653849e800aa97986551b89ead688"},{"path":"/usr/share/zoneinfo/Asia/Tbilisi","mode":33188,"size":1080,"sha256":"bc88efdf57da66aaa71c15d8fbc36d87242adca776e103ddd5531aa45ca21177"},{"path":"/usr/share/zoneinfo/Asia/Tehran","mode":33188,"size":2624,"sha256":"29fc1861f6e088decab370c3ef2c090d0c3fbdea50b78c2d3158ddaf001b8088"},{"path":"/usr/share/zoneinfo/Asia/Tel_Aviv","mode":33188,"size":2321,"sha256":"1e61da0baf4d2d8f149ed84b8694cc5d4aadbee78d2014771417a67622e653fa"},{"path":"/usr/share/zoneinfo/Asia/Thimbu","mode":33188,"size":229,"sha256":"e54c4d565a4be5f34209ba351c7aadd1071dccf8a0380d69e06e936a425203a2"},{"path":"/usr/share/zoneinfo/Asia/Thimphu","mode":33188,"size":229,"sha256":"e54c4d565a4be5f34209ba351c7aadd1071dccf8a0380d69e06e936a425203a2"},{"path":"/usr/share/zoneinfo/Asia/Tokyo","mode":33188,"size":318,"sha256":"046bb09bc08554ef8a54dc05685d0eab10e04c692f6320b6091b6a6f07214c83"},{"path":"/usr/share/zoneinfo/Asia/Tomsk","mode":33188,"size":1255,"sha256":"1142db40b91678b4ab3c2935346f6f0bce6a84353392a1ab97dbeba0ee1582d5"},{"path":"/usr/share/zoneinfo/Asia/Ujung_Pandang","mode":33188,"size":288,"sha256":"24fac901695ef43b73fa8b3cd9e4bf893ceb757c5200b6628ae6a0fc70f01956"},{"path":"/usr/share/zoneinfo/Asia/Ulaanbaatar","mode":33188,"size":921,"sha256":"17a31d0ea8eaf0d1484b54e53d6803eaeaa832740d521a340e1d5c073de97e22"},{"path":"/usr/share/zoneinfo/Asia/Ulan_Bator","mode":33188,"size":921,"sha256":"17a31d0ea8eaf0d1484b54e53d6803eaeaa832740d521a340e1d5c073de97e22"},{"path":"/usr/share/zoneinfo/Asia/Urumqi","mode":33188,"size":187,"sha256":"9ae8868df5441ce4ac33aaed777f5ea6883eb95050b7d66d1e5ec5648c9e3fcc"},{"path":"/usr/share/zoneinfo/Asia/Ust-Nera","mode":33188,"size":1290,"sha256":"ab0edbe8871813e11548d34641521878aca12634a44683945d24ef85016bd0aa"},{"path":"/usr/share/zoneinfo/Asia/Vientiane","mode":33188,"size":220,"sha256":"cf866703a05b067069db05f87584d5c8a3489bcaad3e41bb012609904915c11b"},{"path":"/usr/share/zoneinfo/Asia/Vladivostok","mode":33188,"size":1244,"sha256":"32eb6e1405aa048e6cba3396d4b09ad04ed05c239dbcb054f82e4dbbd2dbbd31"},{"path":"/usr/share/zoneinfo/Asia/Yakutsk","mode":33188,"size":1243,"sha256":"545036a8cb48068d5f6f98bd28eb90bb6c25d3136b58f01486b875780519208e"},{"path":"/usr/share/zoneinfo/Asia/Yangon","mode":33188,"size":297,"sha256":"1b4605825adbae3c7136f3f055d7cbac76faad62703516eaf94fc8d10e1df3ad"},{"path":"/usr/share/zoneinfo/Asia/Yekaterinburg","mode":33188,"size":1281,"sha256":"8819eff29a90ad2c0d3588f56d6e974d99419e80104bfc9313274f0a33e0b590"},{"path":"/usr/share/zoneinfo/Asia/Yerevan","mode":33188,"size":1213,"sha256":"2e456011e9e0d8c1958c17bf34116fe89a3239028010e7db61ae46012c8f2304"},{"path":"/usr/share/zoneinfo/Atlantic/Azores","mode":33188,"size":3493,"sha256":"d3dfcd9c77d1e2a49e15c87aff9e43f0d5283a532b4bc6c7afa22fa14fa0c377"},{"path":"/usr/share/zoneinfo/Atlantic/Bermuda","mode":33188,"size":2004,"sha256":"462d205904f32dcb79317f83ddb4dea1548d51849217dc3e42ba17c3cc7fcf08"},{"path":"/usr/share/zoneinfo/Atlantic/Canary","mode":33188,"size":1911,"sha256":"4617cb1aa75514003f181908e9ccfc1d3d062ef22bb0196867dbe530ec2e1416"},{"path":"/usr/share/zoneinfo/Atlantic/Cape_Verde","mode":33188,"size":284,"sha256":"f7a81342ed5884f34fdc07e6ebf8f0f322e41ba3e2d399d7f516b4d28771350b"},{"path":"/usr/share/zoneinfo/Atlantic/Faeroe","mode":33188,"size":1829,"sha256":"6b1a5769f8ffa2ec29bf298dffd7fb324e625e36fc527c14bb66b6520e6f76a7"},{"path":"/usr/share/zoneinfo/Atlantic/Faroe","mode":33188,"size":1829,"sha256":"6b1a5769f8ffa2ec29bf298dffd7fb324e625e36fc527c14bb66b6520e6f76a7"},{"path":"/usr/share/zoneinfo/Atlantic/Jan_Mayen","mode":33188,"size":2251,"sha256":"0fa4e635da2b178fa3ea13ff3829c702844cf8bd69e16bca8e1d34dbd9249d01"},{"path":"/usr/share/zoneinfo/Atlantic/Madeira","mode":33188,"size":3484,"sha256":"24c616780589fb6a7e22913e3402522517ba4a7460738ccd38f1a3a0e4a21f40"},{"path":"/usr/share/zoneinfo/Atlantic/Reykjavik","mode":33188,"size":1188,"sha256":"9cdcea6aa1eed8276d3f6620e0c0ffae9cfcc3722c443ea6ba39147975eafaa3"},{"path":"/usr/share/zoneinfo/Atlantic/South_Georgia","mode":33188,"size":181,"sha256":"f745dca3964c6ae3e8b88166e0db6df487ee8f6e6ad7fb1ac3ad4e6ab2e0a361"},{"path":"/usr/share/zoneinfo/Atlantic/St_Helena","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/Atlantic/Stanley","mode":33188,"size":1251,"sha256":"57ee27fac7d72ba2c34725702e5876aa27462a09ac4b841b40122afe103a4c41"},{"path":"/usr/share/zoneinfo/Australia/ACT","mode":33188,"size":2223,"sha256":"b540f8e21ed6a6b262336e0eb020c18ab43f283e9774613dd9864239523e4233"},{"path":"/usr/share/zoneinfo/Australia/Adelaide","mode":33188,"size":2238,"sha256":"735476eef81652d7189574f8b7a11c942a986aba24b6ddc644fbebd1eb49245c"},{"path":"/usr/share/zoneinfo/Australia/Brisbane","mode":33188,"size":452,"sha256":"74ac9f5d1d15ef0f6bd9e69c687b9047fb1f749c59279475685721f574b427cc"},{"path":"/usr/share/zoneinfo/Australia/Broken_Hill","mode":33188,"size":2274,"sha256":"d6451675d3b5afb8572e2cbb4d381730da23daa3bfcb57601fe6f815985237db"},{"path":"/usr/share/zoneinfo/Australia/Canberra","mode":33188,"size":2223,"sha256":"b540f8e21ed6a6b262336e0eb020c18ab43f283e9774613dd9864239523e4233"},{"path":"/usr/share/zoneinfo/Australia/Currie","mode":33188,"size":2223,"sha256":"543c7afaebfdd907f8d637efce48bf41c407da72658b8e9c12f7208a54d1d84a"},{"path":"/usr/share/zoneinfo/Australia/Darwin","mode":33188,"size":323,"sha256":"6172d8687a78608d884b04903d36053bdfb56433541930b2a42b405cbb62dc0b"},{"path":"/usr/share/zoneinfo/Australia/Eucla","mode":33188,"size":503,"sha256":"42c7f9c44cf8dbfd564a7539b86278d98285476578bef4bfc01cc3fc61ebb2ba"},{"path":"/usr/share/zoneinfo/Australia/Hobart","mode":33188,"size":2335,"sha256":"de1bb5e82f86774e70082b906462e02a062238e5c4d76149566e21b1cb31b23a"},{"path":"/usr/share/zoneinfo/Australia/LHI","mode":33188,"size":1889,"sha256":"09626975ee86238fd5f85bc275eafad83bc696709d78144cc0bd4ced75acaf2d"},{"path":"/usr/share/zoneinfo/Australia/Lindeman","mode":33188,"size":522,"sha256":"663df35f044a15c743b9716e183595147d0c1838e99148a9473623ac82076bf9"},{"path":"/usr/share/zoneinfo/Australia/Lord_Howe","mode":33188,"size":1889,"sha256":"09626975ee86238fd5f85bc275eafad83bc696709d78144cc0bd4ced75acaf2d"},{"path":"/usr/share/zoneinfo/Australia/Melbourne","mode":33188,"size":2223,"sha256":"272c1f13d01e35e6a58855cbb53878795451928adbf0c8ca2982b79db1f450a7"},{"path":"/usr/share/zoneinfo/Australia/NSW","mode":33188,"size":2223,"sha256":"b540f8e21ed6a6b262336e0eb020c18ab43f283e9774613dd9864239523e4233"},{"path":"/usr/share/zoneinfo/Australia/North","mode":33188,"size":323,"sha256":"6172d8687a78608d884b04903d36053bdfb56433541930b2a42b405cbb62dc0b"},{"path":"/usr/share/zoneinfo/Australia/Perth","mode":33188,"size":479,"sha256":"4ecd4a085ca9ec5b7903016c2d4e311276024a2bcd0c35d40281658e48421f93"},{"path":"/usr/share/zoneinfo/Australia/Queensland","mode":33188,"size":452,"sha256":"74ac9f5d1d15ef0f6bd9e69c687b9047fb1f749c59279475685721f574b427cc"},{"path":"/usr/share/zoneinfo/Australia/South","mode":33188,"size":2238,"sha256":"735476eef81652d7189574f8b7a11c942a986aba24b6ddc644fbebd1eb49245c"},{"path":"/usr/share/zoneinfo/Australia/Sydney","mode":33188,"size":2223,"sha256":"b540f8e21ed6a6b262336e0eb020c18ab43f283e9774613dd9864239523e4233"},{"path":"/usr/share/zoneinfo/Australia/Tasmania","mode":33188,"size":2335,"sha256":"de1bb5e82f86774e70082b906462e02a062238e5c4d76149566e21b1cb31b23a"},{"path":"/usr/share/zoneinfo/Australia/Victoria","mode":33188,"size":2223,"sha256":"272c1f13d01e35e6a58855cbb53878795451928adbf0c8ca2982b79db1f450a7"},{"path":"/usr/share/zoneinfo/Australia/West","mode":33188,"size":479,"sha256":"4ecd4a085ca9ec5b7903016c2d4e311276024a2bcd0c35d40281658e48421f93"},{"path":"/usr/share/zoneinfo/Australia/Yancowinna","mode":33188,"size":2274,"sha256":"d6451675d3b5afb8572e2cbb4d381730da23daa3bfcb57601fe6f815985237db"},{"path":"/usr/share/zoneinfo/Brazil/Acre","mode":33188,"size":662,"sha256":"16c86cccc93c7ebfeffae880e439ce848055e421578982d5cabef8aaec15f802"},{"path":"/usr/share/zoneinfo/Brazil/DeNoronha","mode":33188,"size":742,"sha256":"cb4e968f415ed53e769108c9d5f9710e898716af74536d39b7077b0426f3960d"},{"path":"/usr/share/zoneinfo/Brazil/East","mode":33188,"size":1470,"sha256":"a4090cbdfa5168012d460585f7eab9302f8848cca0419d73cf03993ef12c08c4"},{"path":"/usr/share/zoneinfo/Brazil/West","mode":33188,"size":630,"sha256":"e1213e7b97cfa580b4f9c728c34ffa64a6ab277b06b558893b299c20d3528e6c"},{"path":"/usr/share/zoneinfo/CET","mode":33188,"size":2102,"sha256":"3c0029045f6f80bc5a84f1bb8ed36230454759c54578eb9a8c195d14f442213c"},{"path":"/usr/share/zoneinfo/CST6CDT","mode":33188,"size":2294,"sha256":"44e8b569e60027647f9801a33d0b43be0106a6d3f6cd059677e0ed65c9b8b831"},{"path":"/usr/share/zoneinfo/Canada/Atlantic","mode":33188,"size":3438,"sha256":"627e18218c6f3c3f446c4970abe8164672e2a7ba94bcf841b1e06af5089b94ea"},{"path":"/usr/share/zoneinfo/Canada/Central","mode":33188,"size":2891,"sha256":"77be5c08f6f8ebe5330fb86a60c4447ea2549620609f4ef6a7a7a68d1a12d9d6"},{"path":"/usr/share/zoneinfo/Canada/Eastern","mode":33188,"size":3503,"sha256":"842f7a103dfac9c0c2c33c9cc392a113d266ac064c5c7497883ab41b797ce194"},{"path":"/usr/share/zoneinfo/Canada/Mountain","mode":33188,"size":2346,"sha256":"92ac6208f1ef357787fcfce6a334990252189eb0b427b28bc60e21ab5e792b3c"},{"path":"/usr/share/zoneinfo/Canada/Newfoundland","mode":33188,"size":3664,"sha256":"2b960a58d6d3f6a272707f941f55b15b8ba3fd0fd55f8680ea84af6b1e98bae0"},{"path":"/usr/share/zoneinfo/Canada/Pacific","mode":33188,"size":2901,"sha256":"460182c93960fd636820b1b43cfec871da4f0197556bb6bdb2fa527b637a4332"},{"path":"/usr/share/zoneinfo/Canada/Saskatchewan","mode":33188,"size":994,"sha256":"929d07457407529637626d09f5ca975b4f05801f35d0bfac4e3b0027efee6776"},{"path":"/usr/share/zoneinfo/Canada/Yukon","mode":33188,"size":1609,"sha256":"e4afd69d844499d8bf3bb276d3ecab98ac10cddb21c180b6717e5635485ccf38"},{"path":"/usr/share/zoneinfo/Chile/Continental","mode":33188,"size":2538,"sha256":"b83e4129763ef7a22be3fba68029b4ecb6f14a360112498446d8c89640f420b5"},{"path":"/usr/share/zoneinfo/Chile/EasterIsland","mode":33188,"size":2242,"sha256":"d344955a3a8dea47b50a72d2af7fde01a6a27365bef0fefb2c11429a4f5dfca1"},{"path":"/usr/share/zoneinfo/Cuba","mode":33188,"size":2437,"sha256":"7871f875a8819f415c292519db1590556a0dc1a6ce691bf4f7af55e6716fb894"},{"path":"/usr/share/zoneinfo/EET","mode":33188,"size":1876,"sha256":"0bf6d2669ab45c13a1c9be47c351972feb671770b90a61d9d313fc60b721b2b4"},{"path":"/usr/share/zoneinfo/EST","mode":33188,"size":127,"sha256":"c9e75f112a498ff00344551c3c5c4a62bd15d5c218ee951f4363ab218c5d88eb"},{"path":"/usr/share/zoneinfo/EST5EDT","mode":33188,"size":2294,"sha256":"79ce27e03a2752091e8a49cc7e7ccc9ac202d6c52dd5d224571fe82262fbeec8"},{"path":"/usr/share/zoneinfo/Egypt","mode":33188,"size":1972,"sha256":"279bbe1fa62da67387c63593b60bb655252ef5c8f189cf43469087740af2b4fc"},{"path":"/usr/share/zoneinfo/Eire","mode":33188,"size":3543,"sha256":"ff19972d561b3b6a9bdb0ec69a3ed3b59ca5ccd1b14929e29bf86d757255eec2"},{"path":"/usr/share/zoneinfo/Etc/GMT","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/Etc/GMT+0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/Etc/GMT+1","mode":33188,"size":148,"sha256":"35d004edb2a0b1137ae1ea3659ef8e95a753330f0713fc94929d0f79d8021b07"},{"path":"/usr/share/zoneinfo/Etc/GMT+10","mode":33188,"size":149,"sha256":"4762603f3f51c0d5063ea549f9a578b7ebf26e47fd7109a6e34495ac3e09b2ed"},{"path":"/usr/share/zoneinfo/Etc/GMT+11","mode":33188,"size":149,"sha256":"8a23521d6e93326291dbdacf2857f8a78970bef3dd93a53557da4cc2e79c36ba"},{"path":"/usr/share/zoneinfo/Etc/GMT+12","mode":33188,"size":149,"sha256":"ec7046f7e41252f839950ce04e3f20e41ba228e678aae2a45b5b050ba990e626"},{"path":"/usr/share/zoneinfo/Etc/GMT+2","mode":33188,"size":148,"sha256":"21319b8c2634a8349e84c3bef422998f6dd4f79bad91f79fa38145c1f6b694dd"},{"path":"/usr/share/zoneinfo/Etc/GMT+3","mode":33188,"size":148,"sha256":"e7861defa0a8bc5e0ee58d8a7a993ac22950e3fed608c9532c680b74ef6cc67f"},{"path":"/usr/share/zoneinfo/Etc/GMT+4","mode":33188,"size":148,"sha256":"0f0ab77c5beca68231484090c38ecc1ce211b135511d5431dc1994f8a2580c89"},{"path":"/usr/share/zoneinfo/Etc/GMT+5","mode":33188,"size":148,"sha256":"be7cef32cf0094520b344fc461bc28747e617d6043b8be0b0871e87225ee8568"},{"path":"/usr/share/zoneinfo/Etc/GMT+6","mode":33188,"size":148,"sha256":"d285eec873a91b2660ff29816304693056ee61ac1e9bd3485e26c4bcc067e041"},{"path":"/usr/share/zoneinfo/Etc/GMT+7","mode":33188,"size":148,"sha256":"631be5659ae83739e1056e088289b642caf4d07be5887f74c6cc954e2b0e9e5c"},{"path":"/usr/share/zoneinfo/Etc/GMT+8","mode":33188,"size":148,"sha256":"f0ede5d811e0d8b283b18b80aebe6ce617267664ec313fc5bf01e2880a8c4229"},{"path":"/usr/share/zoneinfo/Etc/GMT+9","mode":33188,"size":148,"sha256":"6aab552f947986b00b2d43ff28a3257ab7b88967322b9ce067e45c5ea96cc014"},{"path":"/usr/share/zoneinfo/Etc/GMT-0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/Etc/GMT-1","mode":33188,"size":149,"sha256":"d5f7f0682e71000de343fce27f2e8cff9e37e50cb064bf0f61245dc7ff6806ed"},{"path":"/usr/share/zoneinfo/Etc/GMT-10","mode":33188,"size":150,"sha256":"2fdcfd00c1be46329891da92b46f49258b35c09eb9e1103e3789a3d58338eb78"},{"path":"/usr/share/zoneinfo/Etc/GMT-11","mode":33188,"size":150,"sha256":"4439c8a7d5a8c87c47b7a81bd2e9534c8c676f610d4038fdf3b3951089a5db91"},{"path":"/usr/share/zoneinfo/Etc/GMT-12","mode":33188,"size":150,"sha256":"5f0c2c21cec4020ec3116c038ca9ff5e5a9e863ddb7fc0beba7136c321b05851"},{"path":"/usr/share/zoneinfo/Etc/GMT-13","mode":33188,"size":150,"sha256":"0c4e6bff6354406378f2bdb165fae025fa100fe8c7d76c6cfaabb716f6f096ca"},{"path":"/usr/share/zoneinfo/Etc/GMT-14","mode":33188,"size":150,"sha256":"4685f92efa5bbdb625dd8d6454a340af8ac0510308b6b66847ad5f7bc3c4fc84"},{"path":"/usr/share/zoneinfo/Etc/GMT-2","mode":33188,"size":149,"sha256":"530335b26ac0306edc8f0683a830bc1e7f5111ad228df4b74c197d2cb9c31387"},{"path":"/usr/share/zoneinfo/Etc/GMT-3","mode":33188,"size":149,"sha256":"a59e1e4a707222ac22fefb3a6dc495cef266872a94d51e5ca862ffde74ef0c4c"},{"path":"/usr/share/zoneinfo/Etc/GMT-4","mode":33188,"size":149,"sha256":"7d6471f8835da5e7906f8220dd9674b664573fee650f0a28b5ab51aa54a4524e"},{"path":"/usr/share/zoneinfo/Etc/GMT-5","mode":33188,"size":149,"sha256":"33a439130048c8b6400ad082b2e4011c7b85fafe9171e13110aa86f266bedfa4"},{"path":"/usr/share/zoneinfo/Etc/GMT-6","mode":33188,"size":149,"sha256":"f2ae16bd9a3a9a75788ca13a281bcc39567c93aaf5ad5402fcbfebac473b6cf7"},{"path":"/usr/share/zoneinfo/Etc/GMT-7","mode":33188,"size":149,"sha256":"b0e37d9bf496f375b7c024e81b6ae5943ccbace0ffbecb684d8bd1847c5cb93a"},{"path":"/usr/share/zoneinfo/Etc/GMT-8","mode":33188,"size":149,"sha256":"5ec67811fbce13ee23123eee60791be8cb5f9c84451ae0d8297738af9b7f0cca"},{"path":"/usr/share/zoneinfo/Etc/GMT-9","mode":33188,"size":149,"sha256":"16ed57cd7c3577fdc22d57683841e922b208a535e6125e686be4f8702a75f485"},{"path":"/usr/share/zoneinfo/Etc/GMT0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/Etc/Greenwich","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/Etc/UCT","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/Etc/UTC","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/Etc/Universal","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/Etc/Zulu","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/Europe/Amsterdam","mode":33188,"size":2949,"sha256":"8a813ac6b8d1b68a7960242cae5325a2269fd1c791b203f8d22f2dfa3b61ba87"},{"path":"/usr/share/zoneinfo/Europe/Andorra","mode":33188,"size":1751,"sha256":"add5505c473225e33a884a02105610a9b95003f429195624b953c18f771317af"},{"path":"/usr/share/zoneinfo/Europe/Astrakhan","mode":33188,"size":1197,"sha256":"a027561f493c02a04d699903a08e9e78ac76eb3a719c4749d9ae9480418baad8"},{"path":"/usr/share/zoneinfo/Europe/Athens","mode":33188,"size":2271,"sha256":"799090551202c0b8417f836facf75049573dd1c27b5e6adeb584fcc414051139"},{"path":"/usr/share/zoneinfo/Europe/Belfast","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/Europe/Belgrade","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/Europe/Berlin","mode":33188,"size":2335,"sha256":"7eb93dcba603d528fdf536160ef6911c16f834afcf88ce23a382b97ff28319d4"},{"path":"/usr/share/zoneinfo/Europe/Bratislava","mode":33188,"size":2338,"sha256":"7290e2da43a8b82b3c46ac2a05e072a8cecbf8516e5c286791dbdd68a761d205"},{"path":"/usr/share/zoneinfo/Europe/Brussels","mode":33188,"size":2970,"sha256":"11497c2fd62834d7c1ab568fb47e5947a7f5a63378dc723d7f73ccab21da5342"},{"path":"/usr/share/zoneinfo/Europe/Bucharest","mode":33188,"size":2221,"sha256":"3b3a0017333b2f466e59c8ac3dc0cf7aa4f0a4608040a3180f752b19d6a93526"},{"path":"/usr/share/zoneinfo/Europe/Budapest","mode":33188,"size":2405,"sha256":"b67f2c4690a87f294ea5d35ae3967c8aa8bde227aeb36c3877285e4e94a17418"},{"path":"/usr/share/zoneinfo/Europe/Busingen","mode":33188,"size":1918,"sha256":"bc45f8c6c8190477cdaae46f77059fab74fde92a02fc57b733f07cb9a55e98a3"},{"path":"/usr/share/zoneinfo/Europe/Chisinau","mode":33188,"size":2445,"sha256":"5749f01c78d0c2fd50d0dc2280c1957ce0419edbfc7c4073c67e6da78153d8c8"},{"path":"/usr/share/zoneinfo/Europe/Copenhagen","mode":33188,"size":2160,"sha256":"d2d9a359ef02d2afe293f429c4fd60fc04fbf8d1d8343c9b224dcfc116c011a8"},{"path":"/usr/share/zoneinfo/Europe/Dublin","mode":33188,"size":3543,"sha256":"ff19972d561b3b6a9bdb0ec69a3ed3b59ca5ccd1b14929e29bf86d757255eec2"},{"path":"/usr/share/zoneinfo/Europe/Gibraltar","mode":33188,"size":3061,"sha256":"c79088f67ba5d3fa9ad989bd573bfdef0e86c89e310ea70bc3e01e14dca1075e"},{"path":"/usr/share/zoneinfo/Europe/Guernsey","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/Europe/Helsinki","mode":33188,"size":1909,"sha256":"ed7d89fae1fb40a9582edd7e03ed02d7fe81ba456b9c1ed8d6ee5f0b931aad45"},{"path":"/usr/share/zoneinfo/Europe/Isle_of_Man","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/Europe/Istanbul","mode":33188,"size":1970,"sha256":"2f24f072fa325c0a9bbecc48ea2782317c459a6cad941a37f7e305238443c45a"},{"path":"/usr/share/zoneinfo/Europe/Jersey","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/Europe/Kaliningrad","mode":33188,"size":1532,"sha256":"78018b1f78b60635b744bc5d78ca209f87c184a634ffe11510b3dfe885eed165"},{"path":"/usr/share/zoneinfo/Europe/Kiev","mode":33188,"size":2097,"sha256":"242912df3212e0725ded4aab25fd869c52f13c3ce619764a883adcbbd937afc5"},{"path":"/usr/share/zoneinfo/Europe/Kirov","mode":33188,"size":1167,"sha256":"a44267313cba43fb671622af5b17cda285def184f6121e8ec6007164643e3c25"},{"path":"/usr/share/zoneinfo/Europe/Lisbon","mode":33188,"size":3469,"sha256":"4bbe65d4ff3394ffa1b4ae6fe2296e333f55bad0ae49ca6717b6076e53490ea2"},{"path":"/usr/share/zoneinfo/Europe/Ljubljana","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/Europe/London","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/Europe/Luxembourg","mode":33188,"size":2974,"sha256":"90b76259274c78a40f34aa5b58545b5409edfbba2fd08efa1b300896cb4062ee"},{"path":"/usr/share/zoneinfo/Europe/Madrid","mode":33188,"size":2637,"sha256":"74103ad1e48f71f4cd9b6d1c03dcd97b58d87bb8affb02b1d6967b204036ebd6"},{"path":"/usr/share/zoneinfo/Europe/Malta","mode":33188,"size":2629,"sha256":"7c4134c8d37bd159e31fd739e8b1b8203a9f3023788bd9c83b8109e361eee5d5"},{"path":"/usr/share/zoneinfo/Europe/Mariehamn","mode":33188,"size":1909,"sha256":"ed7d89fae1fb40a9582edd7e03ed02d7fe81ba456b9c1ed8d6ee5f0b931aad45"},{"path":"/usr/share/zoneinfo/Europe/Minsk","mode":33188,"size":1370,"sha256":"c82aa831a68fec1c918d23393d795fef9dbf4d0948791bcba6ba09f45b3826c4"},{"path":"/usr/share/zoneinfo/Europe/Monaco","mode":33188,"size":2953,"sha256":"7c723359888417b86a66a609ffdd0becf81673cbb3e8b011131088b4d26f6bcd"},{"path":"/usr/share/zoneinfo/Europe/Moscow","mode":33188,"size":1544,"sha256":"02d55516d0f9d497998260b4f129aee59867b77a920ba2ca0c58b15ec8588e7a"},{"path":"/usr/share/zoneinfo/Europe/Nicosia","mode":33188,"size":2016,"sha256":"f2aa2a3f77a43b7558a7508a6cd6c50fdf7d991f9d64da5948fd9003923b1d72"},{"path":"/usr/share/zoneinfo/Europe/Oslo","mode":33188,"size":2251,"sha256":"0fa4e635da2b178fa3ea13ff3829c702844cf8bd69e16bca8e1d34dbd9249d01"},{"path":"/usr/share/zoneinfo/Europe/Paris","mode":33188,"size":2971,"sha256":"735b08e2737de2b47e79f596f3574b5a9e9019e56d2ead0cdc17c0b29e84a585"},{"path":"/usr/share/zoneinfo/Europe/Podgorica","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/Europe/Prague","mode":33188,"size":2338,"sha256":"7290e2da43a8b82b3c46ac2a05e072a8cecbf8516e5c286791dbdd68a761d205"},{"path":"/usr/share/zoneinfo/Europe/Riga","mode":33188,"size":2235,"sha256":"79d10debbaa2743458d0dec1fb71d3c576cea80d245f84819da82a25d93c1401"},{"path":"/usr/share/zoneinfo/Europe/Rome","mode":33188,"size":2692,"sha256":"e878580b27d866d9803e3b82eed5c0b851ef55174e2b76e13caa5e741421a138"},{"path":"/usr/share/zoneinfo/Europe/Samara","mode":33188,"size":1253,"sha256":"52278e6f22bf900faeda4266078cfa7fed25cc1d5653bd345cf3090fde6e9114"},{"path":"/usr/share/zoneinfo/Europe/San_Marino","mode":33188,"size":2692,"sha256":"e878580b27d866d9803e3b82eed5c0b851ef55174e2b76e13caa5e741421a138"},{"path":"/usr/share/zoneinfo/Europe/Sarajevo","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/Europe/Saratov","mode":33188,"size":1197,"sha256":"29ab2a05f63412656a143515fe57218a8e19b9c916dfd05de15a87afcc0d9849"},{"path":"/usr/share/zoneinfo/Europe/Simferopol","mode":33188,"size":1490,"sha256":"b1ee6f714fd88fd61fef6df54f95abacb80dd3036c25e9a10708fec9b11c34cf"},{"path":"/usr/share/zoneinfo/Europe/Skopje","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/Europe/Sofia","mode":33188,"size":2130,"sha256":"16813fb30f2ebb782a806ce0664014ddfbf921890d32ec3d1398bd182bf9245c"},{"path":"/usr/share/zoneinfo/Europe/Stockholm","mode":33188,"size":1918,"sha256":"07b242f9e3d8150663bfaf417fe7d209927fc299fac487789b70841956c35335"},{"path":"/usr/share/zoneinfo/Europe/Tallinn","mode":33188,"size":2187,"sha256":"e3c4ba916c25500c709c56395c040abad62a834fafaf5163a89974b7f66b019a"},{"path":"/usr/share/zoneinfo/Europe/Tirane","mode":33188,"size":2098,"sha256":"62dbc606a32a5f50ceca86c6f96d088ea689bced60a1623c986f045cde9c730a"},{"path":"/usr/share/zoneinfo/Europe/Tiraspol","mode":33188,"size":2445,"sha256":"5749f01c78d0c2fd50d0dc2280c1957ce0419edbfc7c4073c67e6da78153d8c8"},{"path":"/usr/share/zoneinfo/Europe/Ulyanovsk","mode":33188,"size":1281,"sha256":"9cfe87e108465369f14dbf5f8eed9285028f6500c09d06cc3e787be94c55cb91"},{"path":"/usr/share/zoneinfo/Europe/Uzhgorod","mode":33188,"size":2103,"sha256":"098575b4ec6599758c85bcad8dd21d89bca213a9f890c0ead6defd14878705f3"},{"path":"/usr/share/zoneinfo/Europe/Vaduz","mode":33188,"size":1918,"sha256":"bc45f8c6c8190477cdaae46f77059fab74fde92a02fc57b733f07cb9a55e98a3"},{"path":"/usr/share/zoneinfo/Europe/Vatican","mode":33188,"size":2692,"sha256":"e878580b27d866d9803e3b82eed5c0b851ef55174e2b76e13caa5e741421a138"},{"path":"/usr/share/zoneinfo/Europe/Vienna","mode":33188,"size":2237,"sha256":"116fab88b849fbbba59b136477814d2e0fa7d7f735166554d6e72a787cd2ccf8"},{"path":"/usr/share/zoneinfo/Europe/Vilnius","mode":33188,"size":2199,"sha256":"75adc0a906b39e283f5e5020984a36f34b4f58ef1d3099efbc899ff07f035f7e"},{"path":"/usr/share/zoneinfo/Europe/Volgograd","mode":33188,"size":1197,"sha256":"8d840d736f75d20c8b2815c5664252bcbde1fab71fd3d4efe17a97ac83ddaf3f"},{"path":"/usr/share/zoneinfo/Europe/Warsaw","mode":33188,"size":2705,"sha256":"68e7493c1ca050e4134062a74aa4a4fc32159c042b4c9d8d40c8bfc9d273c5fa"},{"path":"/usr/share/zoneinfo/Europe/Zagreb","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/Europe/Zaporozhye","mode":33188,"size":2115,"sha256":"b6c5127b52518818e3b4211e89e5e1e9a479cca65f7763a0afb145d512c38e34"},{"path":"/usr/share/zoneinfo/Europe/Zurich","mode":33188,"size":1918,"sha256":"bc45f8c6c8190477cdaae46f77059fab74fde92a02fc57b733f07cb9a55e98a3"},{"path":"/usr/share/zoneinfo/GB","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/GB-Eire","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/GMT","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/GMT+0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/GMT-0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/GMT0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/Greenwich","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/HST","mode":33188,"size":128,"sha256":"44048bf7df61bdcf45972c13426b039f0d34d80947d60a2603183b3b6be4027f"},{"path":"/usr/share/zoneinfo/Hongkong","mode":33188,"size":1231,"sha256":"680a46ee9866bd0c8435fef70694663c1e8ca2ba1e50ff2979ad62f27295707a"},{"path":"/usr/share/zoneinfo/Iceland","mode":33188,"size":1188,"sha256":"9cdcea6aa1eed8276d3f6620e0c0ffae9cfcc3722c443ea6ba39147975eafaa3"},{"path":"/usr/share/zoneinfo/Indian/Antananarivo","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Indian/Chagos","mode":33188,"size":225,"sha256":"f9d2fc010d11285d8430248e7a9ca16c5fe67949e768866f00b3be70aa0ea871"},{"path":"/usr/share/zoneinfo/Indian/Christmas","mode":33188,"size":182,"sha256":"6d094a3d9b022ed04fc53e4a665588bd73f4eeaee9c23667b46944bac5dbbe05"},{"path":"/usr/share/zoneinfo/Indian/Cocos","mode":33188,"size":191,"sha256":"3a57c446d6734a074659b854ed56cec53c40831a33c1052ce6ef4b5f0f6b0009"},{"path":"/usr/share/zoneinfo/Indian/Comoro","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Indian/Kerguelen","mode":33188,"size":187,"sha256":"4dcaa3dc0c2628097499d2cfd37ab2ad70011ee31be9f7e45391ea2faee63b07"},{"path":"/usr/share/zoneinfo/Indian/Mahe","mode":33188,"size":187,"sha256":"82a6e33139b0394eb1a5cb9ffb150a42df5d6fc2c56ad2642285f1d5e553fd17"},{"path":"/usr/share/zoneinfo/Indian/Maldives","mode":33188,"size":220,"sha256":"b5b933b3fc554914587c6af95702a4c0d93941418737a8895372ea514aa7d475"},{"path":"/usr/share/zoneinfo/Indian/Mauritius","mode":33188,"size":267,"sha256":"f257466ded0ce1a324c63e6ebc3a39354e6cde0504f1daa35136c6855278ef0f"},{"path":"/usr/share/zoneinfo/Indian/Mayotte","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/Indian/Reunion","mode":33188,"size":187,"sha256":"c3d95eaceb2806a82b1f2c093f3d73ca0cfa0034ad0446aefbe8c4904f6a955e"},{"path":"/usr/share/zoneinfo/Iran","mode":33188,"size":2624,"sha256":"29fc1861f6e088decab370c3ef2c090d0c3fbdea50b78c2d3158ddaf001b8088"},{"path":"/usr/share/zoneinfo/Israel","mode":33188,"size":2321,"sha256":"1e61da0baf4d2d8f149ed84b8694cc5d4aadbee78d2014771417a67622e653fa"},{"path":"/usr/share/zoneinfo/Jamaica","mode":33188,"size":507,"sha256":"addb98caf3459bb75d6e14ed76aa66e642bead2d067e7fe81814a4f02cf13503"},{"path":"/usr/share/zoneinfo/Japan","mode":33188,"size":318,"sha256":"046bb09bc08554ef8a54dc05685d0eab10e04c692f6320b6091b6a6f07214c83"},{"path":"/usr/share/zoneinfo/Kwajalein","mode":33188,"size":349,"sha256":"94c42dbf73fe0fde173fed33b5f15512b1ea614f40108ac0dacf6e15c23785e0"},{"path":"/usr/share/zoneinfo/Libya","mode":33188,"size":655,"sha256":"8ff53f7072863fb56f1e71339392b6de7e50675efa4333b9e032b677c9c9a527"},{"path":"/usr/share/zoneinfo/MET","mode":33188,"size":2102,"sha256":"1fff331a4414e98097d33bec1a9bbf2a155d991b57acd1bb4c11f8559fb4e514"},{"path":"/usr/share/zoneinfo/MST","mode":33188,"size":127,"sha256":"f8fb610056087bb3ca8ecf5cdcb5305c1652b649fde512f606b9ee1b3556fb9e"},{"path":"/usr/share/zoneinfo/MST7MDT","mode":33188,"size":2294,"sha256":"85452d031526621178e9b24c91af69b7ecc30df47036669378956135c4e735d0"},{"path":"/usr/share/zoneinfo/Mexico/BajaNorte","mode":33188,"size":2356,"sha256":"d827b95b4fa16b8c56d9a1636341c9112657e567ae84b37a9bfca133ae31babb"},{"path":"/usr/share/zoneinfo/Mexico/BajaSur","mode":33188,"size":1564,"sha256":"9340b719b250773262cec62e771d121105aed168836723dfc305e30bb04cfbb1"},{"path":"/usr/share/zoneinfo/Mexico/General","mode":33188,"size":1618,"sha256":"88bc3fcb1a92ef053e0af4af9053ecbf12855fdf18f859b2a54d826dbfacb655"},{"path":"/usr/share/zoneinfo/NZ","mode":33188,"size":2460,"sha256":"d7b5175387ac78e29f7b9021e411512756be283ed3d1819942ef5d45ecf338e4"},{"path":"/usr/share/zoneinfo/NZ-CHAT","mode":33188,"size":2087,"sha256":"58019f2faa29dc7db7081293230a728769054dd7c0d0fa9e96e8c4299e71314d"},{"path":"/usr/share/zoneinfo/Navajo","mode":33188,"size":2453,"sha256":"f4df3cc74c79d070a25a7927744d3a422a05d862a9a234a12105c5c964efb22d"},{"path":"/usr/share/zoneinfo/PRC","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/PST8PDT","mode":33188,"size":2294,"sha256":"4d8e69bd43e8d71f0f58e115593814d68c1a6aa441255b17b3e9a92a9d6efc46"},{"path":"/usr/share/zoneinfo/Pacific/Apia","mode":33188,"size":1134,"sha256":"fb24a31e538dd3ad0b22cf4788d80cb17d79134622510e2aa67c8712d09721cb"},{"path":"/usr/share/zoneinfo/Pacific/Auckland","mode":33188,"size":2460,"sha256":"d7b5175387ac78e29f7b9021e411512756be283ed3d1819942ef5d45ecf338e4"},{"path":"/usr/share/zoneinfo/Pacific/Bougainville","mode":33188,"size":296,"sha256":"c1b670d434aa6c04cbf73b647a07e5be7dcf2ff30663e10c24e0f0cfabe55b36"},{"path":"/usr/share/zoneinfo/Pacific/Chatham","mode":33188,"size":2087,"sha256":"58019f2faa29dc7db7081293230a728769054dd7c0d0fa9e96e8c4299e71314d"},{"path":"/usr/share/zoneinfo/Pacific/Chuuk","mode":33188,"size":296,"sha256":"cd2606a5760aa15600fa906aec3ddea4aba9b89b1e1143de20c7db52ace5bf32"},{"path":"/usr/share/zoneinfo/Pacific/Easter","mode":33188,"size":2242,"sha256":"d344955a3a8dea47b50a72d2af7fde01a6a27365bef0fefb2c11429a4f5dfca1"},{"path":"/usr/share/zoneinfo/Pacific/Efate","mode":33188,"size":492,"sha256":"85d792affc275df1a1bdcf9067cb59f6b1ab8bb93c450cee1293a8157a43c6ad"},{"path":"/usr/share/zoneinfo/Pacific/Enderbury","mode":33188,"size":259,"sha256":"5bf2e193795d4a8ec88bcdcf338097dfa71c254332ed3235e7d3270ea7051cf7"},{"path":"/usr/share/zoneinfo/Pacific/Fakaofo","mode":33188,"size":221,"sha256":"ebcdbbb97d8fa7c9a20ecf62964d207f1ed81e73a3cbea77dc8be5144950af6d"},{"path":"/usr/share/zoneinfo/Pacific/Fiji","mode":33188,"size":1103,"sha256":"c7419d63f407369e5d91ce53093a6903fd8a9841cdec66aacc843d2c4df8ed10"},{"path":"/usr/share/zoneinfo/Pacific/Funafuti","mode":33188,"size":183,"sha256":"812f276576cae6bbd0135d40700fde4fce64f830f75fea928cabe77c51dce579"},{"path":"/usr/share/zoneinfo/Pacific/Galapagos","mode":33188,"size":268,"sha256":"3727ec66f71d8629656377c1f3a004c5cfade0f6c52b8da8b7c3ba2d36998603"},{"path":"/usr/share/zoneinfo/Pacific/Gambier","mode":33188,"size":186,"sha256":"abd4f7e51731d259e30ec4b33c2bcb899e147ee102eb278a1a9b2bb8001c64db"},{"path":"/usr/share/zoneinfo/Pacific/Guadalcanal","mode":33188,"size":188,"sha256":"a69b3ab3a6e6541933831609ab8bbc3ed5bf0ff678e519226b8df966b4973f20"},{"path":"/usr/share/zoneinfo/Pacific/Guam","mode":33188,"size":525,"sha256":"c97a94f15eb7ed24c114ed3b6103987aedd65435aabb85217845df4695fa9069"},{"path":"/usr/share/zoneinfo/Pacific/Honolulu","mode":33188,"size":338,"sha256":"528f01a0a7c21d9cc853eb79b32ecabe8a343028d116b67e6d05cd616d83d5ee"},{"path":"/usr/share/zoneinfo/Pacific/Johnston","mode":33188,"size":338,"sha256":"528f01a0a7c21d9cc853eb79b32ecabe8a343028d116b67e6d05cd616d83d5ee"},{"path":"/usr/share/zoneinfo/Pacific/Kiritimati","mode":33188,"size":263,"sha256":"b78f341b3f703c5dc508805923c91e3884d91ae8bd1e2f82d9b28b2308cd8eef"},{"path":"/usr/share/zoneinfo/Pacific/Kosrae","mode":33188,"size":386,"sha256":"b5e1e429c7d31a845f3ff7f73604e13049ac51626da067b2cd2f4cceac34b2c3"},{"path":"/usr/share/zoneinfo/Pacific/Kwajalein","mode":33188,"size":349,"sha256":"94c42dbf73fe0fde173fed33b5f15512b1ea614f40108ac0dacf6e15c23785e0"},{"path":"/usr/share/zoneinfo/Pacific/Majuro","mode":33188,"size":339,"sha256":"5663127802eeab9ef7b7eb3c889e76ca9683001ed76a2a4549906e864fd10f32"},{"path":"/usr/share/zoneinfo/Pacific/Marquesas","mode":33188,"size":195,"sha256":"5a63de681b53d7bfc728c5d491b2986ab47347a9f2fd15a6f3b6ff978d2f826d"},{"path":"/usr/share/zoneinfo/Pacific/Midway","mode":33188,"size":196,"sha256":"7218a2ae386cd5e8981a940f6b56f6f9b60a65f3e3bd2ec1fe6c9d43bac4db1a"},{"path":"/usr/share/zoneinfo/Pacific/Nauru","mode":33188,"size":282,"sha256":"90f5b914416c9e4189a530cd7fcf878a19e5f5569da00bc926a4d2b6c0cdf0d5"},{"path":"/usr/share/zoneinfo/Pacific/Niue","mode":33188,"size":266,"sha256":"c16c73631f28c41351fff90d3108bc5751cbd40010fdf872da112a10e9739a53"},{"path":"/usr/share/zoneinfo/Pacific/Norfolk","mode":33188,"size":933,"sha256":"d3ea212e8cfe37da5b6becba0cbc308a26bd5590986d4f046845bb5571aa899c"},{"path":"/usr/share/zoneinfo/Pacific/Noumea","mode":33188,"size":328,"sha256":"13e18b4bb426c3739b34e37d6cdc00d488721a05865cdeca94af76246f55a4de"},{"path":"/usr/share/zoneinfo/Pacific/Pago_Pago","mode":33188,"size":196,"sha256":"7218a2ae386cd5e8981a940f6b56f6f9b60a65f3e3bd2ec1fe6c9d43bac4db1a"},{"path":"/usr/share/zoneinfo/Pacific/Palau","mode":33188,"size":199,"sha256":"fa004039c36449b9a8e280ff0c768e4d15d3853d9f2b87a177d365d8ad864525"},{"path":"/usr/share/zoneinfo/Pacific/Pitcairn","mode":33188,"size":223,"sha256":"b0ad4cbe872b4d208d45bc6d326290cd240c1886150f0ee42638386276a8b0b0"},{"path":"/usr/share/zoneinfo/Pacific/Pohnpei","mode":33188,"size":334,"sha256":"ee4a05d2735ebff35c2f093f0b2d03f70434de110a5403ed7a218e1b73bcf3ed"},{"path":"/usr/share/zoneinfo/Pacific/Ponape","mode":33188,"size":334,"sha256":"ee4a05d2735ebff35c2f093f0b2d03f70434de110a5403ed7a218e1b73bcf3ed"},{"path":"/usr/share/zoneinfo/Pacific/Port_Moresby","mode":33188,"size":206,"sha256":"1fb4613fb4bf246f537e265e441fe5f62713037df40338cfd80cb7d768e8ca5f"},{"path":"/usr/share/zoneinfo/Pacific/Rarotonga","mode":33188,"size":602,"sha256":"9695a885289664511eb65f931860f584e7c5443d6f05b10b5197ac7834d47cde"},{"path":"/usr/share/zoneinfo/Pacific/Saipan","mode":33188,"size":525,"sha256":"c97a94f15eb7ed24c114ed3b6103987aedd65435aabb85217845df4695fa9069"},{"path":"/usr/share/zoneinfo/Pacific/Samoa","mode":33188,"size":196,"sha256":"7218a2ae386cd5e8981a940f6b56f6f9b60a65f3e3bd2ec1fe6c9d43bac4db1a"},{"path":"/usr/share/zoneinfo/Pacific/Tahiti","mode":33188,"size":187,"sha256":"c9a22621ddb737b5d6342691dc2d94e265c81b0e743010b6713986db122fc855"},{"path":"/usr/share/zoneinfo/Pacific/Tarawa","mode":33188,"size":183,"sha256":"28fea38528135a54fd642fe3d2bbb41aa8da6b7c892c3991ab2612a81144e799"},{"path":"/usr/share/zoneinfo/Pacific/Tongatapu","mode":33188,"size":393,"sha256":"14d5bf3a7fea21eb6c9e63970d1dad5b9fbedc5f5b0fd3f5069ee74f7a0f4d8d"},{"path":"/usr/share/zoneinfo/Pacific/Truk","mode":33188,"size":296,"sha256":"cd2606a5760aa15600fa906aec3ddea4aba9b89b1e1143de20c7db52ace5bf32"},{"path":"/usr/share/zoneinfo/Pacific/Wake","mode":33188,"size":183,"sha256":"0346a78cf610bc43eae87c0a332d30ac5cf9c95001a4264731563cccf3c38331"},{"path":"/usr/share/zoneinfo/Pacific/Wallis","mode":33188,"size":183,"sha256":"837699bd07ada63d632fc2303a687e5ef9e194e063bac786055885258206ee5c"},{"path":"/usr/share/zoneinfo/Pacific/Yap","mode":33188,"size":296,"sha256":"cd2606a5760aa15600fa906aec3ddea4aba9b89b1e1143de20c7db52ace5bf32"},{"path":"/usr/share/zoneinfo/Poland","mode":33188,"size":2705,"sha256":"68e7493c1ca050e4134062a74aa4a4fc32159c042b4c9d8d40c8bfc9d273c5fa"},{"path":"/usr/share/zoneinfo/Portugal","mode":33188,"size":3469,"sha256":"4bbe65d4ff3394ffa1b4ae6fe2296e333f55bad0ae49ca6717b6076e53490ea2"},{"path":"/usr/share/zoneinfo/ROC","mode":33188,"size":790,"sha256":"25cfd02bc847bdcb11e586445ba886a76315f1f9be86f7e74944a6e8e8644543"},{"path":"/usr/share/zoneinfo/ROK","mode":33188,"size":659,"sha256":"3673a9439d49ea97b47c9fb28433c6d41c469ca03ad320768f1514d075647c26"},{"path":"/usr/share/zoneinfo/Singapore","mode":33188,"size":424,"sha256":"e6929fde43ffc48bbac4081b31bbf7fd42643b3c26fadf322bdeadeb23cfc748"},{"path":"/usr/share/zoneinfo/Turkey","mode":33188,"size":1970,"sha256":"2f24f072fa325c0a9bbecc48ea2782317c459a6cad941a37f7e305238443c45a"},{"path":"/usr/share/zoneinfo/UCT","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/US/Alaska","mode":33188,"size":2380,"sha256":"f5df0a6f7f9d43cbbd3e74d33a23fe686080eb55965f5d9246b6e859b3db9d18"},{"path":"/usr/share/zoneinfo/US/Aleutian","mode":33188,"size":2365,"sha256":"c45c94d316413c8f666aff65ed1f837a7e2d392262de31ce59fac2e96a1edc81"},{"path":"/usr/share/zoneinfo/US/Arizona","mode":33188,"size":353,"sha256":"9c013ecf82b6ed1dde235b5fc983fe9d23c8d56d610323f7c94c6ba3cd7b4564"},{"path":"/usr/share/zoneinfo/US/Central","mode":33188,"size":3585,"sha256":"143f29b957173a46008187230a38125bd3a03b3dbcba0dc1d1b8661331f71693"},{"path":"/usr/share/zoneinfo/US/East-Indiana","mode":33188,"size":1675,"sha256":"55c2f3feb241f88435e9876e76e2c69ddfd0dfd36a273b551ff480e2cfad99fe"},{"path":"/usr/share/zoneinfo/US/Eastern","mode":33188,"size":3545,"sha256":"5fa6dccc303352e1195c4348b189f3085014d8a56a1976c8e8a32bd4fedb69fd"},{"path":"/usr/share/zoneinfo/US/Hawaii","mode":33188,"size":338,"sha256":"528f01a0a7c21d9cc853eb79b32ecabe8a343028d116b67e6d05cd616d83d5ee"},{"path":"/usr/share/zoneinfo/US/Indiana-Starke","mode":33188,"size":2437,"sha256":"9e75dd6c52c5339c8e2b195ff8ac6a7212e2c5e84b2be3023cc355972c20d856"},{"path":"/usr/share/zoneinfo/US/Michigan","mode":33188,"size":2244,"sha256":"e668e3859786c92f462769f87d5bc4ef31b5d6646bbd1635b91007e2a03dbc6c"},{"path":"/usr/share/zoneinfo/US/Mountain","mode":33188,"size":2453,"sha256":"f4df3cc74c79d070a25a7927744d3a422a05d862a9a234a12105c5c964efb22d"},{"path":"/usr/share/zoneinfo/US/Pacific","mode":33188,"size":2845,"sha256":"fea9d66ff6522e69d22073dc4e84179b7cac2e372b398dc2fafdfdb61a9eb2e1"},{"path":"/usr/share/zoneinfo/US/Pacific-New","mode":33188,"size":2845,"sha256":"fea9d66ff6522e69d22073dc4e84179b7cac2e372b398dc2fafdfdb61a9eb2e1"},{"path":"/usr/share/zoneinfo/US/Samoa","mode":33188,"size":196,"sha256":"7218a2ae386cd5e8981a940f6b56f6f9b60a65f3e3bd2ec1fe6c9d43bac4db1a"},{"path":"/usr/share/zoneinfo/UTC","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/Universal","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/W-SU","mode":33188,"size":1544,"sha256":"02d55516d0f9d497998260b4f129aee59867b77a920ba2ca0c58b15ec8588e7a"},{"path":"/usr/share/zoneinfo/WET","mode":33188,"size":1873,"sha256":"e5e7c4631295e7f17085e3530f99fc2984cc7e4bdb9a07db7702de8c18c2aab1"},{"path":"/usr/share/zoneinfo/Zulu","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/iso3166.tab","mode":33188,"size":4463,"sha256":"04c87fc98ecc5e9f03304cbbd636ab157dc8252369c2e132223228d872945c3e"},{"path":"/usr/share/zoneinfo/leapseconds","mode":33188,"size":3142,"sha256":"c6d5661623eee846100ab7b0b3352d73f7bf2252f8772791662331a28bc0b99f"},{"path":"/usr/share/zoneinfo/posix/Africa/Abidjan","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Accra","mode":33188,"size":842,"sha256":"ea0a89ec3c253390f746107c3ea69392270d8df0dc2d2aed6f23f4cff852bf91"},{"path":"/usr/share/zoneinfo/posix/Africa/Addis_Ababa","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Africa/Algiers","mode":33188,"size":760,"sha256":"d777e8eecb9ebe269692349daa6b45b2463e4a3c2d107ccd139b6206c4fa73cc"},{"path":"/usr/share/zoneinfo/posix/Africa/Asmara","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Africa/Asmera","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Africa/Bamako","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Bangui","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Banjul","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Bissau","mode":33188,"size":208,"sha256":"8ddad13adc33cdee8eaf55cfa31efcafd79305ae8dfcc3be06ff78299f29f1d8"},{"path":"/usr/share/zoneinfo/posix/Africa/Blantyre","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/posix/Africa/Brazzaville","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Bujumbura","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/posix/Africa/Cairo","mode":33188,"size":1972,"sha256":"279bbe1fa62da67387c63593b60bb655252ef5c8f189cf43469087740af2b4fc"},{"path":"/usr/share/zoneinfo/posix/Africa/Casablanca","mode":33188,"size":2465,"sha256":"ffa6b8924f65caa075abd3d790fcca99faf59b66cef9531dda52544ee1d5d673"},{"path":"/usr/share/zoneinfo/posix/Africa/Ceuta","mode":33188,"size":2059,"sha256":"387d2c354117fe2a22f6f3b429e4193a331d3e93d7007a55c50b3b9eedee63de"},{"path":"/usr/share/zoneinfo/posix/Africa/Conakry","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Dakar","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Dar_es_Salaam","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Africa/Djibouti","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Africa/Douala","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/El_Aaiun","mode":33188,"size":2303,"sha256":"8bd0b2fbcc4c1c23746fc012be63f88a543bfcaa3f6d464cdf32c014c7bde110"},{"path":"/usr/share/zoneinfo/posix/Africa/Freetown","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Gaborone","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/posix/Africa/Harare","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/posix/Africa/Johannesburg","mode":33188,"size":271,"sha256":"fcec4247091905d88a0b869e8e5c7ee6bcfba7db6c310165baa95078b0be31af"},{"path":"/usr/share/zoneinfo/posix/Africa/Juba","mode":33188,"size":683,"sha256":"73d986c70173c763e9b262dbf367120bc2a4f63f006c1d412ea9adab77e09da3"},{"path":"/usr/share/zoneinfo/posix/Africa/Kampala","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Africa/Khartoum","mode":33188,"size":713,"sha256":"5256a96f78382e82db80ad8591240c3886fc58f9a83fe94506e3a192fbcf2f4e"},{"path":"/usr/share/zoneinfo/posix/Africa/Kigali","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/posix/Africa/Kinshasa","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Lagos","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Libreville","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Lome","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Luanda","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Lubumbashi","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/posix/Africa/Lusaka","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/posix/Africa/Malabo","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Maputo","mode":33188,"size":171,"sha256":"3d7e6d17cabdaa1814a56dddec02687e1087bc3334fe920ad268a892bf080511"},{"path":"/usr/share/zoneinfo/posix/Africa/Maseru","mode":33188,"size":271,"sha256":"fcec4247091905d88a0b869e8e5c7ee6bcfba7db6c310165baa95078b0be31af"},{"path":"/usr/share/zoneinfo/posix/Africa/Mbabane","mode":33188,"size":271,"sha256":"fcec4247091905d88a0b869e8e5c7ee6bcfba7db6c310165baa95078b0be31af"},{"path":"/usr/share/zoneinfo/posix/Africa/Mogadishu","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Africa/Monrovia","mode":33188,"size":233,"sha256":"3f9672c98983af595b3c6274cf8135728c8815a4f9c98ffba043707609e5d122"},{"path":"/usr/share/zoneinfo/posix/Africa/Nairobi","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Africa/Ndjamena","mode":33188,"size":225,"sha256":"b1391c8edd23b3f73e0bfacf8b878801c58206ca42349c30b22fcb7e8d13de3a"},{"path":"/usr/share/zoneinfo/posix/Africa/Niamey","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Nouakchott","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Ouagadougou","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Porto-Novo","mode":33188,"size":171,"sha256":"e40c3386f3a5cd88a03c811fa30ecac34f31368f960ae79e4a90de295c5b1938"},{"path":"/usr/share/zoneinfo/posix/Africa/Sao_Tome","mode":33188,"size":263,"sha256":"1c04b1866beb73b69104997850cce075376d62716f8d01156e796d878b160545"},{"path":"/usr/share/zoneinfo/posix/Africa/Timbuktu","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Africa/Tripoli","mode":33188,"size":655,"sha256":"8ff53f7072863fb56f1e71339392b6de7e50675efa4333b9e032b677c9c9a527"},{"path":"/usr/share/zoneinfo/posix/Africa/Tunis","mode":33188,"size":710,"sha256":"eecc34436d1dd96c49d6b671ed61bc594548d280a967537a9653841b537a9a92"},{"path":"/usr/share/zoneinfo/posix/Africa/Windhoek","mode":33188,"size":1034,"sha256":"3f032165bd2520eb45848e2d059f61185331ba6faa263861c70ec2becf30fa9d"},{"path":"/usr/share/zoneinfo/posix/America/Adak","mode":33188,"size":2365,"sha256":"c45c94d316413c8f666aff65ed1f837a7e2d392262de31ce59fac2e96a1edc81"},{"path":"/usr/share/zoneinfo/posix/America/Anchorage","mode":33188,"size":2380,"sha256":"f5df0a6f7f9d43cbbd3e74d33a23fe686080eb55965f5d9246b6e859b3db9d18"},{"path":"/usr/share/zoneinfo/posix/America/Anguilla","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Antigua","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Araguaina","mode":33188,"size":910,"sha256":"fb7fe2d06e8ee5c5d9a8a568c8cb37efbb0086824f38d1bc4d8505f963b5970d"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Buenos_Aires","mode":33188,"size":1109,"sha256":"841b9bca947f2acd9adc6cb5c10171204eecec1e46e6042654f355c89debc43f"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Catamarca","mode":33188,"size":1109,"sha256":"e844a8f34c71c2d04bfdac6b11e913b5f20ea9fddb5d145433d0831087f1c5d6"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/ComodRivadavia","mode":33188,"size":1109,"sha256":"e844a8f34c71c2d04bfdac6b11e913b5f20ea9fddb5d145433d0831087f1c5d6"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Cordoba","mode":33188,"size":1109,"sha256":"254a30f9b9b00558350d0c1f40a1d9c8738045bb7fe88e56c81bbb9fbd161026"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Jujuy","mode":33188,"size":1081,"sha256":"233f43f895b08f21cd28918fbdb9c22892511c0996ac6212e019c3e866aca455"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/La_Rioja","mode":33188,"size":1123,"sha256":"edc82d9225b8ae3ca911eab14f8201a8916928cfab233e182f807e715cf18435"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Mendoza","mode":33188,"size":1109,"sha256":"d50f245cf1eeb3650dbbdd45720ddc6b1c5e22aede7981f20b9efe2c7ac68c4d"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Rio_Gallegos","mode":33188,"size":1109,"sha256":"f762067b25cc7e6141b06a6eae77764caccccbfe8716f1370c33e169ec2e1723"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Salta","mode":33188,"size":1081,"sha256":"1deede9c14ed0b4dc6e5a40110c7056083c8fed557b84aadc0fa2a045411e560"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/San_Juan","mode":33188,"size":1123,"sha256":"100c000b03b9a0e19c778d9e81ad8e5c2c34db4b7da24c55d67c0ad8050a67c5"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/San_Luis","mode":33188,"size":1139,"sha256":"ab15b1141b87b1381e5cad386fc374b5a9a2ca922504da5b848074fab91e9abc"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Tucuman","mode":33188,"size":1137,"sha256":"6a623bbcd2144f1e43892777084bde4e2613ae6f22bf92dedf6e1dc6e68248b3"},{"path":"/usr/share/zoneinfo/posix/America/Argentina/Ushuaia","mode":33188,"size":1109,"sha256":"02f9a96426823c7bf25ff15a1f241069e2cb15969d48d0c6cc31aad13a7d0f49"},{"path":"/usr/share/zoneinfo/posix/America/Aruba","mode":33188,"size":212,"sha256":"023d877932f35d889772f561f79e266c8541b984e0ce2bd257723aafc7d883c1"},{"path":"/usr/share/zoneinfo/posix/America/Asuncion","mode":33188,"size":2077,"sha256":"1e29f7cdc530419ad31e4afc8fc2adf40d9577f55e2174a3a82358a027780ca2"},{"path":"/usr/share/zoneinfo/posix/America/Atikokan","mode":33188,"size":345,"sha256":"c30226b472b507b5a30b69557d56f24fcc8e9467110e4d3ec15c2c51de5d245c"},{"path":"/usr/share/zoneinfo/posix/America/Atka","mode":33188,"size":2365,"sha256":"c45c94d316413c8f666aff65ed1f837a7e2d392262de31ce59fac2e96a1edc81"},{"path":"/usr/share/zoneinfo/posix/America/Bahia","mode":33188,"size":1050,"sha256":"2e1c1b5e2579e15a623bfd3774db703a49b937790e68b44a6b99a308c6ecba66"},{"path":"/usr/share/zoneinfo/posix/America/Bahia_Banderas","mode":33188,"size":1588,"sha256":"9d0e0d9f6168635a5f98550a170d423854ff5b662ce0d874c3cba77199bf1cbd"},{"path":"/usr/share/zoneinfo/posix/America/Barbados","mode":33188,"size":344,"sha256":"9b1a7857a01ae2a3ae9a51e0b40cfbed91bac468579ed3c08b54466276bbb1fa"},{"path":"/usr/share/zoneinfo/posix/America/Belem","mode":33188,"size":602,"sha256":"84749f6075de59dc62bd69343194806cfd552641b912a6f8e96c83c99914a187"},{"path":"/usr/share/zoneinfo/posix/America/Belize","mode":33188,"size":978,"sha256":"eb4e57a8c657d0c253ef4e0a5af118c928e6e5875564081a714563addfd4b31a"},{"path":"/usr/share/zoneinfo/posix/America/Blanc-Sablon","mode":33188,"size":307,"sha256":"c7d383bfb7e85331030f8091a9055a5f424e3674407ca0c76cce06b5a0316fdb"},{"path":"/usr/share/zoneinfo/posix/America/Boa_Vista","mode":33188,"size":658,"sha256":"c57a63f22280c2c46587414956efc8fcaadc36ed422589b48929dcc7ab4f6680"},{"path":"/usr/share/zoneinfo/posix/America/Bogota","mode":33188,"size":271,"sha256":"3611de34f765f2d65ec0593e79c678de36092549898680dc4639b8c68f7137ba"},{"path":"/usr/share/zoneinfo/posix/America/Boise","mode":33188,"size":2403,"sha256":"33353ef05ccdda7debe757cf865ee7bd78031f38c6797b8fbfc11f9010f55a10"},{"path":"/usr/share/zoneinfo/posix/America/Buenos_Aires","mode":33188,"size":1109,"sha256":"841b9bca947f2acd9adc6cb5c10171204eecec1e46e6042654f355c89debc43f"},{"path":"/usr/share/zoneinfo/posix/America/Cambridge_Bay","mode":33188,"size":2098,"sha256":"0aeaed5b104ee99ab13a9f5b5a7aaf7f6c9a7f59bdefd15d3c9951551c7b5f6f"},{"path":"/usr/share/zoneinfo/posix/America/Campo_Grande","mode":33188,"size":1470,"sha256":"e670b40a7dd3adf79f66ea43382a70e60caee6ffb59ae92c4c9ee081d16259d2"},{"path":"/usr/share/zoneinfo/posix/America/Cancun","mode":33188,"size":816,"sha256":"d22316873f309799c6f97fefb8a0a8897d0df4eb376f84bb0b71602ec240d04f"},{"path":"/usr/share/zoneinfo/posix/America/Caracas","mode":33188,"size":289,"sha256":"94e8efae88e096d6dd0abda2661d826c004f0c587f97782cb2f911ed7c942f1a"},{"path":"/usr/share/zoneinfo/posix/America/Catamarca","mode":33188,"size":1109,"sha256":"e844a8f34c71c2d04bfdac6b11e913b5f20ea9fddb5d145433d0831087f1c5d6"},{"path":"/usr/share/zoneinfo/posix/America/Cayenne","mode":33188,"size":224,"sha256":"af8de87447f7093759a595cc3d403e5fa7b51fc3520959c4da54956ffbac856a"},{"path":"/usr/share/zoneinfo/posix/America/Cayman","mode":33188,"size":203,"sha256":"fc4fbba14653a3186f3c5b719f7b9bf7d8a5824401064cf6d508205592e55a9f"},{"path":"/usr/share/zoneinfo/posix/America/Chicago","mode":33188,"size":3585,"sha256":"143f29b957173a46008187230a38125bd3a03b3dbcba0dc1d1b8661331f71693"},{"path":"/usr/share/zoneinfo/posix/America/Chihuahua","mode":33188,"size":1522,"sha256":"a7d150e716db5b1c96bb0e50252b80306e1d9e8bcc2bf90a3ae7071906e71513"},{"path":"/usr/share/zoneinfo/posix/America/Coral_Harbour","mode":33188,"size":345,"sha256":"c30226b472b507b5a30b69557d56f24fcc8e9467110e4d3ec15c2c51de5d245c"},{"path":"/usr/share/zoneinfo/posix/America/Cordoba","mode":33188,"size":1109,"sha256":"254a30f9b9b00558350d0c1f40a1d9c8738045bb7fe88e56c81bbb9fbd161026"},{"path":"/usr/share/zoneinfo/posix/America/Costa_Rica","mode":33188,"size":341,"sha256":"4e6ff29a776e053226bf590ebe734896f9150d69074f22a16a1c7199a1484ec5"},{"path":"/usr/share/zoneinfo/posix/America/Creston","mode":33188,"size":233,"sha256":"97b74beec3714be518219f24533cc21edf9b53d01f4ab792a6fe0f88973449eb"},{"path":"/usr/share/zoneinfo/posix/America/Cuiaba","mode":33188,"size":1442,"sha256":"309f877286fad7d01fbbae6bb1a64e23227688e1687a90b6ce67faaef5b0cb67"},{"path":"/usr/share/zoneinfo/posix/America/Curacao","mode":33188,"size":212,"sha256":"023d877932f35d889772f561f79e266c8541b984e0ce2bd257723aafc7d883c1"},{"path":"/usr/share/zoneinfo/posix/America/Danmarkshavn","mode":33188,"size":712,"sha256":"087e39cd6f10b6944b68b1de557289ef33769467f1b29806b96a16cf8e438e6e"},{"path":"/usr/share/zoneinfo/posix/America/Dawson","mode":33188,"size":1609,"sha256":"c379fb9517c07d4df5cbd6aaa2ec4561cbe893ba0e8552d377947fe2b1ff9bf3"},{"path":"/usr/share/zoneinfo/posix/America/Dawson_Creek","mode":33188,"size":1059,"sha256":"29d0245bc04dadcbb196a3b6a81bace1696451166a7417d5bb2a8610f37ec5ba"},{"path":"/usr/share/zoneinfo/posix/America/Denver","mode":33188,"size":2453,"sha256":"f4df3cc74c79d070a25a7927744d3a422a05d862a9a234a12105c5c964efb22d"},{"path":"/usr/share/zoneinfo/posix/America/Detroit","mode":33188,"size":2244,"sha256":"e668e3859786c92f462769f87d5bc4ef31b5d6646bbd1635b91007e2a03dbc6c"},{"path":"/usr/share/zoneinfo/posix/America/Dominica","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Edmonton","mode":33188,"size":2346,"sha256":"92ac6208f1ef357787fcfce6a334990252189eb0b427b28bc60e21ab5e792b3c"},{"path":"/usr/share/zoneinfo/posix/America/Eirunepe","mode":33188,"size":690,"sha256":"07761278f5c58867c645625c9b819ea09e4703d76564e231979e48d6d2e0881a"},{"path":"/usr/share/zoneinfo/posix/America/El_Salvador","mode":33188,"size":250,"sha256":"63215b213a31505bfd545fd52b11214cb614f13f0f55911f414edb44286e7f8a"},{"path":"/usr/share/zoneinfo/posix/America/Ensenada","mode":33188,"size":2356,"sha256":"d827b95b4fa16b8c56d9a1636341c9112657e567ae84b37a9bfca133ae31babb"},{"path":"/usr/share/zoneinfo/posix/America/Fort_Nelson","mode":33188,"size":2249,"sha256":"e7ce9a01cdd313d20352112430341c262e1b90182de490fc95c132daac118ce7"},{"path":"/usr/share/zoneinfo/posix/America/Fort_Wayne","mode":33188,"size":1675,"sha256":"55c2f3feb241f88435e9876e76e2c69ddfd0dfd36a273b551ff480e2cfad99fe"},{"path":"/usr/share/zoneinfo/posix/America/Fortaleza","mode":33188,"size":742,"sha256":"ca3cd6cdd4ec5f945742cd72a91e539756e0ad2eac3dfa62afc21397061eea99"},{"path":"/usr/share/zoneinfo/posix/America/Glace_Bay","mode":33188,"size":2206,"sha256":"e6af24e3b9f1240abb8618fac326ee3a1ecccd25d2fa4936b2a28b0b0880e550"},{"path":"/usr/share/zoneinfo/posix/America/Godthab","mode":33188,"size":1892,"sha256":"356cd2d4e74c958622b77385ae0509b5ea87e691f21207230f6fe1fa67e220af"},{"path":"/usr/share/zoneinfo/posix/America/Goose_Bay","mode":33188,"size":3219,"sha256":"f0c06c6a1841cdc37bfb311c11caba1c974d0d6c27725c04b69657e7ca112a49"},{"path":"/usr/share/zoneinfo/posix/America/Grand_Turk","mode":33188,"size":1881,"sha256":"90848fabb8bcfdbb4e66f5a624c4e7fa88962f16f8b6005f527cd84abebfa574"},{"path":"/usr/share/zoneinfo/posix/America/Grenada","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Guadeloupe","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Guatemala","mode":33188,"size":306,"sha256":"795cc25e5ffe825a8b3d86eed98ad5f9bb9f6d152df2b624f0e2a63b17f0ee43"},{"path":"/usr/share/zoneinfo/posix/America/Guayaquil","mode":33188,"size":271,"sha256":"6f52c0cff32100d797e64032c4ce19fa5a94b75b7678f1beb3c0cb549cdc00f7"},{"path":"/usr/share/zoneinfo/posix/America/Guyana","mode":33188,"size":266,"sha256":"ffa4db9ef9c8a2902355de59b3693aa3dabd21e7a06054772bfcd754902e9342"},{"path":"/usr/share/zoneinfo/posix/America/Halifax","mode":33188,"size":3438,"sha256":"627e18218c6f3c3f446c4970abe8164672e2a7ba94bcf841b1e06af5089b94ea"},{"path":"/usr/share/zoneinfo/posix/America/Havana","mode":33188,"size":2437,"sha256":"7871f875a8819f415c292519db1590556a0dc1a6ce691bf4f7af55e6716fb894"},{"path":"/usr/share/zoneinfo/posix/America/Hermosillo","mode":33188,"size":454,"sha256":"ec6eb21d068f1ca8e80a9e825206ad1b5a04b1e8abb2dd981c6c90b7686b8820"},{"path":"/usr/share/zoneinfo/posix/America/Indiana/Indianapolis","mode":33188,"size":1675,"sha256":"55c2f3feb241f88435e9876e76e2c69ddfd0dfd36a273b551ff480e2cfad99fe"},{"path":"/usr/share/zoneinfo/posix/America/Indiana/Knox","mode":33188,"size":2437,"sha256":"9e75dd6c52c5339c8e2b195ff8ac6a7212e2c5e84b2be3023cc355972c20d856"},{"path":"/usr/share/zoneinfo/posix/America/Indiana/Marengo","mode":33188,"size":1731,"sha256":"64bb87669a7c161454b283e5855e28de7655450680cc403eea0572e580eb2625"},{"path":"/usr/share/zoneinfo/posix/America/Indiana/Petersburg","mode":33188,"size":1913,"sha256":"3eb5dd510d677f9118ec4bca7892db4ed181722fbaf94ef9cb1a441718400321"},{"path":"/usr/share/zoneinfo/posix/America/Indiana/Tell_City","mode":33188,"size":1693,"sha256":"6814c2b71389711819f44b98c880caf317c03a42064b2217103795114781a80f"},{"path":"/usr/share/zoneinfo/posix/America/Indiana/Vevay","mode":33188,"size":1423,"sha256":"5cf728ac267cce51bddf1875219bf0e800d5aaa17794dc2c7408293773f516e5"},{"path":"/usr/share/zoneinfo/posix/America/Indiana/Vincennes","mode":33188,"size":1703,"sha256":"8a9db38f7575f9e2a624c9466128927caef0eea7e9a3841679cd6eb129b019d3"},{"path":"/usr/share/zoneinfo/posix/America/Indiana/Winamac","mode":33188,"size":1787,"sha256":"d2dc919207b8db95bd82aff68b8a498a6d3bec2c33220ba5381ebca171dcc095"},{"path":"/usr/share/zoneinfo/posix/America/Indianapolis","mode":33188,"size":1675,"sha256":"55c2f3feb241f88435e9876e76e2c69ddfd0dfd36a273b551ff480e2cfad99fe"},{"path":"/usr/share/zoneinfo/posix/America/Inuvik","mode":33188,"size":1928,"sha256":"ea64cbc0bf92cf88c8917222f11db8838f42e2d41360cd81bb93f669a2bc685b"},{"path":"/usr/share/zoneinfo/posix/America/Iqaluit","mode":33188,"size":2046,"sha256":"eb8797250b8bd8c3d09893b4f261ffb1bedd668869a051c8e2c80f6c0d63408c"},{"path":"/usr/share/zoneinfo/posix/America/Jamaica","mode":33188,"size":507,"sha256":"addb98caf3459bb75d6e14ed76aa66e642bead2d067e7fe81814a4f02cf13503"},{"path":"/usr/share/zoneinfo/posix/America/Jujuy","mode":33188,"size":1081,"sha256":"233f43f895b08f21cd28918fbdb9c22892511c0996ac6212e019c3e866aca455"},{"path":"/usr/share/zoneinfo/posix/America/Juneau","mode":33188,"size":2362,"sha256":"8185913ee68f7ec72cd98efcee68d1b6bd0c304e303a2dc613b06cd97e6333c8"},{"path":"/usr/share/zoneinfo/posix/America/Kentucky/Louisville","mode":33188,"size":2781,"sha256":"31e1152a8de9463bcef2b5db10415965b96b83a93bd940609bc390bab963f384"},{"path":"/usr/share/zoneinfo/posix/America/Kentucky/Monticello","mode":33188,"size":2361,"sha256":"b87081e46bbe688816a7e03cfdc5b4efe10bd6b92cb5a780df6b0c86af4c1a37"},{"path":"/usr/share/zoneinfo/posix/America/Knox_IN","mode":33188,"size":2437,"sha256":"9e75dd6c52c5339c8e2b195ff8ac6a7212e2c5e84b2be3023cc355972c20d856"},{"path":"/usr/share/zoneinfo/posix/America/Kralendijk","mode":33188,"size":212,"sha256":"023d877932f35d889772f561f79e266c8541b984e0ce2bd257723aafc7d883c1"},{"path":"/usr/share/zoneinfo/posix/America/La_Paz","mode":33188,"size":257,"sha256":"1f10b013aea85ad55c3b3f65d68fa09bba4abe7fb5311018698823f0ab909a88"},{"path":"/usr/share/zoneinfo/posix/America/Lima","mode":33188,"size":431,"sha256":"5f514d5245abb9de7c35fabed4c4cc86f6c027548cd1be04cc84b122878e1ad3"},{"path":"/usr/share/zoneinfo/posix/America/Los_Angeles","mode":33188,"size":2845,"sha256":"fea9d66ff6522e69d22073dc4e84179b7cac2e372b398dc2fafdfdb61a9eb2e1"},{"path":"/usr/share/zoneinfo/posix/America/Louisville","mode":33188,"size":2781,"sha256":"31e1152a8de9463bcef2b5db10415965b96b83a93bd940609bc390bab963f384"},{"path":"/usr/share/zoneinfo/posix/America/Lower_Princes","mode":33188,"size":212,"sha256":"023d877932f35d889772f561f79e266c8541b984e0ce2bd257723aafc7d883c1"},{"path":"/usr/share/zoneinfo/posix/America/Maceio","mode":33188,"size":770,"sha256":"3241ce8df0004a0cb5db2eb3800a3dfe770cc1d24d144fee27862c4dd7400840"},{"path":"/usr/share/zoneinfo/posix/America/Managua","mode":33188,"size":463,"sha256":"a3c1f00bc879ee84e623d25252f1fb8ffd8cf43cd9c8b8bf12b6b5eda8045683"},{"path":"/usr/share/zoneinfo/posix/America/Manaus","mode":33188,"size":630,"sha256":"e1213e7b97cfa580b4f9c728c34ffa64a6ab277b06b558893b299c20d3528e6c"},{"path":"/usr/share/zoneinfo/posix/America/Marigot","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Martinique","mode":33188,"size":257,"sha256":"e087c3e4ae20234a08667adcf6ab4cd03ab3aeee7e035278f271ddb0b65cfff2"},{"path":"/usr/share/zoneinfo/posix/America/Matamoros","mode":33188,"size":1416,"sha256":"4398d831df4bfcfd9bafa22ac35cd55dbb7dfd5f25c138452e8adf275ea11735"},{"path":"/usr/share/zoneinfo/posix/America/Mazatlan","mode":33188,"size":1564,"sha256":"9340b719b250773262cec62e771d121105aed168836723dfc305e30bb04cfbb1"},{"path":"/usr/share/zoneinfo/posix/America/Mendoza","mode":33188,"size":1109,"sha256":"d50f245cf1eeb3650dbbdd45720ddc6b1c5e22aede7981f20b9efe2c7ac68c4d"},{"path":"/usr/share/zoneinfo/posix/America/Menominee","mode":33188,"size":2283,"sha256":"46ced580e74834d2c68a80a60ae05a0b715014bb2b4dad67cf994ac20ce2ac22"},{"path":"/usr/share/zoneinfo/posix/America/Merida","mode":33188,"size":1456,"sha256":"ecdcf4b29f7b439152b9e9b559f04d7d4ba759dd942c2fd685a4ee36798fc8d1"},{"path":"/usr/share/zoneinfo/posix/America/Metlakatla","mode":33188,"size":1432,"sha256":"9d091e1f411ccec6f2274317c53cc3ca45d6895f2c7497583e71ffca496716f3"},{"path":"/usr/share/zoneinfo/posix/America/Mexico_City","mode":33188,"size":1618,"sha256":"88bc3fcb1a92ef053e0af4af9053ecbf12855fdf18f859b2a54d826dbfacb655"},{"path":"/usr/share/zoneinfo/posix/America/Miquelon","mode":33188,"size":1696,"sha256":"21fabc9c2cafd8eef46af9126040cced6ef27d648d73d48951178143e6bb006b"},{"path":"/usr/share/zoneinfo/posix/America/Moncton","mode":33188,"size":3163,"sha256":"1300d5a93bb376cbf23a890a23ea05fa2b229486e7eb7d5959c7834260fbb7b7"},{"path":"/usr/share/zoneinfo/posix/America/Monterrey","mode":33188,"size":1416,"sha256":"89dadca852ebf52e4405c958132255c25fb195604d7df9b844bf50b48a0865d8"},{"path":"/usr/share/zoneinfo/posix/America/Montevideo","mode":33188,"size":1564,"sha256":"550efc39d3e1c9e6909aa80a9d067f9355c47a874fcaf4f59302407ef6f968e1"},{"path":"/usr/share/zoneinfo/posix/America/Montreal","mode":33188,"size":3503,"sha256":"842f7a103dfac9c0c2c33c9cc392a113d266ac064c5c7497883ab41b797ce194"},{"path":"/usr/share/zoneinfo/posix/America/Montserrat","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Nassau","mode":33188,"size":2284,"sha256":"4c999dbcc6c6045acbedf6fd48f5b70b20eb8d8b0bd9612d2bea88dc03aa9f4d"},{"path":"/usr/share/zoneinfo/posix/America/New_York","mode":33188,"size":3545,"sha256":"5fa6dccc303352e1195c4348b189f3085014d8a56a1976c8e8a32bd4fedb69fd"},{"path":"/usr/share/zoneinfo/posix/America/Nipigon","mode":33188,"size":2131,"sha256":"7100ca4bf3044211ff8e770dade20b683880f3965f146ebbdd72c644aaec7c37"},{"path":"/usr/share/zoneinfo/posix/America/Nome","mode":33188,"size":2376,"sha256":"d312bc797eb1b384ccfba0c40822d50b2e0abf37d5daa43dd3e255fdc7573b00"},{"path":"/usr/share/zoneinfo/posix/America/Noronha","mode":33188,"size":742,"sha256":"cb4e968f415ed53e769108c9d5f9710e898716af74536d39b7077b0426f3960d"},{"path":"/usr/share/zoneinfo/posix/America/North_Dakota/Beulah","mode":33188,"size":2389,"sha256":"f604eb42f0197f5edefcd6d43051a0b64e6e1327dbd2d3cfa94d0348b23e1fa8"},{"path":"/usr/share/zoneinfo/posix/America/North_Dakota/Center","mode":33188,"size":2389,"sha256":"08efea4af9a2b6a5ab25e86116cfcf4b93c16ba9b7b22f762d9cb3481ecf3ac8"},{"path":"/usr/share/zoneinfo/posix/America/North_Dakota/New_Salem","mode":33188,"size":2389,"sha256":"c5a43eb6776c326b1250f914f00e9e00e121b9b51f63665f90f245376da2017a"},{"path":"/usr/share/zoneinfo/posix/America/Nuuk","mode":33188,"size":1892,"sha256":"356cd2d4e74c958622b77385ae0509b5ea87e691f21207230f6fe1fa67e220af"},{"path":"/usr/share/zoneinfo/posix/America/Ojinaga","mode":33188,"size":1522,"sha256":"a07ff8fe3ee3531f866afca0f7937d86acec1826fb3eaa655d54300ec22dc713"},{"path":"/usr/share/zoneinfo/posix/America/Panama","mode":33188,"size":203,"sha256":"fc4fbba14653a3186f3c5b719f7b9bf7d8a5824401064cf6d508205592e55a9f"},{"path":"/usr/share/zoneinfo/posix/America/Pangnirtung","mode":33188,"size":2108,"sha256":"1b6a497653df9220c30a022d87ec2aa1320af9e51bb3cdc48756e72d770a6738"},{"path":"/usr/share/zoneinfo/posix/America/Paramaribo","mode":33188,"size":296,"sha256":"57039b31a68b30ba0731916cffa7b9a1bbb52bf7650f7aa62052e89a8fc9edf6"},{"path":"/usr/share/zoneinfo/posix/America/Phoenix","mode":33188,"size":353,"sha256":"9c013ecf82b6ed1dde235b5fc983fe9d23c8d56d610323f7c94c6ba3cd7b4564"},{"path":"/usr/share/zoneinfo/posix/America/Port-au-Prince","mode":33188,"size":1455,"sha256":"b0b60ad1c557c41596e0fcc7fc8b9b39444c78295b147cee495e29985a225da6"},{"path":"/usr/share/zoneinfo/posix/America/Port_of_Spain","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Porto_Acre","mode":33188,"size":662,"sha256":"16c86cccc93c7ebfeffae880e439ce848055e421578982d5cabef8aaec15f802"},{"path":"/usr/share/zoneinfo/posix/America/Porto_Velho","mode":33188,"size":602,"sha256":"29f8daaa8fdca090df7145e69ecdc936cd3fedacea0b723f5c93da2a8c80f976"},{"path":"/usr/share/zoneinfo/posix/America/Puerto_Rico","mode":33188,"size":255,"sha256":"7eee44e1cb7ac885fdd5042815c548bcb6ca84cff8de007e52b53c0b9ad53f19"},{"path":"/usr/share/zoneinfo/posix/America/Punta_Arenas","mode":33188,"size":1911,"sha256":"33e26b3c8bf3dd7100151d3c1842ae9aa8ef69b15f961aa2eee2e1dc3508c6e5"},{"path":"/usr/share/zoneinfo/posix/America/Rainy_River","mode":33188,"size":2131,"sha256":"9a7b8dd4c968de31fe35fd9fe075fad8afc15892067119f638b5aef0d2288d83"},{"path":"/usr/share/zoneinfo/posix/America/Rankin_Inlet","mode":33188,"size":1930,"sha256":"b3ae38ccfa3091ebd8037fd5e1fd2715a72008932f94526a15fb1aa7fae722dc"},{"path":"/usr/share/zoneinfo/posix/America/Recife","mode":33188,"size":742,"sha256":"cebb6d30c20b00bc437d4e0a8c6a0c91db120a3aef2c28bc56960f682b3fc30c"},{"path":"/usr/share/zoneinfo/posix/America/Regina","mode":33188,"size":994,"sha256":"929d07457407529637626d09f5ca975b4f05801f35d0bfac4e3b0027efee6776"},{"path":"/usr/share/zoneinfo/posix/America/Resolute","mode":33188,"size":1930,"sha256":"c529141807704725b059187b9f458080f911b6dd4313e74139d2c7dac287c901"},{"path":"/usr/share/zoneinfo/posix/America/Rio_Branco","mode":33188,"size":662,"sha256":"16c86cccc93c7ebfeffae880e439ce848055e421578982d5cabef8aaec15f802"},{"path":"/usr/share/zoneinfo/posix/America/Rosario","mode":33188,"size":1109,"sha256":"254a30f9b9b00558350d0c1f40a1d9c8738045bb7fe88e56c81bbb9fbd161026"},{"path":"/usr/share/zoneinfo/posix/America/Santa_Isabel","mode":33188,"size":2356,"sha256":"d827b95b4fa16b8c56d9a1636341c9112657e567ae84b37a9bfca133ae31babb"},{"path":"/usr/share/zoneinfo/posix/America/Santarem","mode":33188,"size":632,"sha256":"78440d01f4c5b7c13d1dbe6500ba71188efdcf90069979c80a224d831c8bd97b"},{"path":"/usr/share/zoneinfo/posix/America/Santiago","mode":33188,"size":2538,"sha256":"b83e4129763ef7a22be3fba68029b4ecb6f14a360112498446d8c89640f420b5"},{"path":"/usr/share/zoneinfo/posix/America/Santo_Domingo","mode":33188,"size":491,"sha256":"adf349e4c7314aaa699c4893c589b077f6dfa7d9a54ea9eae459658f9af41dc7"},{"path":"/usr/share/zoneinfo/posix/America/Sao_Paulo","mode":33188,"size":1470,"sha256":"a4090cbdfa5168012d460585f7eab9302f8848cca0419d73cf03993ef12c08c4"},{"path":"/usr/share/zoneinfo/posix/America/Scoresbysund","mode":33188,"size":1930,"sha256":"c668772d49326cde3798d158089d2f9ced43788f904360a6dc67a53868b28f96"},{"path":"/usr/share/zoneinfo/posix/America/Shiprock","mode":33188,"size":2453,"sha256":"f4df3cc74c79d070a25a7927744d3a422a05d862a9a234a12105c5c964efb22d"},{"path":"/usr/share/zoneinfo/posix/America/Sitka","mode":33188,"size":2350,"sha256":"ba79b89ecd8e64dba4119f2c5af2373167557c4bc71b7b134ab252e0b7485fdb"},{"path":"/usr/share/zoneinfo/posix/America/St_Barthelemy","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/St_Johns","mode":33188,"size":3664,"sha256":"2b960a58d6d3f6a272707f941f55b15b8ba3fd0fd55f8680ea84af6b1e98bae0"},{"path":"/usr/share/zoneinfo/posix/America/St_Kitts","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/St_Lucia","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/St_Thomas","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/St_Vincent","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Swift_Current","mode":33188,"size":574,"sha256":"6b6029f04ac07c382e20d315da7a72d9204d813ef83585f042562e7f6788a78f"},{"path":"/usr/share/zoneinfo/posix/America/Tegucigalpa","mode":33188,"size":278,"sha256":"fd295a9cc689a966786b6e0ec9d0f101796ac8b4f04a6f529b192937df3a2115"},{"path":"/usr/share/zoneinfo/posix/America/Thule","mode":33188,"size":1528,"sha256":"9a474a1fc764343470d310369cdbf6d7007ea611116e25bea68f60ddf5a6cd68"},{"path":"/usr/share/zoneinfo/posix/America/Thunder_Bay","mode":33188,"size":2211,"sha256":"aef45e1474369f52e1afb1cd7f312e9f035ca13686092cf2351a353133e1cee6"},{"path":"/usr/share/zoneinfo/posix/America/Tijuana","mode":33188,"size":2356,"sha256":"d827b95b4fa16b8c56d9a1636341c9112657e567ae84b37a9bfca133ae31babb"},{"path":"/usr/share/zoneinfo/posix/America/Toronto","mode":33188,"size":3503,"sha256":"842f7a103dfac9c0c2c33c9cc392a113d266ac064c5c7497883ab41b797ce194"},{"path":"/usr/share/zoneinfo/posix/America/Tortola","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Vancouver","mode":33188,"size":2901,"sha256":"460182c93960fd636820b1b43cfec871da4f0197556bb6bdb2fa527b637a4332"},{"path":"/usr/share/zoneinfo/posix/America/Virgin","mode":33188,"size":170,"sha256":"b2659c267f7555c0640505660234cbe0d7feead3a5e29f41272e28a1d7d18962"},{"path":"/usr/share/zoneinfo/posix/America/Whitehorse","mode":33188,"size":1609,"sha256":"e4afd69d844499d8bf3bb276d3ecab98ac10cddb21c180b6717e5635485ccf38"},{"path":"/usr/share/zoneinfo/posix/America/Winnipeg","mode":33188,"size":2891,"sha256":"77be5c08f6f8ebe5330fb86a60c4447ea2549620609f4ef6a7a7a68d1a12d9d6"},{"path":"/usr/share/zoneinfo/posix/America/Yakutat","mode":33188,"size":2314,"sha256":"07f189f49873b1392989ecbde19d19d33cd6c16953bf7e6b927ca2f1040f7106"},{"path":"/usr/share/zoneinfo/posix/America/Yellowknife","mode":33188,"size":1980,"sha256":"3140de7fe4136fb4920e8bb8ed8d707256e78c672edfce1657ae22672de68768"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Casey","mode":33188,"size":311,"sha256":"008325b0ed1b879047cfd030ccd24cb2fdaaeecdeaedc273f77aaa888ade3136"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Davis","mode":33188,"size":311,"sha256":"8dec77b2a23389d30c680a6fb0241cae32f1c0c71bf28fde1679bdb035a2939b"},{"path":"/usr/share/zoneinfo/posix/Antarctica/DumontDUrville","mode":33188,"size":216,"sha256":"86d1e72a7cad1d9817f57d456e39184b749436a02783a272f2109994addfbd55"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Macquarie","mode":33188,"size":1543,"sha256":"edccaab42adcfc7fa4872ff22b63fdc128a3354fa7d443f895b8f7068ced788f"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Mawson","mode":33188,"size":225,"sha256":"afa4aec36d9ff91992970b4c645e038810f25d8e58118a56568dbc9226704543"},{"path":"/usr/share/zoneinfo/posix/Antarctica/McMurdo","mode":33188,"size":2460,"sha256":"d7b5175387ac78e29f7b9021e411512756be283ed3d1819942ef5d45ecf338e4"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Palmer","mode":33188,"size":1432,"sha256":"aa3fc7dd1b1f1599bf71ed328ae5dba81e09ac3e3a914689e7ea5ff3adc28183"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Rothera","mode":33188,"size":186,"sha256":"e67d9eb78b53d3a415865402758eca495c69c347ed0ca7d5a0238c5f7ac01d8b"},{"path":"/usr/share/zoneinfo/posix/Antarctica/South_Pole","mode":33188,"size":2460,"sha256":"d7b5175387ac78e29f7b9021e411512756be283ed3d1819942ef5d45ecf338e4"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Syowa","mode":33188,"size":187,"sha256":"aef765ec9b3fae2cedbbaf2b525505008aa24f2f4e06abae3f770a9677387879"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Troll","mode":33188,"size":1176,"sha256":"1d8bdfe767292729981993a64fd8a2f745b24058c8bcbcf21bf3b0b6d5075c2d"},{"path":"/usr/share/zoneinfo/posix/Antarctica/Vostok","mode":33188,"size":187,"sha256":"903d2010d8a06be20cd57000e89d92e6f8307dca3810294215a58cd7c7c863e2"},{"path":"/usr/share/zoneinfo/posix/Arctic/Longyearbyen","mode":33188,"size":2251,"sha256":"0fa4e635da2b178fa3ea13ff3829c702844cf8bd69e16bca8e1d34dbd9249d01"},{"path":"/usr/share/zoneinfo/posix/Asia/Aden","mode":33188,"size":187,"sha256":"3102c1755d9a64b2e2b363381bbf52d6a01eb866a4d2cdfd0cf7e0832517094d"},{"path":"/usr/share/zoneinfo/posix/Asia/Almaty","mode":33188,"size":1031,"sha256":"4401628c6d2a36430efdddec3d9aeb9ff091e85daa21d0783298cddfe70c38c4"},{"path":"/usr/share/zoneinfo/posix/Asia/Amman","mode":33188,"size":1877,"sha256":"ba18a1f823f77e478e7030eeb82ddd71a5f3fae6efdf56325b7776304912da08"},{"path":"/usr/share/zoneinfo/posix/Asia/Anadyr","mode":33188,"size":1222,"sha256":"b4b88045d6624e21cb233c7c6226edee88afb63e0ca8d4e3df580d74a6c8a34c"},{"path":"/usr/share/zoneinfo/posix/Asia/Aqtau","mode":33188,"size":1017,"sha256":"e2e79c79371b0c8601cc8da9dc613145b60721e9c574310ed4b7fa9ae9baa30b"},{"path":"/usr/share/zoneinfo/posix/Asia/Aqtobe","mode":33188,"size":1047,"sha256":"ccd2ab0718fc8a637bb44576e4ca3ff267151cc4081dc697e69ebd426dbe4c1d"},{"path":"/usr/share/zoneinfo/posix/Asia/Ashgabat","mode":33188,"size":651,"sha256":"46284acf00fcee991886ee879f507f970bef4105a05d5e330736a02b329d3375"},{"path":"/usr/share/zoneinfo/posix/Asia/Ashkhabad","mode":33188,"size":651,"sha256":"46284acf00fcee991886ee879f507f970bef4105a05d5e330736a02b329d3375"},{"path":"/usr/share/zoneinfo/posix/Asia/Atyrau","mode":33188,"size":1025,"sha256":"44812ada1ccc49ab42dd04e3c5ebe8f9f592682765b0e400972662c34ef6e931"},{"path":"/usr/share/zoneinfo/posix/Asia/Baghdad","mode":33188,"size":1004,"sha256":"942ba9632d564f1e29f60e75a7edf598d3b001515ecdd7d403b147e5bf703cb1"},{"path":"/usr/share/zoneinfo/posix/Asia/Bahrain","mode":33188,"size":225,"sha256":"f15d455b503a1d9b99a9bc15f27e0d87d9bf3cac8100709f6a3140e63bab56bd"},{"path":"/usr/share/zoneinfo/posix/Asia/Baku","mode":33188,"size":1269,"sha256":"8efffa197f6ee0747d60f4b37db8823d2f712f3df7350bfb40461641d9e7ca31"},{"path":"/usr/share/zoneinfo/posix/Asia/Bangkok","mode":33188,"size":220,"sha256":"cf866703a05b067069db05f87584d5c8a3489bcaad3e41bb012609904915c11b"},{"path":"/usr/share/zoneinfo/posix/Asia/Barnaul","mode":33188,"size":1255,"sha256":"b556552d881c7729f21a4fb10c5e75e3885afc08e539461d40d6e4e359dcdd7f"},{"path":"/usr/share/zoneinfo/posix/Asia/Beirut","mode":33188,"size":2175,"sha256":"abdfa509ed982455873c1035962d8642ae8b88ab75f7f1a9a4cf7eea5ce120ef"},{"path":"/usr/share/zoneinfo/posix/Asia/Bishkek","mode":33188,"size":1045,"sha256":"8b449cf64ad7d46bae4196787f47012bfd0899aafd7cac77f8794dd7730b41ee"},{"path":"/usr/share/zoneinfo/posix/Asia/Brunei","mode":33188,"size":229,"sha256":"cd14c89f40eaece7f87f9679ebd6fdc23356c1ee31da031400c59806044ca4d1"},{"path":"/usr/share/zoneinfo/posix/Asia/Calcutta","mode":33188,"size":312,"sha256":"c71d7bc10d52c64f59eae8eac701c1b156bbec3fd9fe750970bed15e9b408fa5"},{"path":"/usr/share/zoneinfo/posix/Asia/Chita","mode":33188,"size":1257,"sha256":"3bc537b6c3f62fbcd134ce4c8e58c351a5770b9216f2483f1e36d8ec9035b3bc"},{"path":"/usr/share/zoneinfo/posix/Asia/Choibalsan","mode":33188,"size":991,"sha256":"6ea08272fe78ef15058b5821d053e907ea937db9bb6ca8f71cb9997a44c64315"},{"path":"/usr/share/zoneinfo/posix/Asia/Chongqing","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/posix/Asia/Chungking","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/posix/Asia/Colombo","mode":33188,"size":413,"sha256":"60108a5aec08236b5e9132d33de72649cdf01f854c86d01a8bd609d820b569ba"},{"path":"/usr/share/zoneinfo/posix/Asia/Dacca","mode":33188,"size":370,"sha256":"b17631c1fb3033ffde15391d2fbec4e3d29b846fd2cfb089898c6b61308eb7b2"},{"path":"/usr/share/zoneinfo/posix/Asia/Damascus","mode":33188,"size":2320,"sha256":"0f42d5702ee52944dde43071569de645a5d668a385c4a2e0cd8aa43d39d2ea21"},{"path":"/usr/share/zoneinfo/posix/Asia/Dhaka","mode":33188,"size":370,"sha256":"b17631c1fb3033ffde15391d2fbec4e3d29b846fd2cfb089898c6b61308eb7b2"},{"path":"/usr/share/zoneinfo/posix/Asia/Dili","mode":33188,"size":253,"sha256":"1f691df244d73613de758975adca5454ee9a91821b3f4382ea9b793ef04b1fc4"},{"path":"/usr/share/zoneinfo/posix/Asia/Dubai","mode":33188,"size":187,"sha256":"52c19684fb4943773d86c43f78c7ad7b46ae7557a8ae9ed16508342bd319678a"},{"path":"/usr/share/zoneinfo/posix/Asia/Dushanbe","mode":33188,"size":621,"sha256":"e832524a0d020a34015e423182bec05920c1e73b4149aab1bb31b7479a0a8f4c"},{"path":"/usr/share/zoneinfo/posix/Asia/Famagusta","mode":33188,"size":2042,"sha256":"4a3e66759c060ff5d9e338169781678161df5b9acd9aec6146f1d4d3cfd9030b"},{"path":"/usr/share/zoneinfo/posix/Asia/Gaza","mode":33188,"size":2351,"sha256":"9c1013e60b7005b6909a9ed2eac9490f682ed99367023eb7f324f73f4958b66b"},{"path":"/usr/share/zoneinfo/posix/Asia/Harbin","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/posix/Asia/Hebron","mode":33188,"size":2379,"sha256":"c591e178b7f704a365468e6e933004b798303e100142f6d940bd8e45a061903d"},{"path":"/usr/share/zoneinfo/posix/Asia/Ho_Chi_Minh","mode":33188,"size":389,"sha256":"013ffccf1a05a9e7b509b55f6b949569dd9e676bfcce10c886fffe59745440e5"},{"path":"/usr/share/zoneinfo/posix/Asia/Hong_Kong","mode":33188,"size":1231,"sha256":"680a46ee9866bd0c8435fef70694663c1e8ca2ba1e50ff2979ad62f27295707a"},{"path":"/usr/share/zoneinfo/posix/Asia/Hovd","mode":33188,"size":921,"sha256":"cdc65f913f2b67cd1d23286944546c42fabb64720b78aaf32f88605a1943689a"},{"path":"/usr/share/zoneinfo/posix/Asia/Irkutsk","mode":33188,"size":1276,"sha256":"77ed8a38a9f3e4a65a5ded6a846089c4c8a60eb245c476f7ee20d62780303eef"},{"path":"/usr/share/zoneinfo/posix/Asia/Istanbul","mode":33188,"size":1970,"sha256":"2f24f072fa325c0a9bbecc48ea2782317c459a6cad941a37f7e305238443c45a"},{"path":"/usr/share/zoneinfo/posix/Asia/Jakarta","mode":33188,"size":392,"sha256":"7ea1c3e53a0d3f40cb6d7724f1bacb4fca1cf0ae96d9ab42f00f2d30dc0dee3a"},{"path":"/usr/share/zoneinfo/posix/Asia/Jayapura","mode":33188,"size":251,"sha256":"c6fa24de2e83f471878b8e10ecd68828eb3aba1f49ce462dac7721661386eb0c"},{"path":"/usr/share/zoneinfo/posix/Asia/Jerusalem","mode":33188,"size":2321,"sha256":"1e61da0baf4d2d8f149ed84b8694cc5d4aadbee78d2014771417a67622e653fa"},{"path":"/usr/share/zoneinfo/posix/Asia/Kabul","mode":33188,"size":229,"sha256":"386b98b95b19bbec52c6d8f334e04a178f4f99f2b8a1cea33c142375668d7227"},{"path":"/usr/share/zoneinfo/posix/Asia/Kamchatka","mode":33188,"size":1198,"sha256":"a45d587c7134607cb6feade6af9a04203c38b1ed481f7c7ce8eb10e7cd972cac"},{"path":"/usr/share/zoneinfo/posix/Asia/Karachi","mode":33188,"size":417,"sha256":"fc4b2a68ad79efadecf52f333fa19cbaa5dd084cdc9bf96ab8b65a75c559a370"},{"path":"/usr/share/zoneinfo/posix/Asia/Kashgar","mode":33188,"size":187,"sha256":"9ae8868df5441ce4ac33aaed777f5ea6883eb95050b7d66d1e5ec5648c9e3fcc"},{"path":"/usr/share/zoneinfo/posix/Asia/Kathmandu","mode":33188,"size":238,"sha256":"5c557b86c5f0fdd19d105afbd38bd9daaad1cd075e9efdbe80547ddca85ae5ae"},{"path":"/usr/share/zoneinfo/posix/Asia/Katmandu","mode":33188,"size":238,"sha256":"5c557b86c5f0fdd19d105afbd38bd9daaad1cd075e9efdbe80547ddca85ae5ae"},{"path":"/usr/share/zoneinfo/posix/Asia/Khandyga","mode":33188,"size":1311,"sha256":"0169f2ad82832f6466984cad9cc673fb4098ee15e14b21521ce54f37a3fa6de3"},{"path":"/usr/share/zoneinfo/posix/Asia/Kolkata","mode":33188,"size":312,"sha256":"c71d7bc10d52c64f59eae8eac701c1b156bbec3fd9fe750970bed15e9b408fa5"},{"path":"/usr/share/zoneinfo/posix/Asia/Krasnoyarsk","mode":33188,"size":1243,"sha256":"9122ec3df9d2f1e1767edfbc9cce49e7cff95491cb9de234c4588f985eb361c8"},{"path":"/usr/share/zoneinfo/posix/Asia/Kuala_Lumpur","mode":33188,"size":424,"sha256":"268d3cc29dae9854fea1b9109da2873602c48806994d3f3df0b9ca9863fcf59b"},{"path":"/usr/share/zoneinfo/posix/Asia/Kuching","mode":33188,"size":521,"sha256":"0d0c68d2cddcf9431056b27b884c89951de456a484fdf96a2b10c78faf195bd8"},{"path":"/usr/share/zoneinfo/posix/Asia/Kuwait","mode":33188,"size":187,"sha256":"3102c1755d9a64b2e2b363381bbf52d6a01eb866a4d2cdfd0cf7e0832517094d"},{"path":"/usr/share/zoneinfo/posix/Asia/Macao","mode":33188,"size":1255,"sha256":"bc423d28d8ba83fb0ba6984472c46dc83c014dd4876b59f6c8e2a4d8761fc585"},{"path":"/usr/share/zoneinfo/posix/Asia/Macau","mode":33188,"size":1255,"sha256":"bc423d28d8ba83fb0ba6984472c46dc83c014dd4876b59f6c8e2a4d8761fc585"},{"path":"/usr/share/zoneinfo/posix/Asia/Magadan","mode":33188,"size":1258,"sha256":"a32f022b2aa9b370f41866047c28b6d96007bec7e7f05e4fd1a2f06111057e8b"},{"path":"/usr/share/zoneinfo/posix/Asia/Makassar","mode":33188,"size":288,"sha256":"24fac901695ef43b73fa8b3cd9e4bf893ceb757c5200b6628ae6a0fc70f01956"},{"path":"/usr/share/zoneinfo/posix/Asia/Manila","mode":33188,"size":359,"sha256":"01cb854c5033bef7324b3102f4362206e1a792d703a478fe090135943b180392"},{"path":"/usr/share/zoneinfo/posix/Asia/Muscat","mode":33188,"size":187,"sha256":"52c19684fb4943773d86c43f78c7ad7b46ae7557a8ae9ed16508342bd319678a"},{"path":"/usr/share/zoneinfo/posix/Asia/Nicosia","mode":33188,"size":2016,"sha256":"f2aa2a3f77a43b7558a7508a6cd6c50fdf7d991f9d64da5948fd9003923b1d72"},{"path":"/usr/share/zoneinfo/posix/Asia/Novokuznetsk","mode":33188,"size":1197,"sha256":"45df208266ce41dccdae6a47b6b78235a2e70c4eeb69b28e30125e03e7b9e0d3"},{"path":"/usr/share/zoneinfo/posix/Asia/Novosibirsk","mode":33188,"size":1255,"sha256":"53f555c078378d726db6d203c96bee7efc9b138c10cfd634f750b28cb6212ba5"},{"path":"/usr/share/zoneinfo/posix/Asia/Omsk","mode":33188,"size":1243,"sha256":"e32bfb976274657a892f5918b3f42e56c838dac040e06ac60c2d36318c80fd49"},{"path":"/usr/share/zoneinfo/posix/Asia/Oral","mode":33188,"size":1039,"sha256":"4ddd665f81f9ffe7fa3c7540f5065ddad72274da22913885eefe86951a857998"},{"path":"/usr/share/zoneinfo/posix/Asia/Phnom_Penh","mode":33188,"size":220,"sha256":"cf866703a05b067069db05f87584d5c8a3489bcaad3e41bb012609904915c11b"},{"path":"/usr/share/zoneinfo/posix/Asia/Pontianak","mode":33188,"size":395,"sha256":"2516ac2bc84fe6498a50bc8865ec00e3499b38f2f485403cd5028578a98d1fd8"},{"path":"/usr/share/zoneinfo/posix/Asia/Pyongyang","mode":33188,"size":267,"sha256":"a108bfd54c6c22fbc67177c281c1058dfb1f00f40803ffc04fda5f41d4ba6505"},{"path":"/usr/share/zoneinfo/posix/Asia/Qatar","mode":33188,"size":225,"sha256":"f15d455b503a1d9b99a9bc15f27e0d87d9bf3cac8100709f6a3140e63bab56bd"},{"path":"/usr/share/zoneinfo/posix/Asia/Qostanay","mode":33188,"size":1047,"sha256":"b763af98dc579384866d60e3541d7f87c10b492310a4bdd3f927d28d091edeca"},{"path":"/usr/share/zoneinfo/posix/Asia/Qyzylorda","mode":33188,"size":1077,"sha256":"e116692a053d3b100258a742dd5577df8ae1e262d0f23830606c87b80031d4a2"},{"path":"/usr/share/zoneinfo/posix/Asia/Rangoon","mode":33188,"size":297,"sha256":"1b4605825adbae3c7136f3f055d7cbac76faad62703516eaf94fc8d10e1df3ad"},{"path":"/usr/share/zoneinfo/posix/Asia/Riyadh","mode":33188,"size":187,"sha256":"3102c1755d9a64b2e2b363381bbf52d6a01eb866a4d2cdfd0cf7e0832517094d"},{"path":"/usr/share/zoneinfo/posix/Asia/Saigon","mode":33188,"size":389,"sha256":"013ffccf1a05a9e7b509b55f6b949569dd9e676bfcce10c886fffe59745440e5"},{"path":"/usr/share/zoneinfo/posix/Asia/Sakhalin","mode":33188,"size":1234,"sha256":"d6af67dd853ea20ec92aa39fdd647b70ec329606e7565536030dbdd70f062148"},{"path":"/usr/share/zoneinfo/posix/Asia/Samarkand","mode":33188,"size":619,"sha256":"fd928b56ff2b6fdf1e28c198d8871e87979473109dfc395a51d8aaed0efb5924"},{"path":"/usr/share/zoneinfo/posix/Asia/Seoul","mode":33188,"size":659,"sha256":"3673a9439d49ea97b47c9fb28433c6d41c469ca03ad320768f1514d075647c26"},{"path":"/usr/share/zoneinfo/posix/Asia/Shanghai","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/posix/Asia/Singapore","mode":33188,"size":424,"sha256":"e6929fde43ffc48bbac4081b31bbf7fd42643b3c26fadf322bdeadeb23cfc748"},{"path":"/usr/share/zoneinfo/posix/Asia/Srednekolymsk","mode":33188,"size":1244,"sha256":"35c545e24d61a31f5fd4fa712d8b6cc09ecbdfddee10e5b859d6b29e57d98806"},{"path":"/usr/share/zoneinfo/posix/Asia/Taipei","mode":33188,"size":790,"sha256":"25cfd02bc847bdcb11e586445ba886a76315f1f9be86f7e74944a6e8e8644543"},{"path":"/usr/share/zoneinfo/posix/Asia/Tashkent","mode":33188,"size":635,"sha256":"8674eb501cd25c540258e94006ce151f91f653849e800aa97986551b89ead688"},{"path":"/usr/share/zoneinfo/posix/Asia/Tbilisi","mode":33188,"size":1080,"sha256":"bc88efdf57da66aaa71c15d8fbc36d87242adca776e103ddd5531aa45ca21177"},{"path":"/usr/share/zoneinfo/posix/Asia/Tehran","mode":33188,"size":2624,"sha256":"29fc1861f6e088decab370c3ef2c090d0c3fbdea50b78c2d3158ddaf001b8088"},{"path":"/usr/share/zoneinfo/posix/Asia/Tel_Aviv","mode":33188,"size":2321,"sha256":"1e61da0baf4d2d8f149ed84b8694cc5d4aadbee78d2014771417a67622e653fa"},{"path":"/usr/share/zoneinfo/posix/Asia/Thimbu","mode":33188,"size":229,"sha256":"e54c4d565a4be5f34209ba351c7aadd1071dccf8a0380d69e06e936a425203a2"},{"path":"/usr/share/zoneinfo/posix/Asia/Thimphu","mode":33188,"size":229,"sha256":"e54c4d565a4be5f34209ba351c7aadd1071dccf8a0380d69e06e936a425203a2"},{"path":"/usr/share/zoneinfo/posix/Asia/Tokyo","mode":33188,"size":318,"sha256":"046bb09bc08554ef8a54dc05685d0eab10e04c692f6320b6091b6a6f07214c83"},{"path":"/usr/share/zoneinfo/posix/Asia/Tomsk","mode":33188,"size":1255,"sha256":"1142db40b91678b4ab3c2935346f6f0bce6a84353392a1ab97dbeba0ee1582d5"},{"path":"/usr/share/zoneinfo/posix/Asia/Ujung_Pandang","mode":33188,"size":288,"sha256":"24fac901695ef43b73fa8b3cd9e4bf893ceb757c5200b6628ae6a0fc70f01956"},{"path":"/usr/share/zoneinfo/posix/Asia/Ulaanbaatar","mode":33188,"size":921,"sha256":"17a31d0ea8eaf0d1484b54e53d6803eaeaa832740d521a340e1d5c073de97e22"},{"path":"/usr/share/zoneinfo/posix/Asia/Ulan_Bator","mode":33188,"size":921,"sha256":"17a31d0ea8eaf0d1484b54e53d6803eaeaa832740d521a340e1d5c073de97e22"},{"path":"/usr/share/zoneinfo/posix/Asia/Urumqi","mode":33188,"size":187,"sha256":"9ae8868df5441ce4ac33aaed777f5ea6883eb95050b7d66d1e5ec5648c9e3fcc"},{"path":"/usr/share/zoneinfo/posix/Asia/Ust-Nera","mode":33188,"size":1290,"sha256":"ab0edbe8871813e11548d34641521878aca12634a44683945d24ef85016bd0aa"},{"path":"/usr/share/zoneinfo/posix/Asia/Vientiane","mode":33188,"size":220,"sha256":"cf866703a05b067069db05f87584d5c8a3489bcaad3e41bb012609904915c11b"},{"path":"/usr/share/zoneinfo/posix/Asia/Vladivostok","mode":33188,"size":1244,"sha256":"32eb6e1405aa048e6cba3396d4b09ad04ed05c239dbcb054f82e4dbbd2dbbd31"},{"path":"/usr/share/zoneinfo/posix/Asia/Yakutsk","mode":33188,"size":1243,"sha256":"545036a8cb48068d5f6f98bd28eb90bb6c25d3136b58f01486b875780519208e"},{"path":"/usr/share/zoneinfo/posix/Asia/Yangon","mode":33188,"size":297,"sha256":"1b4605825adbae3c7136f3f055d7cbac76faad62703516eaf94fc8d10e1df3ad"},{"path":"/usr/share/zoneinfo/posix/Asia/Yekaterinburg","mode":33188,"size":1281,"sha256":"8819eff29a90ad2c0d3588f56d6e974d99419e80104bfc9313274f0a33e0b590"},{"path":"/usr/share/zoneinfo/posix/Asia/Yerevan","mode":33188,"size":1213,"sha256":"2e456011e9e0d8c1958c17bf34116fe89a3239028010e7db61ae46012c8f2304"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Azores","mode":33188,"size":3493,"sha256":"d3dfcd9c77d1e2a49e15c87aff9e43f0d5283a532b4bc6c7afa22fa14fa0c377"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Bermuda","mode":33188,"size":2004,"sha256":"462d205904f32dcb79317f83ddb4dea1548d51849217dc3e42ba17c3cc7fcf08"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Canary","mode":33188,"size":1911,"sha256":"4617cb1aa75514003f181908e9ccfc1d3d062ef22bb0196867dbe530ec2e1416"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Cape_Verde","mode":33188,"size":284,"sha256":"f7a81342ed5884f34fdc07e6ebf8f0f322e41ba3e2d399d7f516b4d28771350b"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Faeroe","mode":33188,"size":1829,"sha256":"6b1a5769f8ffa2ec29bf298dffd7fb324e625e36fc527c14bb66b6520e6f76a7"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Faroe","mode":33188,"size":1829,"sha256":"6b1a5769f8ffa2ec29bf298dffd7fb324e625e36fc527c14bb66b6520e6f76a7"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Jan_Mayen","mode":33188,"size":2251,"sha256":"0fa4e635da2b178fa3ea13ff3829c702844cf8bd69e16bca8e1d34dbd9249d01"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Madeira","mode":33188,"size":3484,"sha256":"24c616780589fb6a7e22913e3402522517ba4a7460738ccd38f1a3a0e4a21f40"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Reykjavik","mode":33188,"size":1188,"sha256":"9cdcea6aa1eed8276d3f6620e0c0ffae9cfcc3722c443ea6ba39147975eafaa3"},{"path":"/usr/share/zoneinfo/posix/Atlantic/South_Georgia","mode":33188,"size":181,"sha256":"f745dca3964c6ae3e8b88166e0db6df487ee8f6e6ad7fb1ac3ad4e6ab2e0a361"},{"path":"/usr/share/zoneinfo/posix/Atlantic/St_Helena","mode":33188,"size":170,"sha256":"d5ded126df8f693ce1ff83e85aa4d44185c2bdef7da1f915b214f53deffdee47"},{"path":"/usr/share/zoneinfo/posix/Atlantic/Stanley","mode":33188,"size":1251,"sha256":"57ee27fac7d72ba2c34725702e5876aa27462a09ac4b841b40122afe103a4c41"},{"path":"/usr/share/zoneinfo/posix/Australia/ACT","mode":33188,"size":2223,"sha256":"b540f8e21ed6a6b262336e0eb020c18ab43f283e9774613dd9864239523e4233"},{"path":"/usr/share/zoneinfo/posix/Australia/Adelaide","mode":33188,"size":2238,"sha256":"735476eef81652d7189574f8b7a11c942a986aba24b6ddc644fbebd1eb49245c"},{"path":"/usr/share/zoneinfo/posix/Australia/Brisbane","mode":33188,"size":452,"sha256":"74ac9f5d1d15ef0f6bd9e69c687b9047fb1f749c59279475685721f574b427cc"},{"path":"/usr/share/zoneinfo/posix/Australia/Broken_Hill","mode":33188,"size":2274,"sha256":"d6451675d3b5afb8572e2cbb4d381730da23daa3bfcb57601fe6f815985237db"},{"path":"/usr/share/zoneinfo/posix/Australia/Canberra","mode":33188,"size":2223,"sha256":"b540f8e21ed6a6b262336e0eb020c18ab43f283e9774613dd9864239523e4233"},{"path":"/usr/share/zoneinfo/posix/Australia/Currie","mode":33188,"size":2223,"sha256":"543c7afaebfdd907f8d637efce48bf41c407da72658b8e9c12f7208a54d1d84a"},{"path":"/usr/share/zoneinfo/posix/Australia/Darwin","mode":33188,"size":323,"sha256":"6172d8687a78608d884b04903d36053bdfb56433541930b2a42b405cbb62dc0b"},{"path":"/usr/share/zoneinfo/posix/Australia/Eucla","mode":33188,"size":503,"sha256":"42c7f9c44cf8dbfd564a7539b86278d98285476578bef4bfc01cc3fc61ebb2ba"},{"path":"/usr/share/zoneinfo/posix/Australia/Hobart","mode":33188,"size":2335,"sha256":"de1bb5e82f86774e70082b906462e02a062238e5c4d76149566e21b1cb31b23a"},{"path":"/usr/share/zoneinfo/posix/Australia/LHI","mode":33188,"size":1889,"sha256":"09626975ee86238fd5f85bc275eafad83bc696709d78144cc0bd4ced75acaf2d"},{"path":"/usr/share/zoneinfo/posix/Australia/Lindeman","mode":33188,"size":522,"sha256":"663df35f044a15c743b9716e183595147d0c1838e99148a9473623ac82076bf9"},{"path":"/usr/share/zoneinfo/posix/Australia/Lord_Howe","mode":33188,"size":1889,"sha256":"09626975ee86238fd5f85bc275eafad83bc696709d78144cc0bd4ced75acaf2d"},{"path":"/usr/share/zoneinfo/posix/Australia/Melbourne","mode":33188,"size":2223,"sha256":"272c1f13d01e35e6a58855cbb53878795451928adbf0c8ca2982b79db1f450a7"},{"path":"/usr/share/zoneinfo/posix/Australia/NSW","mode":33188,"size":2223,"sha256":"b540f8e21ed6a6b262336e0eb020c18ab43f283e9774613dd9864239523e4233"},{"path":"/usr/share/zoneinfo/posix/Australia/North","mode":33188,"size":323,"sha256":"6172d8687a78608d884b04903d36053bdfb56433541930b2a42b405cbb62dc0b"},{"path":"/usr/share/zoneinfo/posix/Australia/Perth","mode":33188,"size":479,"sha256":"4ecd4a085ca9ec5b7903016c2d4e311276024a2bcd0c35d40281658e48421f93"},{"path":"/usr/share/zoneinfo/posix/Australia/Queensland","mode":33188,"size":452,"sha256":"74ac9f5d1d15ef0f6bd9e69c687b9047fb1f749c59279475685721f574b427cc"},{"path":"/usr/share/zoneinfo/posix/Australia/South","mode":33188,"size":2238,"sha256":"735476eef81652d7189574f8b7a11c942a986aba24b6ddc644fbebd1eb49245c"},{"path":"/usr/share/zoneinfo/posix/Australia/Sydney","mode":33188,"size":2223,"sha256":"b540f8e21ed6a6b262336e0eb020c18ab43f283e9774613dd9864239523e4233"},{"path":"/usr/share/zoneinfo/posix/Australia/Tasmania","mode":33188,"size":2335,"sha256":"de1bb5e82f86774e70082b906462e02a062238e5c4d76149566e21b1cb31b23a"},{"path":"/usr/share/zoneinfo/posix/Australia/Victoria","mode":33188,"size":2223,"sha256":"272c1f13d01e35e6a58855cbb53878795451928adbf0c8ca2982b79db1f450a7"},{"path":"/usr/share/zoneinfo/posix/Australia/West","mode":33188,"size":479,"sha256":"4ecd4a085ca9ec5b7903016c2d4e311276024a2bcd0c35d40281658e48421f93"},{"path":"/usr/share/zoneinfo/posix/Australia/Yancowinna","mode":33188,"size":2274,"sha256":"d6451675d3b5afb8572e2cbb4d381730da23daa3bfcb57601fe6f815985237db"},{"path":"/usr/share/zoneinfo/posix/Brazil/Acre","mode":33188,"size":662,"sha256":"16c86cccc93c7ebfeffae880e439ce848055e421578982d5cabef8aaec15f802"},{"path":"/usr/share/zoneinfo/posix/Brazil/DeNoronha","mode":33188,"size":742,"sha256":"cb4e968f415ed53e769108c9d5f9710e898716af74536d39b7077b0426f3960d"},{"path":"/usr/share/zoneinfo/posix/Brazil/East","mode":33188,"size":1470,"sha256":"a4090cbdfa5168012d460585f7eab9302f8848cca0419d73cf03993ef12c08c4"},{"path":"/usr/share/zoneinfo/posix/Brazil/West","mode":33188,"size":630,"sha256":"e1213e7b97cfa580b4f9c728c34ffa64a6ab277b06b558893b299c20d3528e6c"},{"path":"/usr/share/zoneinfo/posix/CET","mode":33188,"size":2102,"sha256":"3c0029045f6f80bc5a84f1bb8ed36230454759c54578eb9a8c195d14f442213c"},{"path":"/usr/share/zoneinfo/posix/CST6CDT","mode":33188,"size":2294,"sha256":"44e8b569e60027647f9801a33d0b43be0106a6d3f6cd059677e0ed65c9b8b831"},{"path":"/usr/share/zoneinfo/posix/Canada/Atlantic","mode":33188,"size":3438,"sha256":"627e18218c6f3c3f446c4970abe8164672e2a7ba94bcf841b1e06af5089b94ea"},{"path":"/usr/share/zoneinfo/posix/Canada/Central","mode":33188,"size":2891,"sha256":"77be5c08f6f8ebe5330fb86a60c4447ea2549620609f4ef6a7a7a68d1a12d9d6"},{"path":"/usr/share/zoneinfo/posix/Canada/Eastern","mode":33188,"size":3503,"sha256":"842f7a103dfac9c0c2c33c9cc392a113d266ac064c5c7497883ab41b797ce194"},{"path":"/usr/share/zoneinfo/posix/Canada/Mountain","mode":33188,"size":2346,"sha256":"92ac6208f1ef357787fcfce6a334990252189eb0b427b28bc60e21ab5e792b3c"},{"path":"/usr/share/zoneinfo/posix/Canada/Newfoundland","mode":33188,"size":3664,"sha256":"2b960a58d6d3f6a272707f941f55b15b8ba3fd0fd55f8680ea84af6b1e98bae0"},{"path":"/usr/share/zoneinfo/posix/Canada/Pacific","mode":33188,"size":2901,"sha256":"460182c93960fd636820b1b43cfec871da4f0197556bb6bdb2fa527b637a4332"},{"path":"/usr/share/zoneinfo/posix/Canada/Saskatchewan","mode":33188,"size":994,"sha256":"929d07457407529637626d09f5ca975b4f05801f35d0bfac4e3b0027efee6776"},{"path":"/usr/share/zoneinfo/posix/Canada/Yukon","mode":33188,"size":1609,"sha256":"e4afd69d844499d8bf3bb276d3ecab98ac10cddb21c180b6717e5635485ccf38"},{"path":"/usr/share/zoneinfo/posix/Chile/Continental","mode":33188,"size":2538,"sha256":"b83e4129763ef7a22be3fba68029b4ecb6f14a360112498446d8c89640f420b5"},{"path":"/usr/share/zoneinfo/posix/Chile/EasterIsland","mode":33188,"size":2242,"sha256":"d344955a3a8dea47b50a72d2af7fde01a6a27365bef0fefb2c11429a4f5dfca1"},{"path":"/usr/share/zoneinfo/posix/Cuba","mode":33188,"size":2437,"sha256":"7871f875a8819f415c292519db1590556a0dc1a6ce691bf4f7af55e6716fb894"},{"path":"/usr/share/zoneinfo/posix/EET","mode":33188,"size":1876,"sha256":"0bf6d2669ab45c13a1c9be47c351972feb671770b90a61d9d313fc60b721b2b4"},{"path":"/usr/share/zoneinfo/posix/EST","mode":33188,"size":127,"sha256":"c9e75f112a498ff00344551c3c5c4a62bd15d5c218ee951f4363ab218c5d88eb"},{"path":"/usr/share/zoneinfo/posix/EST5EDT","mode":33188,"size":2294,"sha256":"79ce27e03a2752091e8a49cc7e7ccc9ac202d6c52dd5d224571fe82262fbeec8"},{"path":"/usr/share/zoneinfo/posix/Egypt","mode":33188,"size":1972,"sha256":"279bbe1fa62da67387c63593b60bb655252ef5c8f189cf43469087740af2b4fc"},{"path":"/usr/share/zoneinfo/posix/Eire","mode":33188,"size":3543,"sha256":"ff19972d561b3b6a9bdb0ec69a3ed3b59ca5ccd1b14929e29bf86d757255eec2"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+1","mode":33188,"size":148,"sha256":"35d004edb2a0b1137ae1ea3659ef8e95a753330f0713fc94929d0f79d8021b07"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+10","mode":33188,"size":149,"sha256":"4762603f3f51c0d5063ea549f9a578b7ebf26e47fd7109a6e34495ac3e09b2ed"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+11","mode":33188,"size":149,"sha256":"8a23521d6e93326291dbdacf2857f8a78970bef3dd93a53557da4cc2e79c36ba"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+12","mode":33188,"size":149,"sha256":"ec7046f7e41252f839950ce04e3f20e41ba228e678aae2a45b5b050ba990e626"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+2","mode":33188,"size":148,"sha256":"21319b8c2634a8349e84c3bef422998f6dd4f79bad91f79fa38145c1f6b694dd"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+3","mode":33188,"size":148,"sha256":"e7861defa0a8bc5e0ee58d8a7a993ac22950e3fed608c9532c680b74ef6cc67f"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+4","mode":33188,"size":148,"sha256":"0f0ab77c5beca68231484090c38ecc1ce211b135511d5431dc1994f8a2580c89"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+5","mode":33188,"size":148,"sha256":"be7cef32cf0094520b344fc461bc28747e617d6043b8be0b0871e87225ee8568"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+6","mode":33188,"size":148,"sha256":"d285eec873a91b2660ff29816304693056ee61ac1e9bd3485e26c4bcc067e041"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+7","mode":33188,"size":148,"sha256":"631be5659ae83739e1056e088289b642caf4d07be5887f74c6cc954e2b0e9e5c"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+8","mode":33188,"size":148,"sha256":"f0ede5d811e0d8b283b18b80aebe6ce617267664ec313fc5bf01e2880a8c4229"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT+9","mode":33188,"size":148,"sha256":"6aab552f947986b00b2d43ff28a3257ab7b88967322b9ce067e45c5ea96cc014"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-1","mode":33188,"size":149,"sha256":"d5f7f0682e71000de343fce27f2e8cff9e37e50cb064bf0f61245dc7ff6806ed"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-10","mode":33188,"size":150,"sha256":"2fdcfd00c1be46329891da92b46f49258b35c09eb9e1103e3789a3d58338eb78"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-11","mode":33188,"size":150,"sha256":"4439c8a7d5a8c87c47b7a81bd2e9534c8c676f610d4038fdf3b3951089a5db91"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-12","mode":33188,"size":150,"sha256":"5f0c2c21cec4020ec3116c038ca9ff5e5a9e863ddb7fc0beba7136c321b05851"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-13","mode":33188,"size":150,"sha256":"0c4e6bff6354406378f2bdb165fae025fa100fe8c7d76c6cfaabb716f6f096ca"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-14","mode":33188,"size":150,"sha256":"4685f92efa5bbdb625dd8d6454a340af8ac0510308b6b66847ad5f7bc3c4fc84"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-2","mode":33188,"size":149,"sha256":"530335b26ac0306edc8f0683a830bc1e7f5111ad228df4b74c197d2cb9c31387"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-3","mode":33188,"size":149,"sha256":"a59e1e4a707222ac22fefb3a6dc495cef266872a94d51e5ca862ffde74ef0c4c"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-4","mode":33188,"size":149,"sha256":"7d6471f8835da5e7906f8220dd9674b664573fee650f0a28b5ab51aa54a4524e"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-5","mode":33188,"size":149,"sha256":"33a439130048c8b6400ad082b2e4011c7b85fafe9171e13110aa86f266bedfa4"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-6","mode":33188,"size":149,"sha256":"f2ae16bd9a3a9a75788ca13a281bcc39567c93aaf5ad5402fcbfebac473b6cf7"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-7","mode":33188,"size":149,"sha256":"b0e37d9bf496f375b7c024e81b6ae5943ccbace0ffbecb684d8bd1847c5cb93a"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-8","mode":33188,"size":149,"sha256":"5ec67811fbce13ee23123eee60791be8cb5f9c84451ae0d8297738af9b7f0cca"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT-9","mode":33188,"size":149,"sha256":"16ed57cd7c3577fdc22d57683841e922b208a535e6125e686be4f8702a75f485"},{"path":"/usr/share/zoneinfo/posix/Etc/GMT0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/Etc/Greenwich","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/Etc/UCT","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/posix/Etc/UTC","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/posix/Etc/Universal","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/posix/Etc/Zulu","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/posix/Europe/Amsterdam","mode":33188,"size":2949,"sha256":"8a813ac6b8d1b68a7960242cae5325a2269fd1c791b203f8d22f2dfa3b61ba87"},{"path":"/usr/share/zoneinfo/posix/Europe/Andorra","mode":33188,"size":1751,"sha256":"add5505c473225e33a884a02105610a9b95003f429195624b953c18f771317af"},{"path":"/usr/share/zoneinfo/posix/Europe/Astrakhan","mode":33188,"size":1197,"sha256":"a027561f493c02a04d699903a08e9e78ac76eb3a719c4749d9ae9480418baad8"},{"path":"/usr/share/zoneinfo/posix/Europe/Athens","mode":33188,"size":2271,"sha256":"799090551202c0b8417f836facf75049573dd1c27b5e6adeb584fcc414051139"},{"path":"/usr/share/zoneinfo/posix/Europe/Belfast","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/posix/Europe/Belgrade","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/posix/Europe/Berlin","mode":33188,"size":2335,"sha256":"7eb93dcba603d528fdf536160ef6911c16f834afcf88ce23a382b97ff28319d4"},{"path":"/usr/share/zoneinfo/posix/Europe/Bratislava","mode":33188,"size":2338,"sha256":"7290e2da43a8b82b3c46ac2a05e072a8cecbf8516e5c286791dbdd68a761d205"},{"path":"/usr/share/zoneinfo/posix/Europe/Brussels","mode":33188,"size":2970,"sha256":"11497c2fd62834d7c1ab568fb47e5947a7f5a63378dc723d7f73ccab21da5342"},{"path":"/usr/share/zoneinfo/posix/Europe/Bucharest","mode":33188,"size":2221,"sha256":"3b3a0017333b2f466e59c8ac3dc0cf7aa4f0a4608040a3180f752b19d6a93526"},{"path":"/usr/share/zoneinfo/posix/Europe/Budapest","mode":33188,"size":2405,"sha256":"b67f2c4690a87f294ea5d35ae3967c8aa8bde227aeb36c3877285e4e94a17418"},{"path":"/usr/share/zoneinfo/posix/Europe/Busingen","mode":33188,"size":1918,"sha256":"bc45f8c6c8190477cdaae46f77059fab74fde92a02fc57b733f07cb9a55e98a3"},{"path":"/usr/share/zoneinfo/posix/Europe/Chisinau","mode":33188,"size":2445,"sha256":"5749f01c78d0c2fd50d0dc2280c1957ce0419edbfc7c4073c67e6da78153d8c8"},{"path":"/usr/share/zoneinfo/posix/Europe/Copenhagen","mode":33188,"size":2160,"sha256":"d2d9a359ef02d2afe293f429c4fd60fc04fbf8d1d8343c9b224dcfc116c011a8"},{"path":"/usr/share/zoneinfo/posix/Europe/Dublin","mode":33188,"size":3543,"sha256":"ff19972d561b3b6a9bdb0ec69a3ed3b59ca5ccd1b14929e29bf86d757255eec2"},{"path":"/usr/share/zoneinfo/posix/Europe/Gibraltar","mode":33188,"size":3061,"sha256":"c79088f67ba5d3fa9ad989bd573bfdef0e86c89e310ea70bc3e01e14dca1075e"},{"path":"/usr/share/zoneinfo/posix/Europe/Guernsey","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/posix/Europe/Helsinki","mode":33188,"size":1909,"sha256":"ed7d89fae1fb40a9582edd7e03ed02d7fe81ba456b9c1ed8d6ee5f0b931aad45"},{"path":"/usr/share/zoneinfo/posix/Europe/Isle_of_Man","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/posix/Europe/Istanbul","mode":33188,"size":1970,"sha256":"2f24f072fa325c0a9bbecc48ea2782317c459a6cad941a37f7e305238443c45a"},{"path":"/usr/share/zoneinfo/posix/Europe/Jersey","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/posix/Europe/Kaliningrad","mode":33188,"size":1532,"sha256":"78018b1f78b60635b744bc5d78ca209f87c184a634ffe11510b3dfe885eed165"},{"path":"/usr/share/zoneinfo/posix/Europe/Kiev","mode":33188,"size":2097,"sha256":"242912df3212e0725ded4aab25fd869c52f13c3ce619764a883adcbbd937afc5"},{"path":"/usr/share/zoneinfo/posix/Europe/Kirov","mode":33188,"size":1167,"sha256":"a44267313cba43fb671622af5b17cda285def184f6121e8ec6007164643e3c25"},{"path":"/usr/share/zoneinfo/posix/Europe/Lisbon","mode":33188,"size":3469,"sha256":"4bbe65d4ff3394ffa1b4ae6fe2296e333f55bad0ae49ca6717b6076e53490ea2"},{"path":"/usr/share/zoneinfo/posix/Europe/Ljubljana","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/posix/Europe/London","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/posix/Europe/Luxembourg","mode":33188,"size":2974,"sha256":"90b76259274c78a40f34aa5b58545b5409edfbba2fd08efa1b300896cb4062ee"},{"path":"/usr/share/zoneinfo/posix/Europe/Madrid","mode":33188,"size":2637,"sha256":"74103ad1e48f71f4cd9b6d1c03dcd97b58d87bb8affb02b1d6967b204036ebd6"},{"path":"/usr/share/zoneinfo/posix/Europe/Malta","mode":33188,"size":2629,"sha256":"7c4134c8d37bd159e31fd739e8b1b8203a9f3023788bd9c83b8109e361eee5d5"},{"path":"/usr/share/zoneinfo/posix/Europe/Mariehamn","mode":33188,"size":1909,"sha256":"ed7d89fae1fb40a9582edd7e03ed02d7fe81ba456b9c1ed8d6ee5f0b931aad45"},{"path":"/usr/share/zoneinfo/posix/Europe/Minsk","mode":33188,"size":1370,"sha256":"c82aa831a68fec1c918d23393d795fef9dbf4d0948791bcba6ba09f45b3826c4"},{"path":"/usr/share/zoneinfo/posix/Europe/Monaco","mode":33188,"size":2953,"sha256":"7c723359888417b86a66a609ffdd0becf81673cbb3e8b011131088b4d26f6bcd"},{"path":"/usr/share/zoneinfo/posix/Europe/Moscow","mode":33188,"size":1544,"sha256":"02d55516d0f9d497998260b4f129aee59867b77a920ba2ca0c58b15ec8588e7a"},{"path":"/usr/share/zoneinfo/posix/Europe/Nicosia","mode":33188,"size":2016,"sha256":"f2aa2a3f77a43b7558a7508a6cd6c50fdf7d991f9d64da5948fd9003923b1d72"},{"path":"/usr/share/zoneinfo/posix/Europe/Oslo","mode":33188,"size":2251,"sha256":"0fa4e635da2b178fa3ea13ff3829c702844cf8bd69e16bca8e1d34dbd9249d01"},{"path":"/usr/share/zoneinfo/posix/Europe/Paris","mode":33188,"size":2971,"sha256":"735b08e2737de2b47e79f596f3574b5a9e9019e56d2ead0cdc17c0b29e84a585"},{"path":"/usr/share/zoneinfo/posix/Europe/Podgorica","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/posix/Europe/Prague","mode":33188,"size":2338,"sha256":"7290e2da43a8b82b3c46ac2a05e072a8cecbf8516e5c286791dbdd68a761d205"},{"path":"/usr/share/zoneinfo/posix/Europe/Riga","mode":33188,"size":2235,"sha256":"79d10debbaa2743458d0dec1fb71d3c576cea80d245f84819da82a25d93c1401"},{"path":"/usr/share/zoneinfo/posix/Europe/Rome","mode":33188,"size":2692,"sha256":"e878580b27d866d9803e3b82eed5c0b851ef55174e2b76e13caa5e741421a138"},{"path":"/usr/share/zoneinfo/posix/Europe/Samara","mode":33188,"size":1253,"sha256":"52278e6f22bf900faeda4266078cfa7fed25cc1d5653bd345cf3090fde6e9114"},{"path":"/usr/share/zoneinfo/posix/Europe/San_Marino","mode":33188,"size":2692,"sha256":"e878580b27d866d9803e3b82eed5c0b851ef55174e2b76e13caa5e741421a138"},{"path":"/usr/share/zoneinfo/posix/Europe/Sarajevo","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/posix/Europe/Saratov","mode":33188,"size":1197,"sha256":"29ab2a05f63412656a143515fe57218a8e19b9c916dfd05de15a87afcc0d9849"},{"path":"/usr/share/zoneinfo/posix/Europe/Simferopol","mode":33188,"size":1490,"sha256":"b1ee6f714fd88fd61fef6df54f95abacb80dd3036c25e9a10708fec9b11c34cf"},{"path":"/usr/share/zoneinfo/posix/Europe/Skopje","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/posix/Europe/Sofia","mode":33188,"size":2130,"sha256":"16813fb30f2ebb782a806ce0664014ddfbf921890d32ec3d1398bd182bf9245c"},{"path":"/usr/share/zoneinfo/posix/Europe/Stockholm","mode":33188,"size":1918,"sha256":"07b242f9e3d8150663bfaf417fe7d209927fc299fac487789b70841956c35335"},{"path":"/usr/share/zoneinfo/posix/Europe/Tallinn","mode":33188,"size":2187,"sha256":"e3c4ba916c25500c709c56395c040abad62a834fafaf5163a89974b7f66b019a"},{"path":"/usr/share/zoneinfo/posix/Europe/Tirane","mode":33188,"size":2098,"sha256":"62dbc606a32a5f50ceca86c6f96d088ea689bced60a1623c986f045cde9c730a"},{"path":"/usr/share/zoneinfo/posix/Europe/Tiraspol","mode":33188,"size":2445,"sha256":"5749f01c78d0c2fd50d0dc2280c1957ce0419edbfc7c4073c67e6da78153d8c8"},{"path":"/usr/share/zoneinfo/posix/Europe/Ulyanovsk","mode":33188,"size":1281,"sha256":"9cfe87e108465369f14dbf5f8eed9285028f6500c09d06cc3e787be94c55cb91"},{"path":"/usr/share/zoneinfo/posix/Europe/Uzhgorod","mode":33188,"size":2103,"sha256":"098575b4ec6599758c85bcad8dd21d89bca213a9f890c0ead6defd14878705f3"},{"path":"/usr/share/zoneinfo/posix/Europe/Vaduz","mode":33188,"size":1918,"sha256":"bc45f8c6c8190477cdaae46f77059fab74fde92a02fc57b733f07cb9a55e98a3"},{"path":"/usr/share/zoneinfo/posix/Europe/Vatican","mode":33188,"size":2692,"sha256":"e878580b27d866d9803e3b82eed5c0b851ef55174e2b76e13caa5e741421a138"},{"path":"/usr/share/zoneinfo/posix/Europe/Vienna","mode":33188,"size":2237,"sha256":"116fab88b849fbbba59b136477814d2e0fa7d7f735166554d6e72a787cd2ccf8"},{"path":"/usr/share/zoneinfo/posix/Europe/Vilnius","mode":33188,"size":2199,"sha256":"75adc0a906b39e283f5e5020984a36f34b4f58ef1d3099efbc899ff07f035f7e"},{"path":"/usr/share/zoneinfo/posix/Europe/Volgograd","mode":33188,"size":1197,"sha256":"8d840d736f75d20c8b2815c5664252bcbde1fab71fd3d4efe17a97ac83ddaf3f"},{"path":"/usr/share/zoneinfo/posix/Europe/Warsaw","mode":33188,"size":2705,"sha256":"68e7493c1ca050e4134062a74aa4a4fc32159c042b4c9d8d40c8bfc9d273c5fa"},{"path":"/usr/share/zoneinfo/posix/Europe/Zagreb","mode":33188,"size":1957,"sha256":"e957543623baaba84999b40188e7e0948471b75a8ff4f88abb267e773feb8e5c"},{"path":"/usr/share/zoneinfo/posix/Europe/Zaporozhye","mode":33188,"size":2115,"sha256":"b6c5127b52518818e3b4211e89e5e1e9a479cca65f7763a0afb145d512c38e34"},{"path":"/usr/share/zoneinfo/posix/Europe/Zurich","mode":33188,"size":1918,"sha256":"bc45f8c6c8190477cdaae46f77059fab74fde92a02fc57b733f07cb9a55e98a3"},{"path":"/usr/share/zoneinfo/posix/GB","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/posix/GB-Eire","mode":33188,"size":3687,"sha256":"b14c486019e3cb259cf8235a0d6a4bc3ff6cfa726a165f1ea2df403c8ae31b86"},{"path":"/usr/share/zoneinfo/posix/GMT","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/GMT+0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/GMT-0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/GMT0","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/Greenwich","mode":33188,"size":127,"sha256":"d7b39879094135d13efd282937690b43f48bb53597ce3e78697f48dcceaeb3ec"},{"path":"/usr/share/zoneinfo/posix/HST","mode":33188,"size":128,"sha256":"44048bf7df61bdcf45972c13426b039f0d34d80947d60a2603183b3b6be4027f"},{"path":"/usr/share/zoneinfo/posix/Hongkong","mode":33188,"size":1231,"sha256":"680a46ee9866bd0c8435fef70694663c1e8ca2ba1e50ff2979ad62f27295707a"},{"path":"/usr/share/zoneinfo/posix/Iceland","mode":33188,"size":1188,"sha256":"9cdcea6aa1eed8276d3f6620e0c0ffae9cfcc3722c443ea6ba39147975eafaa3"},{"path":"/usr/share/zoneinfo/posix/Indian/Antananarivo","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Indian/Chagos","mode":33188,"size":225,"sha256":"f9d2fc010d11285d8430248e7a9ca16c5fe67949e768866f00b3be70aa0ea871"},{"path":"/usr/share/zoneinfo/posix/Indian/Christmas","mode":33188,"size":182,"sha256":"6d094a3d9b022ed04fc53e4a665588bd73f4eeaee9c23667b46944bac5dbbe05"},{"path":"/usr/share/zoneinfo/posix/Indian/Cocos","mode":33188,"size":191,"sha256":"3a57c446d6734a074659b854ed56cec53c40831a33c1052ce6ef4b5f0f6b0009"},{"path":"/usr/share/zoneinfo/posix/Indian/Comoro","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Indian/Kerguelen","mode":33188,"size":187,"sha256":"4dcaa3dc0c2628097499d2cfd37ab2ad70011ee31be9f7e45391ea2faee63b07"},{"path":"/usr/share/zoneinfo/posix/Indian/Mahe","mode":33188,"size":187,"sha256":"82a6e33139b0394eb1a5cb9ffb150a42df5d6fc2c56ad2642285f1d5e553fd17"},{"path":"/usr/share/zoneinfo/posix/Indian/Maldives","mode":33188,"size":220,"sha256":"b5b933b3fc554914587c6af95702a4c0d93941418737a8895372ea514aa7d475"},{"path":"/usr/share/zoneinfo/posix/Indian/Mauritius","mode":33188,"size":267,"sha256":"f257466ded0ce1a324c63e6ebc3a39354e6cde0504f1daa35136c6855278ef0f"},{"path":"/usr/share/zoneinfo/posix/Indian/Mayotte","mode":33188,"size":285,"sha256":"f143bcb83b80bc1ad0bbb8ad736c852e62bbeb6b3134412bfa77684663ed222a"},{"path":"/usr/share/zoneinfo/posix/Indian/Reunion","mode":33188,"size":187,"sha256":"c3d95eaceb2806a82b1f2c093f3d73ca0cfa0034ad0446aefbe8c4904f6a955e"},{"path":"/usr/share/zoneinfo/posix/Iran","mode":33188,"size":2624,"sha256":"29fc1861f6e088decab370c3ef2c090d0c3fbdea50b78c2d3158ddaf001b8088"},{"path":"/usr/share/zoneinfo/posix/Israel","mode":33188,"size":2321,"sha256":"1e61da0baf4d2d8f149ed84b8694cc5d4aadbee78d2014771417a67622e653fa"},{"path":"/usr/share/zoneinfo/posix/Jamaica","mode":33188,"size":507,"sha256":"addb98caf3459bb75d6e14ed76aa66e642bead2d067e7fe81814a4f02cf13503"},{"path":"/usr/share/zoneinfo/posix/Japan","mode":33188,"size":318,"sha256":"046bb09bc08554ef8a54dc05685d0eab10e04c692f6320b6091b6a6f07214c83"},{"path":"/usr/share/zoneinfo/posix/Kwajalein","mode":33188,"size":349,"sha256":"94c42dbf73fe0fde173fed33b5f15512b1ea614f40108ac0dacf6e15c23785e0"},{"path":"/usr/share/zoneinfo/posix/Libya","mode":33188,"size":655,"sha256":"8ff53f7072863fb56f1e71339392b6de7e50675efa4333b9e032b677c9c9a527"},{"path":"/usr/share/zoneinfo/posix/MET","mode":33188,"size":2102,"sha256":"1fff331a4414e98097d33bec1a9bbf2a155d991b57acd1bb4c11f8559fb4e514"},{"path":"/usr/share/zoneinfo/posix/MST","mode":33188,"size":127,"sha256":"f8fb610056087bb3ca8ecf5cdcb5305c1652b649fde512f606b9ee1b3556fb9e"},{"path":"/usr/share/zoneinfo/posix/MST7MDT","mode":33188,"size":2294,"sha256":"85452d031526621178e9b24c91af69b7ecc30df47036669378956135c4e735d0"},{"path":"/usr/share/zoneinfo/posix/Mexico/BajaNorte","mode":33188,"size":2356,"sha256":"d827b95b4fa16b8c56d9a1636341c9112657e567ae84b37a9bfca133ae31babb"},{"path":"/usr/share/zoneinfo/posix/Mexico/BajaSur","mode":33188,"size":1564,"sha256":"9340b719b250773262cec62e771d121105aed168836723dfc305e30bb04cfbb1"},{"path":"/usr/share/zoneinfo/posix/Mexico/General","mode":33188,"size":1618,"sha256":"88bc3fcb1a92ef053e0af4af9053ecbf12855fdf18f859b2a54d826dbfacb655"},{"path":"/usr/share/zoneinfo/posix/NZ","mode":33188,"size":2460,"sha256":"d7b5175387ac78e29f7b9021e411512756be283ed3d1819942ef5d45ecf338e4"},{"path":"/usr/share/zoneinfo/posix/NZ-CHAT","mode":33188,"size":2087,"sha256":"58019f2faa29dc7db7081293230a728769054dd7c0d0fa9e96e8c4299e71314d"},{"path":"/usr/share/zoneinfo/posix/Navajo","mode":33188,"size":2453,"sha256":"f4df3cc74c79d070a25a7927744d3a422a05d862a9a234a12105c5c964efb22d"},{"path":"/usr/share/zoneinfo/posix/PRC","mode":33188,"size":582,"sha256":"395b1d4ba9ef45348272c98ecab314999ecaa510f7c5830342ed6eba42cfc25d"},{"path":"/usr/share/zoneinfo/posix/PST8PDT","mode":33188,"size":2294,"sha256":"4d8e69bd43e8d71f0f58e115593814d68c1a6aa441255b17b3e9a92a9d6efc46"},{"path":"/usr/share/zoneinfo/posix/Pacific/Apia","mode":33188,"size":1134,"sha256":"fb24a31e538dd3ad0b22cf4788d80cb17d79134622510e2aa67c8712d09721cb"},{"path":"/usr/share/zoneinfo/posix/Pacific/Auckland","mode":33188,"size":2460,"sha256":"d7b5175387ac78e29f7b9021e411512756be283ed3d1819942ef5d45ecf338e4"},{"path":"/usr/share/zoneinfo/posix/Pacific/Bougainville","mode":33188,"size":296,"sha256":"c1b670d434aa6c04cbf73b647a07e5be7dcf2ff30663e10c24e0f0cfabe55b36"},{"path":"/usr/share/zoneinfo/posix/Pacific/Chatham","mode":33188,"size":2087,"sha256":"58019f2faa29dc7db7081293230a728769054dd7c0d0fa9e96e8c4299e71314d"},{"path":"/usr/share/zoneinfo/posix/Pacific/Chuuk","mode":33188,"size":296,"sha256":"cd2606a5760aa15600fa906aec3ddea4aba9b89b1e1143de20c7db52ace5bf32"},{"path":"/usr/share/zoneinfo/posix/Pacific/Easter","mode":33188,"size":2242,"sha256":"d344955a3a8dea47b50a72d2af7fde01a6a27365bef0fefb2c11429a4f5dfca1"},{"path":"/usr/share/zoneinfo/posix/Pacific/Efate","mode":33188,"size":492,"sha256":"85d792affc275df1a1bdcf9067cb59f6b1ab8bb93c450cee1293a8157a43c6ad"},{"path":"/usr/share/zoneinfo/posix/Pacific/Enderbury","mode":33188,"size":259,"sha256":"5bf2e193795d4a8ec88bcdcf338097dfa71c254332ed3235e7d3270ea7051cf7"},{"path":"/usr/share/zoneinfo/posix/Pacific/Fakaofo","mode":33188,"size":221,"sha256":"ebcdbbb97d8fa7c9a20ecf62964d207f1ed81e73a3cbea77dc8be5144950af6d"},{"path":"/usr/share/zoneinfo/posix/Pacific/Fiji","mode":33188,"size":1103,"sha256":"c7419d63f407369e5d91ce53093a6903fd8a9841cdec66aacc843d2c4df8ed10"},{"path":"/usr/share/zoneinfo/posix/Pacific/Funafuti","mode":33188,"size":183,"sha256":"812f276576cae6bbd0135d40700fde4fce64f830f75fea928cabe77c51dce579"},{"path":"/usr/share/zoneinfo/posix/Pacific/Galapagos","mode":33188,"size":268,"sha256":"3727ec66f71d8629656377c1f3a004c5cfade0f6c52b8da8b7c3ba2d36998603"},{"path":"/usr/share/zoneinfo/posix/Pacific/Gambier","mode":33188,"size":186,"sha256":"abd4f7e51731d259e30ec4b33c2bcb899e147ee102eb278a1a9b2bb8001c64db"},{"path":"/usr/share/zoneinfo/posix/Pacific/Guadalcanal","mode":33188,"size":188,"sha256":"a69b3ab3a6e6541933831609ab8bbc3ed5bf0ff678e519226b8df966b4973f20"},{"path":"/usr/share/zoneinfo/posix/Pacific/Guam","mode":33188,"size":525,"sha256":"c97a94f15eb7ed24c114ed3b6103987aedd65435aabb85217845df4695fa9069"},{"path":"/usr/share/zoneinfo/posix/Pacific/Honolulu","mode":33188,"size":338,"sha256":"528f01a0a7c21d9cc853eb79b32ecabe8a343028d116b67e6d05cd616d83d5ee"},{"path":"/usr/share/zoneinfo/posix/Pacific/Johnston","mode":33188,"size":338,"sha256":"528f01a0a7c21d9cc853eb79b32ecabe8a343028d116b67e6d05cd616d83d5ee"},{"path":"/usr/share/zoneinfo/posix/Pacific/Kiritimati","mode":33188,"size":263,"sha256":"b78f341b3f703c5dc508805923c91e3884d91ae8bd1e2f82d9b28b2308cd8eef"},{"path":"/usr/share/zoneinfo/posix/Pacific/Kosrae","mode":33188,"size":386,"sha256":"b5e1e429c7d31a845f3ff7f73604e13049ac51626da067b2cd2f4cceac34b2c3"},{"path":"/usr/share/zoneinfo/posix/Pacific/Kwajalein","mode":33188,"size":349,"sha256":"94c42dbf73fe0fde173fed33b5f15512b1ea614f40108ac0dacf6e15c23785e0"},{"path":"/usr/share/zoneinfo/posix/Pacific/Majuro","mode":33188,"size":339,"sha256":"5663127802eeab9ef7b7eb3c889e76ca9683001ed76a2a4549906e864fd10f32"},{"path":"/usr/share/zoneinfo/posix/Pacific/Marquesas","mode":33188,"size":195,"sha256":"5a63de681b53d7bfc728c5d491b2986ab47347a9f2fd15a6f3b6ff978d2f826d"},{"path":"/usr/share/zoneinfo/posix/Pacific/Midway","mode":33188,"size":196,"sha256":"7218a2ae386cd5e8981a940f6b56f6f9b60a65f3e3bd2ec1fe6c9d43bac4db1a"},{"path":"/usr/share/zoneinfo/posix/Pacific/Nauru","mode":33188,"size":282,"sha256":"90f5b914416c9e4189a530cd7fcf878a19e5f5569da00bc926a4d2b6c0cdf0d5"},{"path":"/usr/share/zoneinfo/posix/Pacific/Niue","mode":33188,"size":266,"sha256":"c16c73631f28c41351fff90d3108bc5751cbd40010fdf872da112a10e9739a53"},{"path":"/usr/share/zoneinfo/posix/Pacific/Norfolk","mode":33188,"size":933,"sha256":"d3ea212e8cfe37da5b6becba0cbc308a26bd5590986d4f046845bb5571aa899c"},{"path":"/usr/share/zoneinfo/posix/Pacific/Noumea","mode":33188,"size":328,"sha256":"13e18b4bb426c3739b34e37d6cdc00d488721a05865cdeca94af76246f55a4de"},{"path":"/usr/share/zoneinfo/posix/Pacific/Pago_Pago","mode":33188,"size":196,"sha256":"7218a2ae386cd5e8981a940f6b56f6f9b60a65f3e3bd2ec1fe6c9d43bac4db1a"},{"path":"/usr/share/zoneinfo/posix/Pacific/Palau","mode":33188,"size":199,"sha256":"fa004039c36449b9a8e280ff0c768e4d15d3853d9f2b87a177d365d8ad864525"},{"path":"/usr/share/zoneinfo/posix/Pacific/Pitcairn","mode":33188,"size":223,"sha256":"b0ad4cbe872b4d208d45bc6d326290cd240c1886150f0ee42638386276a8b0b0"},{"path":"/usr/share/zoneinfo/posix/Pacific/Pohnpei","mode":33188,"size":334,"sha256":"ee4a05d2735ebff35c2f093f0b2d03f70434de110a5403ed7a218e1b73bcf3ed"},{"path":"/usr/share/zoneinfo/posix/Pacific/Ponape","mode":33188,"size":334,"sha256":"ee4a05d2735ebff35c2f093f0b2d03f70434de110a5403ed7a218e1b73bcf3ed"},{"path":"/usr/share/zoneinfo/posix/Pacific/Port_Moresby","mode":33188,"size":206,"sha256":"1fb4613fb4bf246f537e265e441fe5f62713037df40338cfd80cb7d768e8ca5f"},{"path":"/usr/share/zoneinfo/posix/Pacific/Rarotonga","mode":33188,"size":602,"sha256":"9695a885289664511eb65f931860f584e7c5443d6f05b10b5197ac7834d47cde"},{"path":"/usr/share/zoneinfo/posix/Pacific/Saipan","mode":33188,"size":525,"sha256":"c97a94f15eb7ed24c114ed3b6103987aedd65435aabb85217845df4695fa9069"},{"path":"/usr/share/zoneinfo/posix/Pacific/Samoa","mode":33188,"size":196,"sha256":"7218a2ae386cd5e8981a940f6b56f6f9b60a65f3e3bd2ec1fe6c9d43bac4db1a"},{"path":"/usr/share/zoneinfo/posix/Pacific/Tahiti","mode":33188,"size":187,"sha256":"c9a22621ddb737b5d6342691dc2d94e265c81b0e743010b6713986db122fc855"},{"path":"/usr/share/zoneinfo/posix/Pacific/Tarawa","mode":33188,"size":183,"sha256":"28fea38528135a54fd642fe3d2bbb41aa8da6b7c892c3991ab2612a81144e799"},{"path":"/usr/share/zoneinfo/posix/Pacific/Tongatapu","mode":33188,"size":393,"sha256":"14d5bf3a7fea21eb6c9e63970d1dad5b9fbedc5f5b0fd3f5069ee74f7a0f4d8d"},{"path":"/usr/share/zoneinfo/posix/Pacific/Truk","mode":33188,"size":296,"sha256":"cd2606a5760aa15600fa906aec3ddea4aba9b89b1e1143de20c7db52ace5bf32"},{"path":"/usr/share/zoneinfo/posix/Pacific/Wake","mode":33188,"size":183,"sha256":"0346a78cf610bc43eae87c0a332d30ac5cf9c95001a4264731563cccf3c38331"},{"path":"/usr/share/zoneinfo/posix/Pacific/Wallis","mode":33188,"size":183,"sha256":"837699bd07ada63d632fc2303a687e5ef9e194e063bac786055885258206ee5c"},{"path":"/usr/share/zoneinfo/posix/Pacific/Yap","mode":33188,"size":296,"sha256":"cd2606a5760aa15600fa906aec3ddea4aba9b89b1e1143de20c7db52ace5bf32"},{"path":"/usr/share/zoneinfo/posix/Poland","mode":33188,"size":2705,"sha256":"68e7493c1ca050e4134062a74aa4a4fc32159c042b4c9d8d40c8bfc9d273c5fa"},{"path":"/usr/share/zoneinfo/posix/Portugal","mode":33188,"size":3469,"sha256":"4bbe65d4ff3394ffa1b4ae6fe2296e333f55bad0ae49ca6717b6076e53490ea2"},{"path":"/usr/share/zoneinfo/posix/ROC","mode":33188,"size":790,"sha256":"25cfd02bc847bdcb11e586445ba886a76315f1f9be86f7e74944a6e8e8644543"},{"path":"/usr/share/zoneinfo/posix/ROK","mode":33188,"size":659,"sha256":"3673a9439d49ea97b47c9fb28433c6d41c469ca03ad320768f1514d075647c26"},{"path":"/usr/share/zoneinfo/posix/Singapore","mode":33188,"size":424,"sha256":"e6929fde43ffc48bbac4081b31bbf7fd42643b3c26fadf322bdeadeb23cfc748"},{"path":"/usr/share/zoneinfo/posix/Turkey","mode":33188,"size":1970,"sha256":"2f24f072fa325c0a9bbecc48ea2782317c459a6cad941a37f7e305238443c45a"},{"path":"/usr/share/zoneinfo/posix/UCT","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/posix/US/Alaska","mode":33188,"size":2380,"sha256":"f5df0a6f7f9d43cbbd3e74d33a23fe686080eb55965f5d9246b6e859b3db9d18"},{"path":"/usr/share/zoneinfo/posix/US/Aleutian","mode":33188,"size":2365,"sha256":"c45c94d316413c8f666aff65ed1f837a7e2d392262de31ce59fac2e96a1edc81"},{"path":"/usr/share/zoneinfo/posix/US/Arizona","mode":33188,"size":353,"sha256":"9c013ecf82b6ed1dde235b5fc983fe9d23c8d56d610323f7c94c6ba3cd7b4564"},{"path":"/usr/share/zoneinfo/posix/US/Central","mode":33188,"size":3585,"sha256":"143f29b957173a46008187230a38125bd3a03b3dbcba0dc1d1b8661331f71693"},{"path":"/usr/share/zoneinfo/posix/US/East-Indiana","mode":33188,"size":1675,"sha256":"55c2f3feb241f88435e9876e76e2c69ddfd0dfd36a273b551ff480e2cfad99fe"},{"path":"/usr/share/zoneinfo/posix/US/Eastern","mode":33188,"size":3545,"sha256":"5fa6dccc303352e1195c4348b189f3085014d8a56a1976c8e8a32bd4fedb69fd"},{"path":"/usr/share/zoneinfo/posix/US/Hawaii","mode":33188,"size":338,"sha256":"528f01a0a7c21d9cc853eb79b32ecabe8a343028d116b67e6d05cd616d83d5ee"},{"path":"/usr/share/zoneinfo/posix/US/Indiana-Starke","mode":33188,"size":2437,"sha256":"9e75dd6c52c5339c8e2b195ff8ac6a7212e2c5e84b2be3023cc355972c20d856"},{"path":"/usr/share/zoneinfo/posix/US/Michigan","mode":33188,"size":2244,"sha256":"e668e3859786c92f462769f87d5bc4ef31b5d6646bbd1635b91007e2a03dbc6c"},{"path":"/usr/share/zoneinfo/posix/US/Mountain","mode":33188,"size":2453,"sha256":"f4df3cc74c79d070a25a7927744d3a422a05d862a9a234a12105c5c964efb22d"},{"path":"/usr/share/zoneinfo/posix/US/Pacific","mode":33188,"size":2845,"sha256":"fea9d66ff6522e69d22073dc4e84179b7cac2e372b398dc2fafdfdb61a9eb2e1"},{"path":"/usr/share/zoneinfo/posix/US/Pacific-New","mode":33188,"size":2845,"sha256":"fea9d66ff6522e69d22073dc4e84179b7cac2e372b398dc2fafdfdb61a9eb2e1"},{"path":"/usr/share/zoneinfo/posix/US/Samoa","mode":33188,"size":196,"sha256":"7218a2ae386cd5e8981a940f6b56f6f9b60a65f3e3bd2ec1fe6c9d43bac4db1a"},{"path":"/usr/share/zoneinfo/posix/UTC","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/posix/Universal","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/posix/W-SU","mode":33188,"size":1544,"sha256":"02d55516d0f9d497998260b4f129aee59867b77a920ba2ca0c58b15ec8588e7a"},{"path":"/usr/share/zoneinfo/posix/WET","mode":33188,"size":1873,"sha256":"e5e7c4631295e7f17085e3530f99fc2984cc7e4bdb9a07db7702de8c18c2aab1"},{"path":"/usr/share/zoneinfo/posix/Zulu","mode":33188,"size":127,"sha256":"3c71b358be81e13b1c24e199a119fd001dbcdb90edc7d44c2c7ae175321a0215"},{"path":"/usr/share/zoneinfo/posixrules","mode":33188,"size":3545,"sha256":"5fa6dccc303352e1195c4348b189f3085014d8a56a1976c8e8a32bd4fedb69fd"},{"path":"/usr/share/zoneinfo/right/Africa/Abidjan","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Accra","mode":33188,"size":1382,"sha256":"fbee22da817893911690f2ee7093499893985e39c0ced1116709947f9bd206d5"},{"path":"/usr/share/zoneinfo/right/Africa/Addis_Ababa","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Africa/Algiers","mode":33188,"size":1300,"sha256":"84081708d8029add247fd5add1ed963c2811b8b7841b65540ba7bbb02a068019"},{"path":"/usr/share/zoneinfo/right/Africa/Asmara","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Africa/Asmera","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Africa/Bamako","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Bangui","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Banjul","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Bissau","mode":33188,"size":748,"sha256":"197606820a95c35d6c3d2f64e5e1d9542e198732db52d3b9ca6ff7294bb0ff9b"},{"path":"/usr/share/zoneinfo/right/Africa/Blantyre","mode":33188,"size":711,"sha256":"3e39755e95604e242f4218d248dafd51ffa09392975c3f86c26907e6aad60da9"},{"path":"/usr/share/zoneinfo/right/Africa/Brazzaville","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Bujumbura","mode":33188,"size":711,"sha256":"3e39755e95604e242f4218d248dafd51ffa09392975c3f86c26907e6aad60da9"},{"path":"/usr/share/zoneinfo/right/Africa/Cairo","mode":33188,"size":2512,"sha256":"a3c84ceb744bbb495b49ef286308143f267da03f75931b82fdcb5c5a3aebcdd8"},{"path":"/usr/share/zoneinfo/right/Africa/Casablanca","mode":33188,"size":3005,"sha256":"dfcbc616b2e3e38b3dd19cccbf3c3a3859aa40e4bc8342df4b19347a34ca1fce"},{"path":"/usr/share/zoneinfo/right/Africa/Ceuta","mode":33188,"size":2599,"sha256":"ca6b06411c93017e93ded83d917cac8399690d6fb2771bcc66ecf132ee2e3ef6"},{"path":"/usr/share/zoneinfo/right/Africa/Conakry","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Dakar","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Dar_es_Salaam","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Africa/Djibouti","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Africa/Douala","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/El_Aaiun","mode":33188,"size":2843,"sha256":"356a80604aa80dd33c013e1340a88f828cad5c942d4e6d2ffc7842f7057b758f"},{"path":"/usr/share/zoneinfo/right/Africa/Freetown","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Gaborone","mode":33188,"size":711,"sha256":"3e39755e95604e242f4218d248dafd51ffa09392975c3f86c26907e6aad60da9"},{"path":"/usr/share/zoneinfo/right/Africa/Harare","mode":33188,"size":711,"sha256":"3e39755e95604e242f4218d248dafd51ffa09392975c3f86c26907e6aad60da9"},{"path":"/usr/share/zoneinfo/right/Africa/Johannesburg","mode":33188,"size":811,"sha256":"af7338314b4255661ce9afdd064e487321d4369ce15488395bb20bb4627d1ae2"},{"path":"/usr/share/zoneinfo/right/Africa/Juba","mode":33188,"size":1223,"sha256":"2837717687d9cf2982e14bc35199ebe448380678330f15de5a6a2c49ef204b3c"},{"path":"/usr/share/zoneinfo/right/Africa/Kampala","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Africa/Khartoum","mode":33188,"size":1253,"sha256":"0cd1350c87bd18606418d615dd78790f8ee9458ade7acb1af82b67afbdfc27f1"},{"path":"/usr/share/zoneinfo/right/Africa/Kigali","mode":33188,"size":711,"sha256":"3e39755e95604e242f4218d248dafd51ffa09392975c3f86c26907e6aad60da9"},{"path":"/usr/share/zoneinfo/right/Africa/Kinshasa","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Lagos","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Libreville","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Lome","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Luanda","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Lubumbashi","mode":33188,"size":711,"sha256":"3e39755e95604e242f4218d248dafd51ffa09392975c3f86c26907e6aad60da9"},{"path":"/usr/share/zoneinfo/right/Africa/Lusaka","mode":33188,"size":711,"sha256":"3e39755e95604e242f4218d248dafd51ffa09392975c3f86c26907e6aad60da9"},{"path":"/usr/share/zoneinfo/right/Africa/Malabo","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Maputo","mode":33188,"size":711,"sha256":"3e39755e95604e242f4218d248dafd51ffa09392975c3f86c26907e6aad60da9"},{"path":"/usr/share/zoneinfo/right/Africa/Maseru","mode":33188,"size":811,"sha256":"af7338314b4255661ce9afdd064e487321d4369ce15488395bb20bb4627d1ae2"},{"path":"/usr/share/zoneinfo/right/Africa/Mbabane","mode":33188,"size":811,"sha256":"af7338314b4255661ce9afdd064e487321d4369ce15488395bb20bb4627d1ae2"},{"path":"/usr/share/zoneinfo/right/Africa/Mogadishu","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Africa/Monrovia","mode":33188,"size":773,"sha256":"eb1deb0dd9325844227c376d1532b484511c76f79f42032806553d36a9464e55"},{"path":"/usr/share/zoneinfo/right/Africa/Nairobi","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Africa/Ndjamena","mode":33188,"size":765,"sha256":"180050fab205819406f6d6b572fe6f37eb805cc3f796543185c3229108470189"},{"path":"/usr/share/zoneinfo/right/Africa/Niamey","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Nouakchott","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Ouagadougou","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Porto-Novo","mode":33188,"size":711,"sha256":"699bdf57ddb361bef922d520674b4fecd15db812c73e984727455fa7c3ada2d3"},{"path":"/usr/share/zoneinfo/right/Africa/Sao_Tome","mode":33188,"size":803,"sha256":"0de4113ee9dadb292b55aaf2d49c4726604149a44fd6c52af4f098e6d3be5560"},{"path":"/usr/share/zoneinfo/right/Africa/Timbuktu","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Africa/Tripoli","mode":33188,"size":1195,"sha256":"72bb85f8ac4ec74b2ae92214c047c82f1f39c9c0785d0f54e152b8c1d940adda"},{"path":"/usr/share/zoneinfo/right/Africa/Tunis","mode":33188,"size":1250,"sha256":"dbc64f2ddde5756e10d2ec8156bbe83f6f9ecbeb33b5bd6d771542f623d8fc39"},{"path":"/usr/share/zoneinfo/right/Africa/Windhoek","mode":33188,"size":1574,"sha256":"aae55113e05e137fa3b35bd85ee258afbcb1da33b7f05227e2bb8398163244b9"},{"path":"/usr/share/zoneinfo/right/America/Adak","mode":33188,"size":2905,"sha256":"6d3e31970fee36399f30950e3f68ce7a5038be38a64547241c2ac97daaccd994"},{"path":"/usr/share/zoneinfo/right/America/Anchorage","mode":33188,"size":2920,"sha256":"b5b62f7337785e26117bbc34ef7976018f021e63eb3e208f8c752d4f949ef2ef"},{"path":"/usr/share/zoneinfo/right/America/Anguilla","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Antigua","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Araguaina","mode":33188,"size":1445,"sha256":"82109fd707c8edb4e656ff24c036c4745b6eb99568f9f8be4a9480f69718b893"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Buenos_Aires","mode":33188,"size":1644,"sha256":"11f0d85022c24b9744ed8511f75ca67bed67a3e5d8b439fd02ec0d05d1afa710"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Catamarca","mode":33188,"size":1644,"sha256":"e8eb2f2a5ceead008a4000d50d3e8363a3181dd29a51600efd0328fe1ff75ba0"},{"path":"/usr/share/zoneinfo/right/America/Argentina/ComodRivadavia","mode":33188,"size":1644,"sha256":"e8eb2f2a5ceead008a4000d50d3e8363a3181dd29a51600efd0328fe1ff75ba0"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Cordoba","mode":33188,"size":1644,"sha256":"71317d3d37f6c9547838beb260ddc830350e32ebb702fc280a878e0cc20b5b01"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Jujuy","mode":33188,"size":1616,"sha256":"f9b3f77caa862cee71a893e64fe1e4dbb24eda9ceff5875ae5b744638810aa14"},{"path":"/usr/share/zoneinfo/right/America/Argentina/La_Rioja","mode":33188,"size":1658,"sha256":"ca44f15fcc0edf702aa78d83f590d05964fffa5955e697ad7e12c1231f974402"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Mendoza","mode":33188,"size":1644,"sha256":"f5005f3971c083b81c94b0fa05262178468f7fb74462576a412f3d42b8dde50d"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Rio_Gallegos","mode":33188,"size":1644,"sha256":"91cf62d744daee339ecffef8c6d3222602c0edcbac281a986de084084eee0a66"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Salta","mode":33188,"size":1616,"sha256":"29c28845ace42cd30c66b7368489b0739b6e576a6ec994612aa6b0f21e3e41e7"},{"path":"/usr/share/zoneinfo/right/America/Argentina/San_Juan","mode":33188,"size":1658,"sha256":"f37e4d35b9e3881d3a842b82322841fba4b1af27a4cc6a6e32a29ee516f5b7d9"},{"path":"/usr/share/zoneinfo/right/America/Argentina/San_Luis","mode":33188,"size":1674,"sha256":"792ff8486d80c28aca88a4dd4a235f7fa2d8096c78b712807867d70ed696350b"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Tucuman","mode":33188,"size":1672,"sha256":"ff5b362c9623df8cc3c5322a8bc5fc68b8cb55a0bb2e869856244559179e65f4"},{"path":"/usr/share/zoneinfo/right/America/Argentina/Ushuaia","mode":33188,"size":1644,"sha256":"ef3d614cc912b10dfd59f42f529a41d4e4f5dc0a653a5cbecf7f49eaf32518a7"},{"path":"/usr/share/zoneinfo/right/America/Aruba","mode":33188,"size":752,"sha256":"ec9709d87bbdd0aae7be4070156e5dc05c12d822da203cb1030354342bae2df0"},{"path":"/usr/share/zoneinfo/right/America/Asuncion","mode":33188,"size":2612,"sha256":"a8578deb3800b6aacd9e448736cc82f80dbb0247516df7a22663e822bf3d959c"},{"path":"/usr/share/zoneinfo/right/America/Atikokan","mode":33188,"size":885,"sha256":"2fe220cd5f52ece0e3aa468ed33c443eaad61fc9e3bfbb47b7b754e8ad1a4613"},{"path":"/usr/share/zoneinfo/right/America/Atka","mode":33188,"size":2905,"sha256":"6d3e31970fee36399f30950e3f68ce7a5038be38a64547241c2ac97daaccd994"},{"path":"/usr/share/zoneinfo/right/America/Bahia","mode":33188,"size":1585,"sha256":"57be9fcdea20da18d7324009677d390f2098a1035f052a946e4c0ab101b52aa7"},{"path":"/usr/share/zoneinfo/right/America/Bahia_Banderas","mode":33188,"size":2128,"sha256":"e44343d2e96738b96a6d83d5327dda8d041b1fb8e62b281f7fac7e56642b960b"},{"path":"/usr/share/zoneinfo/right/America/Barbados","mode":33188,"size":884,"sha256":"64d664790217c76976a3a1f386ac82fc0f2295247f64547385711656b9f8f13b"},{"path":"/usr/share/zoneinfo/right/America/Belem","mode":33188,"size":1137,"sha256":"b42a81883f67e3e7f2ab0d7599a7828babe2847de45cca683ad9c1b9e0e5f517"},{"path":"/usr/share/zoneinfo/right/America/Belize","mode":33188,"size":1518,"sha256":"8128f9212e7e47481a2893da5f65f2c0047bf1329e314591435d7bb18b81b136"},{"path":"/usr/share/zoneinfo/right/America/Blanc-Sablon","mode":33188,"size":847,"sha256":"6e9969e343200d865e82628b88310774524c38ae9c5ede30b7e5163acb70e6a1"},{"path":"/usr/share/zoneinfo/right/America/Boa_Vista","mode":33188,"size":1193,"sha256":"571117b369cd426ece6f39b03b5105236c6b45bb48a14633c510b8217f9d1425"},{"path":"/usr/share/zoneinfo/right/America/Bogota","mode":33188,"size":806,"sha256":"2e6720337c693fb0d3d5b9da958aed2736a828d3db08d060262c04e98dd4d09d"},{"path":"/usr/share/zoneinfo/right/America/Boise","mode":33188,"size":2943,"sha256":"7189c739198e19615b75a8a336aabd3cb223a765487382eb16c783cbb91c8c95"},{"path":"/usr/share/zoneinfo/right/America/Buenos_Aires","mode":33188,"size":1644,"sha256":"11f0d85022c24b9744ed8511f75ca67bed67a3e5d8b439fd02ec0d05d1afa710"},{"path":"/usr/share/zoneinfo/right/America/Cambridge_Bay","mode":33188,"size":2638,"sha256":"dfa58c30cd1217d5f8e9dcb757d64bfb901c28a5f9475a38ac7de9e03c2d80c0"},{"path":"/usr/share/zoneinfo/right/America/Campo_Grande","mode":33188,"size":2005,"sha256":"a8706aa08dfa1b1d590cbea13a10219797f5462aaba556a2173265c54c3ee514"},{"path":"/usr/share/zoneinfo/right/America/Cancun","mode":33188,"size":1356,"sha256":"c8ce65577ce494166ad8f57f14a55ae961e27dd7aa356d8802fb5c9f2d510fb6"},{"path":"/usr/share/zoneinfo/right/America/Caracas","mode":33188,"size":824,"sha256":"a96e2b167e1bada8a827a7102f82ab54b80f2e34748c157c39d50d4605a1b3f6"},{"path":"/usr/share/zoneinfo/right/America/Catamarca","mode":33188,"size":1644,"sha256":"e8eb2f2a5ceead008a4000d50d3e8363a3181dd29a51600efd0328fe1ff75ba0"},{"path":"/usr/share/zoneinfo/right/America/Cayenne","mode":33188,"size":759,"sha256":"0eafc920b259f82d386d82c7ba4dae9301cec9a9dea17abcfd27f40dd2b06d18"},{"path":"/usr/share/zoneinfo/right/America/Cayman","mode":33188,"size":743,"sha256":"6962181adfca6314029efa4c3a2dae17c775d6031cff3bd6c63d49ed30c31cb1"},{"path":"/usr/share/zoneinfo/right/America/Chicago","mode":33188,"size":4125,"sha256":"94f71253caa6bde6db52f2f5ad3b816df0c2da9af7cc7d4a4abf1b91e391821f"},{"path":"/usr/share/zoneinfo/right/America/Chihuahua","mode":33188,"size":2062,"sha256":"1f0007a74669d2ede5ccea2c49ff17ced52ae2e28756ebbf5eb08aa08b3e9d45"},{"path":"/usr/share/zoneinfo/right/America/Coral_Harbour","mode":33188,"size":885,"sha256":"2fe220cd5f52ece0e3aa468ed33c443eaad61fc9e3bfbb47b7b754e8ad1a4613"},{"path":"/usr/share/zoneinfo/right/America/Cordoba","mode":33188,"size":1644,"sha256":"71317d3d37f6c9547838beb260ddc830350e32ebb702fc280a878e0cc20b5b01"},{"path":"/usr/share/zoneinfo/right/America/Costa_Rica","mode":33188,"size":881,"sha256":"a697b205589062aab7599c2e812f164df50b32f2d9c8f2ea7b42f1e53b4e3e94"},{"path":"/usr/share/zoneinfo/right/America/Creston","mode":33188,"size":773,"sha256":"071acbeb9c771d5bd244b0d6bd73b7e7893aa40deb19c1074908a0094de4463f"},{"path":"/usr/share/zoneinfo/right/America/Cuiaba","mode":33188,"size":1977,"sha256":"8df0f198ed0c5152081615876698fccee1adf1a84368ea30b3e7a00671e231e2"},{"path":"/usr/share/zoneinfo/right/America/Curacao","mode":33188,"size":752,"sha256":"ec9709d87bbdd0aae7be4070156e5dc05c12d822da203cb1030354342bae2df0"},{"path":"/usr/share/zoneinfo/right/America/Danmarkshavn","mode":33188,"size":1252,"sha256":"99b1ff4ad370c93145279b56504ccd2d0bb39f92c002aaa490bd5969285cdd1f"},{"path":"/usr/share/zoneinfo/right/America/Dawson","mode":33188,"size":2149,"sha256":"973edbe5bc39b28902053c11641794cd6f455380235bfb9a738a02ff6fd93df3"},{"path":"/usr/share/zoneinfo/right/America/Dawson_Creek","mode":33188,"size":1599,"sha256":"4f2bb35e6c4c8804409dc81ad024881457705dca4ae468184f73c04bff51ead1"},{"path":"/usr/share/zoneinfo/right/America/Denver","mode":33188,"size":2993,"sha256":"7448c66048e5489a28ecad3adc495351163e62cedff714bec6d15506a9e1f548"},{"path":"/usr/share/zoneinfo/right/America/Detroit","mode":33188,"size":2784,"sha256":"5549176b1eddafbfea4f7156db3872560d9c7085e200706ca281103c7918d1dd"},{"path":"/usr/share/zoneinfo/right/America/Dominica","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Edmonton","mode":33188,"size":2886,"sha256":"022478c15aee3ef60c10f350122529278adf3954d02e30f78df5ca8d6eb937ee"},{"path":"/usr/share/zoneinfo/right/America/Eirunepe","mode":33188,"size":1225,"sha256":"c4f55d375fc0af9be895823939d16d5b414619368817025e4ca1cd33b72b251f"},{"path":"/usr/share/zoneinfo/right/America/El_Salvador","mode":33188,"size":790,"sha256":"04993007b8086580ac35e8fa524bbdcd45f045c965608fca3da26deaa1ede337"},{"path":"/usr/share/zoneinfo/right/America/Ensenada","mode":33188,"size":2896,"sha256":"a1a5199868d6aa4c24fef5e908e99e4c6e116d16afc554d25ec431990d8f02da"},{"path":"/usr/share/zoneinfo/right/America/Fort_Nelson","mode":33188,"size":2789,"sha256":"c20108fb21d7e76aef2c0bd669f1dfd6043b5269020bde6cff669f088d13abec"},{"path":"/usr/share/zoneinfo/right/America/Fort_Wayne","mode":33188,"size":2215,"sha256":"7dfb7b2796f9b9d9a69d402b2e8269a2f834e1d01e2da34af490b2b24c21ace5"},{"path":"/usr/share/zoneinfo/right/America/Fortaleza","mode":33188,"size":1277,"sha256":"0c7c0174e80d20bb3233959a3c804006cbeff3d3ac86ab6b1e21988da7efdc9c"},{"path":"/usr/share/zoneinfo/right/America/Glace_Bay","mode":33188,"size":2746,"sha256":"799c72cab5fafdcf48dfe766d52c24e7fd7f4a61e0d554c97888023766219287"},{"path":"/usr/share/zoneinfo/right/America/Godthab","mode":33188,"size":2427,"sha256":"9624c131f68def896035d8ad7e011456dfc60c90a2956e32545fc391e4ec9a44"},{"path":"/usr/share/zoneinfo/right/America/Goose_Bay","mode":33188,"size":3759,"sha256":"462bef059c879d10cbcce574a128bc2d847dfc342dd77f43e6494f3aba6cf94c"},{"path":"/usr/share/zoneinfo/right/America/Grand_Turk","mode":33188,"size":2421,"sha256":"50148cea43182f25effdaba081e72c55239b58f5985a2af2e1ace6d591ef2388"},{"path":"/usr/share/zoneinfo/right/America/Grenada","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Guadeloupe","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Guatemala","mode":33188,"size":846,"sha256":"b8d8d7b3edd1a237b4d4aee860162700cf11e25aa9102ba61bed6640ced94463"},{"path":"/usr/share/zoneinfo/right/America/Guayaquil","mode":33188,"size":806,"sha256":"261c214acf962a01f616006a670d717ed104b80afb006f3c78e7e1054c9637fa"},{"path":"/usr/share/zoneinfo/right/America/Guyana","mode":33188,"size":801,"sha256":"8664ad5ccf6551c731f7235c7dc307cf5ef4106dc109e99da1cfc3b193b8d536"},{"path":"/usr/share/zoneinfo/right/America/Halifax","mode":33188,"size":3978,"sha256":"86c84ef0a21a387fdd0058046268c5eca94c10cb73231638724d344cc478bd10"},{"path":"/usr/share/zoneinfo/right/America/Havana","mode":33188,"size":2977,"sha256":"0d4bfd6b414442661f79556ac625c9f30e051af6694be67e3ad312e9e9589c50"},{"path":"/usr/share/zoneinfo/right/America/Hermosillo","mode":33188,"size":994,"sha256":"778350bbb96f05ab2e74834f35be215801da358dd7c261f1ba3bfe6f1c9b07e9"},{"path":"/usr/share/zoneinfo/right/America/Indiana/Indianapolis","mode":33188,"size":2215,"sha256":"7dfb7b2796f9b9d9a69d402b2e8269a2f834e1d01e2da34af490b2b24c21ace5"},{"path":"/usr/share/zoneinfo/right/America/Indiana/Knox","mode":33188,"size":2977,"sha256":"ac4c928ad03acaf42f346aa81bf9d269a513adb14a955ff55a5177927832c6a8"},{"path":"/usr/share/zoneinfo/right/America/Indiana/Marengo","mode":33188,"size":2271,"sha256":"b3e8fe887a5ce407f7208f16d0b296a4594b3f93de33b70d5a260139f66cfab2"},{"path":"/usr/share/zoneinfo/right/America/Indiana/Petersburg","mode":33188,"size":2453,"sha256":"285f27ebb54838060d3a33238dae6ee695af5c258d40780fc89c797a239360ba"},{"path":"/usr/share/zoneinfo/right/America/Indiana/Tell_City","mode":33188,"size":2233,"sha256":"2e364ec1dc4a5ebca7a3bbe89b3f498f9d2f1362739d26a08d887571f3a65d19"},{"path":"/usr/share/zoneinfo/right/America/Indiana/Vevay","mode":33188,"size":1963,"sha256":"74d2b6f797d63017075f1425e695e5f61a6e1b3ef08f812bc330e22fae18333a"},{"path":"/usr/share/zoneinfo/right/America/Indiana/Vincennes","mode":33188,"size":2243,"sha256":"970baaf1ed777c07d74546d61282e9df9a0488ad90084210a770c82ae78b8357"},{"path":"/usr/share/zoneinfo/right/America/Indiana/Winamac","mode":33188,"size":2327,"sha256":"cade9b122bd306fd5bb1fd4ff0471861c8eaed414a166ba570554a349a7a20b6"},{"path":"/usr/share/zoneinfo/right/America/Indianapolis","mode":33188,"size":2215,"sha256":"7dfb7b2796f9b9d9a69d402b2e8269a2f834e1d01e2da34af490b2b24c21ace5"},{"path":"/usr/share/zoneinfo/right/America/Inuvik","mode":33188,"size":2468,"sha256":"c51f2f3cef4844e5c800ed3592d85bc69e5f05dc4a53e94c76b2433be16b1a5f"},{"path":"/usr/share/zoneinfo/right/America/Iqaluit","mode":33188,"size":2586,"sha256":"7179d696e8f2aac641bbe8a0b0635128246fd4669e258befaac2e91170f75d1e"},{"path":"/usr/share/zoneinfo/right/America/Jamaica","mode":33188,"size":1047,"sha256":"47ddec901639efbe7268363dcc0d8b92a855372b0cae12720d68cce9a8974fdb"},{"path":"/usr/share/zoneinfo/right/America/Jujuy","mode":33188,"size":1616,"sha256":"f9b3f77caa862cee71a893e64fe1e4dbb24eda9ceff5875ae5b744638810aa14"},{"path":"/usr/share/zoneinfo/right/America/Juneau","mode":33188,"size":2902,"sha256":"2be628832b78514026f7932644e221fd4490d502f686f069d7ebf8ba0b220c40"},{"path":"/usr/share/zoneinfo/right/America/Kentucky/Louisville","mode":33188,"size":3321,"sha256":"afb7d1fa10278e2b8275017c592ba7679b4800a5fd1c875f5ecc8aa5ab21befe"},{"path":"/usr/share/zoneinfo/right/America/Kentucky/Monticello","mode":33188,"size":2901,"sha256":"ff56ff4d9ee52923c57354d5d836e87cc8acb748bbf0648c2406bcbafaa4227c"},{"path":"/usr/share/zoneinfo/right/America/Knox_IN","mode":33188,"size":2977,"sha256":"ac4c928ad03acaf42f346aa81bf9d269a513adb14a955ff55a5177927832c6a8"},{"path":"/usr/share/zoneinfo/right/America/Kralendijk","mode":33188,"size":752,"sha256":"ec9709d87bbdd0aae7be4070156e5dc05c12d822da203cb1030354342bae2df0"},{"path":"/usr/share/zoneinfo/right/America/La_Paz","mode":33188,"size":792,"sha256":"c95fb5fbc80f32110f36c756e648d901e362e4d96bc48e5b8d5eaf8c232654f7"},{"path":"/usr/share/zoneinfo/right/America/Lima","mode":33188,"size":966,"sha256":"f1ddf01592db3ede97b94d43fd210e2a841365b84017601248f51b21c20314eb"},{"path":"/usr/share/zoneinfo/right/America/Los_Angeles","mode":33188,"size":3385,"sha256":"5f2a6fb2744e29e2a6ac88e89843ce0c74f8934b37d1b35d67e115d5363c9e57"},{"path":"/usr/share/zoneinfo/right/America/Louisville","mode":33188,"size":3321,"sha256":"afb7d1fa10278e2b8275017c592ba7679b4800a5fd1c875f5ecc8aa5ab21befe"},{"path":"/usr/share/zoneinfo/right/America/Lower_Princes","mode":33188,"size":752,"sha256":"ec9709d87bbdd0aae7be4070156e5dc05c12d822da203cb1030354342bae2df0"},{"path":"/usr/share/zoneinfo/right/America/Maceio","mode":33188,"size":1305,"sha256":"564da2e13a0ac0d0bf7901bef8f811e53c3d78b51dbd5dc200630ba34151e6c8"},{"path":"/usr/share/zoneinfo/right/America/Managua","mode":33188,"size":1003,"sha256":"1a2e937499925a46e4d2b93113e7b035fdc270174a8fb4b65fd61f163b430ca3"},{"path":"/usr/share/zoneinfo/right/America/Manaus","mode":33188,"size":1165,"sha256":"c921cc8c1a0a1ed91805b81c0f22d5ee3a78fe3422f6366160c37b03302fd250"},{"path":"/usr/share/zoneinfo/right/America/Marigot","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Martinique","mode":33188,"size":797,"sha256":"18a0f75cca7c62ff1b7c8e0463856c1fa811e796806ef23cfd53d40a860861fa"},{"path":"/usr/share/zoneinfo/right/America/Matamoros","mode":33188,"size":1956,"sha256":"298a0a44d6576a9c127e048262a3f7f1b613653e0520a75bf912a65ccef50771"},{"path":"/usr/share/zoneinfo/right/America/Mazatlan","mode":33188,"size":2104,"sha256":"972ebc94965c29a285412a68e853fc7729bd741b5be52edeb9f3b9a1a707ac43"},{"path":"/usr/share/zoneinfo/right/America/Mendoza","mode":33188,"size":1644,"sha256":"f5005f3971c083b81c94b0fa05262178468f7fb74462576a412f3d42b8dde50d"},{"path":"/usr/share/zoneinfo/right/America/Menominee","mode":33188,"size":2823,"sha256":"a9f238c519f7699a3bdd001ffb5588fc5c80329a14c95309aa424c0026440108"},{"path":"/usr/share/zoneinfo/right/America/Merida","mode":33188,"size":1996,"sha256":"a6352eb8ee46c326f0231e5e22ae330d465964514c21390e28aa5ddee377fb5c"},{"path":"/usr/share/zoneinfo/right/America/Metlakatla","mode":33188,"size":1972,"sha256":"fc8c8661c4ebe17757c7fcc12b570674a0a84af90cdb36edf7e19d0293c36dfd"},{"path":"/usr/share/zoneinfo/right/America/Mexico_City","mode":33188,"size":2158,"sha256":"2b2e4e7d462f693d46142205a03882b383f3cfbc6eaa0a4c514fe71fd5112f12"},{"path":"/usr/share/zoneinfo/right/America/Miquelon","mode":33188,"size":2231,"sha256":"fa668103b3e90dc7ebbb2666fe3e76b29b15627b2eb6a82317a2f9b474ce98c2"},{"path":"/usr/share/zoneinfo/right/America/Moncton","mode":33188,"size":3703,"sha256":"d587577011570e8271781f98b52f5ccb8650a7a1dc2c50789f4cb5d5d7e9c13a"},{"path":"/usr/share/zoneinfo/right/America/Monterrey","mode":33188,"size":1956,"sha256":"a0334e1c8f6ebfdb959a536fea620a72031db45036d563864cdaba4e34b0c2c7"},{"path":"/usr/share/zoneinfo/right/America/Montevideo","mode":33188,"size":2099,"sha256":"5717f3694cbcfdddb8b0ce33c5b50193f3cc1af97474230f0fe4f230d4769b01"},{"path":"/usr/share/zoneinfo/right/America/Montreal","mode":33188,"size":4043,"sha256":"bd1fdaf567be65339c2fe8cadf9e690d0929548cd731edcb41ae7f322885a590"},{"path":"/usr/share/zoneinfo/right/America/Montserrat","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Nassau","mode":33188,"size":2824,"sha256":"b3526d4c47155f9f9049070f75b3981b9f17b153e9482afe6e3f83e0f84adad6"},{"path":"/usr/share/zoneinfo/right/America/New_York","mode":33188,"size":4085,"sha256":"9699b3dbf1b5a2fe33cc0eeb1bae542d83608786c0b1872b07b24adda81556a1"},{"path":"/usr/share/zoneinfo/right/America/Nipigon","mode":33188,"size":2671,"sha256":"bedddedf42d1ecd3db1eeb61988fa1216f75b06c45a768822a16b4bf3e78542f"},{"path":"/usr/share/zoneinfo/right/America/Nome","mode":33188,"size":2916,"sha256":"2f167608a9d4171d89ee0a4d68c3ee845ebbd073e3759dc663a95dc8c865e4c1"},{"path":"/usr/share/zoneinfo/right/America/Noronha","mode":33188,"size":1277,"sha256":"cc5b5c148b76dc58c925f589124f7f1ac05a52e9bc8f8cb0bf8bbef2b5779c78"},{"path":"/usr/share/zoneinfo/right/America/North_Dakota/Beulah","mode":33188,"size":2929,"sha256":"5a05c79be4ba9c4ed5a70aedbb8e83c2864c9ee5d974824130552d11097f654d"},{"path":"/usr/share/zoneinfo/right/America/North_Dakota/Center","mode":33188,"size":2929,"sha256":"c4daf0f8f179948ca4f3edfef1c4bf6ea9926d157cbb83334d990c4f3ae76fb3"},{"path":"/usr/share/zoneinfo/right/America/North_Dakota/New_Salem","mode":33188,"size":2929,"sha256":"f728e13f15039666ade97ebb9e0e7d54b575495e14aa88ccf2761d29e5a390f4"},{"path":"/usr/share/zoneinfo/right/America/Nuuk","mode":33188,"size":2427,"sha256":"9624c131f68def896035d8ad7e011456dfc60c90a2956e32545fc391e4ec9a44"},{"path":"/usr/share/zoneinfo/right/America/Ojinaga","mode":33188,"size":2062,"sha256":"e9cb05ec786e833e837b19a3d7bfe611e6d3ff3da1fc576fa5ea4f44c43f937f"},{"path":"/usr/share/zoneinfo/right/America/Panama","mode":33188,"size":743,"sha256":"6962181adfca6314029efa4c3a2dae17c775d6031cff3bd6c63d49ed30c31cb1"},{"path":"/usr/share/zoneinfo/right/America/Pangnirtung","mode":33188,"size":2648,"sha256":"c71e8ae865312e517ebc4076ecb9665c2cfdc7155549d18462e01275961925b8"},{"path":"/usr/share/zoneinfo/right/America/Paramaribo","mode":33188,"size":831,"sha256":"cf4b95b3e776a776aaffb4c77cb62dcad960796b0876d0663c01ae3da38c078c"},{"path":"/usr/share/zoneinfo/right/America/Phoenix","mode":33188,"size":893,"sha256":"8a89f0e65cd0a0b2edbbf65a7a81441aa91073b133edac17c25c6c9f809b8995"},{"path":"/usr/share/zoneinfo/right/America/Port-au-Prince","mode":33188,"size":1995,"sha256":"aab1855d3200ed78c12406a44d8558a9a875dc57f94090b2c205811a92b5e066"},{"path":"/usr/share/zoneinfo/right/America/Port_of_Spain","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Porto_Acre","mode":33188,"size":1197,"sha256":"90e09a708c3c756baf60fafda6f8a5f3316b8f0f13ae2433bcad860c74bd544c"},{"path":"/usr/share/zoneinfo/right/America/Porto_Velho","mode":33188,"size":1137,"sha256":"651eea662c20cfff098d84663237abba967604a6d0258d138d75e06ab483390b"},{"path":"/usr/share/zoneinfo/right/America/Puerto_Rico","mode":33188,"size":795,"sha256":"a9e478dd8515a4c8086ff535afe44db1cf53b9400ec62aed7b6d122ecfb778f3"},{"path":"/usr/share/zoneinfo/right/America/Punta_Arenas","mode":33188,"size":2446,"sha256":"300872a317db68e683587783e80e3a464c63971da1774b539fea0ee26763c451"},{"path":"/usr/share/zoneinfo/right/America/Rainy_River","mode":33188,"size":2671,"sha256":"1680a0ae7e1d154aa9672b6e2d24155987de256acd7273f23177ef258d4ffe16"},{"path":"/usr/share/zoneinfo/right/America/Rankin_Inlet","mode":33188,"size":2470,"sha256":"1bb3cc33e21e5e7663a0cabcb02f9e7f74ee0619dcd0d84d4a4a31f611698b57"},{"path":"/usr/share/zoneinfo/right/America/Recife","mode":33188,"size":1277,"sha256":"4bf3764907eedcdc1325748d005e883ead0253178f552bf8c26f91c9472c5884"},{"path":"/usr/share/zoneinfo/right/America/Regina","mode":33188,"size":1534,"sha256":"7ef7b8f3a4e1baf07289907c77a4218ac0be68c7a24e980940a05cbba77e53c9"},{"path":"/usr/share/zoneinfo/right/America/Resolute","mode":33188,"size":2470,"sha256":"2a208ed79da175c5081c8db0fb767d9b0e0270e4a73bb95f24ae0ffd22b6354f"},{"path":"/usr/share/zoneinfo/right/America/Rio_Branco","mode":33188,"size":1197,"sha256":"90e09a708c3c756baf60fafda6f8a5f3316b8f0f13ae2433bcad860c74bd544c"},{"path":"/usr/share/zoneinfo/right/America/Rosario","mode":33188,"size":1644,"sha256":"71317d3d37f6c9547838beb260ddc830350e32ebb702fc280a878e0cc20b5b01"},{"path":"/usr/share/zoneinfo/right/America/Santa_Isabel","mode":33188,"size":2896,"sha256":"a1a5199868d6aa4c24fef5e908e99e4c6e116d16afc554d25ec431990d8f02da"},{"path":"/usr/share/zoneinfo/right/America/Santarem","mode":33188,"size":1167,"sha256":"5994056b5ce743dfdcdc80dba996df44665d743abbdff8d8841b7b4ac326339f"},{"path":"/usr/share/zoneinfo/right/America/Santiago","mode":33188,"size":3073,"sha256":"986a3d87481910c37ff5045ecb26e8d7832333bb9b8bf0cefa8f2518c787fcb5"},{"path":"/usr/share/zoneinfo/right/America/Santo_Domingo","mode":33188,"size":1031,"sha256":"24bf349defe5c3ed5d8950593acbcd57dc662784ddfae68b31cddfa02746f2ba"},{"path":"/usr/share/zoneinfo/right/America/Sao_Paulo","mode":33188,"size":2005,"sha256":"30ef7b506e76ac5286ad4415d7daa8abf0af2b6c63abb540869a8dc1c61f28a0"},{"path":"/usr/share/zoneinfo/right/America/Scoresbysund","mode":33188,"size":2465,"sha256":"fa41c201d42521e8a0db51e00fa9487fad84467b15706e00221088e217ba129d"},{"path":"/usr/share/zoneinfo/right/America/Shiprock","mode":33188,"size":2993,"sha256":"7448c66048e5489a28ecad3adc495351163e62cedff714bec6d15506a9e1f548"},{"path":"/usr/share/zoneinfo/right/America/Sitka","mode":33188,"size":2890,"sha256":"81ba6e3b87b7f9c9814c4f607a3c722a0bbd8355ab1647c51847882b3a3c0628"},{"path":"/usr/share/zoneinfo/right/America/St_Barthelemy","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/St_Johns","mode":33188,"size":4204,"sha256":"10784794564849767481803ad10924bd7092c041b5e5859dc7cdf883abe13a7e"},{"path":"/usr/share/zoneinfo/right/America/St_Kitts","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/St_Lucia","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/St_Thomas","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/St_Vincent","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Swift_Current","mode":33188,"size":1114,"sha256":"7752d4a7cd93e6c9a16f89dfa148ce6ac6f491cf40359f9d6730e03b4aedf848"},{"path":"/usr/share/zoneinfo/right/America/Tegucigalpa","mode":33188,"size":818,"sha256":"c37dd7463adb25b95fd20bd17473e710e03c9c5d36481b4626a82aabd7469983"},{"path":"/usr/share/zoneinfo/right/America/Thule","mode":33188,"size":2068,"sha256":"67e571d61867a4ea726d7b19f5fabca2a7751219685d57eee29570ec9225f0ea"},{"path":"/usr/share/zoneinfo/right/America/Thunder_Bay","mode":33188,"size":2751,"sha256":"2c04cafec84e648e5d1154986626b32ebdb0def10d7c8843d27bbee20ad82e5e"},{"path":"/usr/share/zoneinfo/right/America/Tijuana","mode":33188,"size":2896,"sha256":"a1a5199868d6aa4c24fef5e908e99e4c6e116d16afc554d25ec431990d8f02da"},{"path":"/usr/share/zoneinfo/right/America/Toronto","mode":33188,"size":4043,"sha256":"bd1fdaf567be65339c2fe8cadf9e690d0929548cd731edcb41ae7f322885a590"},{"path":"/usr/share/zoneinfo/right/America/Tortola","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Vancouver","mode":33188,"size":3441,"sha256":"59f3b401ccdbabb740e3395b75233402d6d2e0590195df1e5d8e73e736158361"},{"path":"/usr/share/zoneinfo/right/America/Virgin","mode":33188,"size":710,"sha256":"dbe365d9a8abfd164690db1cec6c51c19f86154900595509c991401e13a16585"},{"path":"/usr/share/zoneinfo/right/America/Whitehorse","mode":33188,"size":2149,"sha256":"656e8559dd8f0f71b49cbd7e39ea69f9b229cd28cbbd26d67c067faeb71e3dcb"},{"path":"/usr/share/zoneinfo/right/America/Winnipeg","mode":33188,"size":3431,"sha256":"a91e3074914af25d44e7428f07b7e15c46a9b1c61adf146d78058bfb95128031"},{"path":"/usr/share/zoneinfo/right/America/Yakutat","mode":33188,"size":2854,"sha256":"a8d6177b9fb9653500c7a5468e35508251be2a6dce9040ad9ebfbffcd4cc3ad2"},{"path":"/usr/share/zoneinfo/right/America/Yellowknife","mode":33188,"size":2520,"sha256":"ffb6c39b1c757ff250651391b07dc8d3e3ea361f837472ef57c62eea144677ef"},{"path":"/usr/share/zoneinfo/right/Antarctica/Casey","mode":33188,"size":846,"sha256":"18906bd500b39972ffa02b9ec4b7495a37701aedad4a5b37be9cbc57724687e3"},{"path":"/usr/share/zoneinfo/right/Antarctica/Davis","mode":33188,"size":846,"sha256":"74c57bbabd9734817648bb1b717ba8cea2d000297a0c82d9d9f0ecfb5a6de509"},{"path":"/usr/share/zoneinfo/right/Antarctica/DumontDUrville","mode":33188,"size":751,"sha256":"02aadd2f58956d4ecf18d22258af85b368a0140656ef079ea81e0f9e3eae59ef"},{"path":"/usr/share/zoneinfo/right/Antarctica/Macquarie","mode":33188,"size":2078,"sha256":"5a6da6a5a6c84bb235622dcd38baf933b6252ac2524e2d4ebfc6b2283f44aeef"},{"path":"/usr/share/zoneinfo/right/Antarctica/Mawson","mode":33188,"size":760,"sha256":"c21ee7da441169a32db233d5f712b0e0e9f467224c31005a6ee94791e80dce7d"},{"path":"/usr/share/zoneinfo/right/Antarctica/McMurdo","mode":33188,"size":3000,"sha256":"c6fa7d47e6fb209806155ca05d2d0721726515ad678714f3197b9daeb9da3a96"},{"path":"/usr/share/zoneinfo/right/Antarctica/Palmer","mode":33188,"size":1967,"sha256":"3d776d3217806a1dfa38b342c7d413bf1c05d47e440625a25850f10de050175a"},{"path":"/usr/share/zoneinfo/right/Antarctica/Rothera","mode":33188,"size":721,"sha256":"6a17dce1f665a2ca8026fef6634fca93b698392000e97f89797ef44b57afa7ca"},{"path":"/usr/share/zoneinfo/right/Antarctica/South_Pole","mode":33188,"size":3000,"sha256":"c6fa7d47e6fb209806155ca05d2d0721726515ad678714f3197b9daeb9da3a96"},{"path":"/usr/share/zoneinfo/right/Antarctica/Syowa","mode":33188,"size":722,"sha256":"785f2980f27b1976e65a7e5bc7f1d944d5b7e78656a35b30ef8f144c35103a5b"},{"path":"/usr/share/zoneinfo/right/Antarctica/Troll","mode":33188,"size":1711,"sha256":"4fe25a3e29129e9204e750a191c11202dc66e122423c1d97ea03d579182e38ac"},{"path":"/usr/share/zoneinfo/right/Antarctica/Vostok","mode":33188,"size":722,"sha256":"85a1b3ff9f71acab9c1e01cb31ee3e9330b9abe48a84763b8d35c6a3b7d6086c"},{"path":"/usr/share/zoneinfo/right/Arctic/Longyearbyen","mode":33188,"size":2791,"sha256":"b9f4a8a248c4b945a12640b4be549baaa438a9c3472822028e9f4988cd4e8b63"},{"path":"/usr/share/zoneinfo/right/Asia/Aden","mode":33188,"size":722,"sha256":"f3f24b3aba19f09734826f156f5537eb97ef899b249ec673048e5d07369487c7"},{"path":"/usr/share/zoneinfo/right/Asia/Almaty","mode":33188,"size":1566,"sha256":"bb58e7c09cb5daf5f6afc61969735809085f8f7d1fb9d129f2dff6d52c2d5370"},{"path":"/usr/share/zoneinfo/right/Asia/Amman","mode":33188,"size":2417,"sha256":"0dfa946fc43a7d4ad00e75aba44720018d82f36411351b2e5a103dbfadaf0d8c"},{"path":"/usr/share/zoneinfo/right/Asia/Anadyr","mode":33188,"size":1757,"sha256":"723f952ffdde9c6027874689c1b831211ed782bcd1a78b0b3a63f9dd22b661f4"},{"path":"/usr/share/zoneinfo/right/Asia/Aqtau","mode":33188,"size":1552,"sha256":"aee361faa20979a35b89ac0f538cb4b67c793a36ccfcd98bae1f0f1e2dce98e1"},{"path":"/usr/share/zoneinfo/right/Asia/Aqtobe","mode":33188,"size":1582,"sha256":"58034c93dece9d7b3b8f44e6d39318814c3a5810cd460e87d888c572e8794b17"},{"path":"/usr/share/zoneinfo/right/Asia/Ashgabat","mode":33188,"size":1186,"sha256":"67ef3f1da89446f546c8f8767c16e3106e8c85df4a20d89bc1870f0ea174a20d"},{"path":"/usr/share/zoneinfo/right/Asia/Ashkhabad","mode":33188,"size":1186,"sha256":"67ef3f1da89446f546c8f8767c16e3106e8c85df4a20d89bc1870f0ea174a20d"},{"path":"/usr/share/zoneinfo/right/Asia/Atyrau","mode":33188,"size":1560,"sha256":"37546c1d6704164b04d1126a889c03876bd08241f2fa70e8ec6d6f3012857651"},{"path":"/usr/share/zoneinfo/right/Asia/Baghdad","mode":33188,"size":1539,"sha256":"71e50815aa9bfebe11c36f200503c2c62d89bf715a067175d2091185bb6b2829"},{"path":"/usr/share/zoneinfo/right/Asia/Bahrain","mode":33188,"size":760,"sha256":"2e7b84c80828a81f1f7bbaf7355133a81ad96b1273a29c223acf12d1446d4922"},{"path":"/usr/share/zoneinfo/right/Asia/Baku","mode":33188,"size":1804,"sha256":"3a06bcc490313e6868f2c50f64a724c494f39c23420e741d4e78208abdd5f69d"},{"path":"/usr/share/zoneinfo/right/Asia/Bangkok","mode":33188,"size":755,"sha256":"d91fabfc29473f96272f2e96868a44393d6ce11950b7a5ec32eae83dc142b4a4"},{"path":"/usr/share/zoneinfo/right/Asia/Barnaul","mode":33188,"size":1790,"sha256":"0436ee225d77df15229ebf4e30079643bb2cf55131d60b1d6718ddbb77826710"},{"path":"/usr/share/zoneinfo/right/Asia/Beirut","mode":33188,"size":2715,"sha256":"3e24a502c1fb5fb0dd7a8c738f28074b8e785311ba73a33fb597c2172ca288a0"},{"path":"/usr/share/zoneinfo/right/Asia/Bishkek","mode":33188,"size":1564,"sha256":"9bab70e971735626c3169c9a45153d4da93114bfd8b7295e5d56fc0173cc26fd"},{"path":"/usr/share/zoneinfo/right/Asia/Brunei","mode":33188,"size":764,"sha256":"a44c283addb335506e1b7a9c288240d2c651e1bbfbfefd9cadfa7181aaf4b1ec"},{"path":"/usr/share/zoneinfo/right/Asia/Calcutta","mode":33188,"size":852,"sha256":"637147fe7b40e10955c08b61ecc5639148589ce9bd6939cf7b98bc02cccd5036"},{"path":"/usr/share/zoneinfo/right/Asia/Chita","mode":33188,"size":1792,"sha256":"d935e891890a25a2d1ebf88768f70193d23e3d6522c67ed4e4c1435fd9de6a0e"},{"path":"/usr/share/zoneinfo/right/Asia/Choibalsan","mode":33188,"size":1526,"sha256":"5e68707f2d985de61d9a1ca14134c5f96781eff2486e40be8d5b4d34708d59e2"},{"path":"/usr/share/zoneinfo/right/Asia/Chongqing","mode":33188,"size":1122,"sha256":"add747558dc8f3175776014d9653cf734a761b95dec62f06a3922bfce9f82b6e"},{"path":"/usr/share/zoneinfo/right/Asia/Chungking","mode":33188,"size":1122,"sha256":"add747558dc8f3175776014d9653cf734a761b95dec62f06a3922bfce9f82b6e"},{"path":"/usr/share/zoneinfo/right/Asia/Colombo","mode":33188,"size":948,"sha256":"d2105ff2a10182bf68780abfa1b9a22574b1e30efe6a249b4f8e0f17058fa659"},{"path":"/usr/share/zoneinfo/right/Asia/Dacca","mode":33188,"size":905,"sha256":"8b30cb0ad86ae48068d4d6293137bb66ac4ebc73000ba2cca9428ef13c244b8a"},{"path":"/usr/share/zoneinfo/right/Asia/Damascus","mode":33188,"size":2860,"sha256":"e23e8576a6f8b5b65a356e535ba0ffc916d211a155207e486dd40b1757f3b831"},{"path":"/usr/share/zoneinfo/right/Asia/Dhaka","mode":33188,"size":905,"sha256":"8b30cb0ad86ae48068d4d6293137bb66ac4ebc73000ba2cca9428ef13c244b8a"},{"path":"/usr/share/zoneinfo/right/Asia/Dili","mode":33188,"size":788,"sha256":"1027c57d5d5094c84e80ab360790f0355acce56ec10c6df5567ad35baeba093b"},{"path":"/usr/share/zoneinfo/right/Asia/Dubai","mode":33188,"size":722,"sha256":"86cb3519886f292920f8c8ff5b551bb66ab5c7ab559ef378584a464dfcc539fc"},{"path":"/usr/share/zoneinfo/right/Asia/Dushanbe","mode":33188,"size":1156,"sha256":"518c7e9aabe61a423f703f9285036c37b0b63db85614a54fc053b72dc0f7ac9f"},{"path":"/usr/share/zoneinfo/right/Asia/Famagusta","mode":33188,"size":2582,"sha256":"40438f760718c79a99e171a199690123f0cc531fef996423c2ca840d20b6bce9"},{"path":"/usr/share/zoneinfo/right/Asia/Gaza","mode":33188,"size":2891,"sha256":"3fba0ceae7f3ec40b707a1c175d94d80971b89ee57bcbbaadf7869e7e6d1c30f"},{"path":"/usr/share/zoneinfo/right/Asia/Harbin","mode":33188,"size":1122,"sha256":"add747558dc8f3175776014d9653cf734a761b95dec62f06a3922bfce9f82b6e"},{"path":"/usr/share/zoneinfo/right/Asia/Hebron","mode":33188,"size":2919,"sha256":"a127bd976cb4e475370adf690228950629af04ae9ee163dbd8a7dd4543aa3a15"},{"path":"/usr/share/zoneinfo/right/Asia/Ho_Chi_Minh","mode":33188,"size":924,"sha256":"496bbfe0b2bbd4922f8a4a5cc56a405485c1b9df21375d75996ac5e3008f87b9"},{"path":"/usr/share/zoneinfo/right/Asia/Hong_Kong","mode":33188,"size":1771,"sha256":"f4f912297ccc9172c05ffe76746d938e832d85d3154b4638709753c0f4800c7c"},{"path":"/usr/share/zoneinfo/right/Asia/Hovd","mode":33188,"size":1456,"sha256":"c51f36d33e1b9fc550b8dd1d2182d8b441a8c77d6f64a5a89859b901a08e2759"},{"path":"/usr/share/zoneinfo/right/Asia/Irkutsk","mode":33188,"size":1811,"sha256":"ad1c94f9d9a0e542c80d2b53c4980131675936f6d6e7f04615c1e5029ff1d643"},{"path":"/usr/share/zoneinfo/right/Asia/Istanbul","mode":33188,"size":2505,"sha256":"d0fd3d19c0e209595df3017696f8dc59d900be1dd6a3a8b354f7798ba6ce1f4d"},{"path":"/usr/share/zoneinfo/right/Asia/Jakarta","mode":33188,"size":932,"sha256":"1e1d6c8a2a336137b702b0e68da98b2b2c3135a1844f9bc17d05d0eff1ef18bd"},{"path":"/usr/share/zoneinfo/right/Asia/Jayapura","mode":33188,"size":791,"sha256":"ccfa8a6a43b97d5dd2e2c33f84951460b2bffcc1202919ef38c3b097a83167db"},{"path":"/usr/share/zoneinfo/right/Asia/Jerusalem","mode":33188,"size":2861,"sha256":"f11b537da563f2c93dcda9206f3cb54ea87dbe701572cfe159854b4b8f1ef90b"},{"path":"/usr/share/zoneinfo/right/Asia/Kabul","mode":33188,"size":764,"sha256":"94835befd0e3581a0cf3c5d3fe177b2f1319868077ccd423af2fda0996cfee7b"},{"path":"/usr/share/zoneinfo/right/Asia/Kamchatka","mode":33188,"size":1733,"sha256":"bc897301c4b520c5fe1201efc6b656b77e54c55cec912beab9891463f79410f3"},{"path":"/usr/share/zoneinfo/right/Asia/Karachi","mode":33188,"size":957,"sha256":"08c8c89e2687b19464bc067b6b368bfe3106c980538c0b3314e7301e192a295a"},{"path":"/usr/share/zoneinfo/right/Asia/Kashgar","mode":33188,"size":722,"sha256":"c73db62481070869d19d18143892e5fea592a147cc3a230b120d2b0663882591"},{"path":"/usr/share/zoneinfo/right/Asia/Kathmandu","mode":33188,"size":773,"sha256":"c9482baab20e577e331c8c15889c2b881eff5de670ff0502c3c8bdc5e985c1cc"},{"path":"/usr/share/zoneinfo/right/Asia/Katmandu","mode":33188,"size":773,"sha256":"c9482baab20e577e331c8c15889c2b881eff5de670ff0502c3c8bdc5e985c1cc"},{"path":"/usr/share/zoneinfo/right/Asia/Khandyga","mode":33188,"size":1846,"sha256":"79a1086c8573e9fc21ad02d2c092f00182fc14fecf7aee7df2c66d16d33f58d8"},{"path":"/usr/share/zoneinfo/right/Asia/Kolkata","mode":33188,"size":852,"sha256":"637147fe7b40e10955c08b61ecc5639148589ce9bd6939cf7b98bc02cccd5036"},{"path":"/usr/share/zoneinfo/right/Asia/Krasnoyarsk","mode":33188,"size":1778,"sha256":"1f2e856dd5b062136b649c0b86738d31ac218406fdee6d98f26b110c0e913287"},{"path":"/usr/share/zoneinfo/right/Asia/Kuala_Lumpur","mode":33188,"size":959,"sha256":"b49df9efbe233fded04d2a35bafd4a2291fd7c91639a7761e5882d5824c8868e"},{"path":"/usr/share/zoneinfo/right/Asia/Kuching","mode":33188,"size":1056,"sha256":"217b0ff65b13b272a0661ebbbfb6cd392f13fdd0612dcfbe1077c40d2fcf58cb"},{"path":"/usr/share/zoneinfo/right/Asia/Kuwait","mode":33188,"size":722,"sha256":"f3f24b3aba19f09734826f156f5537eb97ef899b249ec673048e5d07369487c7"},{"path":"/usr/share/zoneinfo/right/Asia/Macao","mode":33188,"size":1795,"sha256":"470b21048ae38a2d611012c63f0359ae5bf685afa696d9cdb2a17438635b5283"},{"path":"/usr/share/zoneinfo/right/Asia/Macau","mode":33188,"size":1795,"sha256":"470b21048ae38a2d611012c63f0359ae5bf685afa696d9cdb2a17438635b5283"},{"path":"/usr/share/zoneinfo/right/Asia/Magadan","mode":33188,"size":1793,"sha256":"4da1ed819b7a50248044e582cd1221e878cc104f429900dccda3d097b9ad6ad4"},{"path":"/usr/share/zoneinfo/right/Asia/Makassar","mode":33188,"size":828,"sha256":"6bb9b9d31d2f3c57b17a9ec143294ffaa86669e793adf98c5acd1a980d6d4125"},{"path":"/usr/share/zoneinfo/right/Asia/Manila","mode":33188,"size":899,"sha256":"676bd6835773f0de41e52285dbb78830de3f80d98097f06dfedafff34b6c40aa"},{"path":"/usr/share/zoneinfo/right/Asia/Muscat","mode":33188,"size":722,"sha256":"86cb3519886f292920f8c8ff5b551bb66ab5c7ab559ef378584a464dfcc539fc"},{"path":"/usr/share/zoneinfo/right/Asia/Nicosia","mode":33188,"size":2556,"sha256":"b801d86c6b957dd1affe34a2d19a0c580be861d8ccd283d9f48e2dc991fe3696"},{"path":"/usr/share/zoneinfo/right/Asia/Novokuznetsk","mode":33188,"size":1732,"sha256":"121a05f4f5f4f88638e53bd570db3a9f3c247d29020491e871c55df3febc59e0"},{"path":"/usr/share/zoneinfo/right/Asia/Novosibirsk","mode":33188,"size":1790,"sha256":"0efbee40872e742db4124508044fdabf5cbc616ed26dcfe5fb80e1a97b0f365d"},{"path":"/usr/share/zoneinfo/right/Asia/Omsk","mode":33188,"size":1778,"sha256":"64615d9337250ed8ef6a150d1b331947f4b75e3132d9319ad5243d07d41089d0"},{"path":"/usr/share/zoneinfo/right/Asia/Oral","mode":33188,"size":1574,"sha256":"f6881fc8bcbf070d6f8d5dac52f19fdf9162ce8d5144766b92620705fe82d59a"},{"path":"/usr/share/zoneinfo/right/Asia/Phnom_Penh","mode":33188,"size":755,"sha256":"d91fabfc29473f96272f2e96868a44393d6ce11950b7a5ec32eae83dc142b4a4"},{"path":"/usr/share/zoneinfo/right/Asia/Pontianak","mode":33188,"size":935,"sha256":"5387a863122580120cb3ee351bcada3b3dfbf163424291b97bac4e2cabd9845f"},{"path":"/usr/share/zoneinfo/right/Asia/Pyongyang","mode":33188,"size":807,"sha256":"c74b65040a8f280458f9f6054fdecb2b980510376426b6367a457ec0da0ac08d"},{"path":"/usr/share/zoneinfo/right/Asia/Qatar","mode":33188,"size":760,"sha256":"2e7b84c80828a81f1f7bbaf7355133a81ad96b1273a29c223acf12d1446d4922"},{"path":"/usr/share/zoneinfo/right/Asia/Qostanay","mode":33188,"size":1582,"sha256":"c2fcd0ffd483e7c87cc92e63f5409cfa72e322ef99bfb89ff040ef53ce6f0170"},{"path":"/usr/share/zoneinfo/right/Asia/Qyzylorda","mode":33188,"size":1604,"sha256":"4bb11726867dc275fd2622da77c437aedd48df9d2ffac75af12f3540408f13e5"},{"path":"/usr/share/zoneinfo/right/Asia/Rangoon","mode":33188,"size":832,"sha256":"a38bd662f07725a121cbb302b992167054cd598c5127c30514f1fe1fe0c8d70d"},{"path":"/usr/share/zoneinfo/right/Asia/Riyadh","mode":33188,"size":722,"sha256":"f3f24b3aba19f09734826f156f5537eb97ef899b249ec673048e5d07369487c7"},{"path":"/usr/share/zoneinfo/right/Asia/Saigon","mode":33188,"size":924,"sha256":"496bbfe0b2bbd4922f8a4a5cc56a405485c1b9df21375d75996ac5e3008f87b9"},{"path":"/usr/share/zoneinfo/right/Asia/Sakhalin","mode":33188,"size":1769,"sha256":"a0651f797d67edd06928f67bbebb2872fff7b5c8d42e3dbb5554dd66389d610a"},{"path":"/usr/share/zoneinfo/right/Asia/Samarkand","mode":33188,"size":1154,"sha256":"8e8266acc24f1234e3df68f68e1d4c80e3c9c3ed313da024517f3051f9dcaa09"},{"path":"/usr/share/zoneinfo/right/Asia/Seoul","mode":33188,"size":1199,"sha256":"6c95b3eee50a28160e185e76e2bab6ec9f28f50e2d9a3166b20c4acfcf4aef1c"},{"path":"/usr/share/zoneinfo/right/Asia/Shanghai","mode":33188,"size":1122,"sha256":"add747558dc8f3175776014d9653cf734a761b95dec62f06a3922bfce9f82b6e"},{"path":"/usr/share/zoneinfo/right/Asia/Singapore","mode":33188,"size":959,"sha256":"91e407e2266fb1de8a5a90631744cd5b213f2521db783258f2f9f41697517dda"},{"path":"/usr/share/zoneinfo/right/Asia/Srednekolymsk","mode":33188,"size":1779,"sha256":"bc4ac100afd7e317e5939451b677a707dc1a51e646f380bf56411916084a2f87"},{"path":"/usr/share/zoneinfo/right/Asia/Taipei","mode":33188,"size":1330,"sha256":"d5ff02c7a5dc9adb7a5b8de1e492f8ace92d832e8f2f6879265520c47f850078"},{"path":"/usr/share/zoneinfo/right/Asia/Tashkent","mode":33188,"size":1170,"sha256":"7ef3e54ff15a28d5054bc7a3c2946ad05849d57a4cf0096f1982a59be031a207"},{"path":"/usr/share/zoneinfo/right/Asia/Tbilisi","mode":33188,"size":1615,"sha256":"265b4e7c276a60c19c2039171c2b633b3b0c0d51c7d3d527a11c9eaa0b2b9ec7"},{"path":"/usr/share/zoneinfo/right/Asia/Tehran","mode":33188,"size":3164,"sha256":"c5940a0ac0a0fb9c21f747d475f7b30031ec8c2700fbfa1bfd1496724c953715"},{"path":"/usr/share/zoneinfo/right/Asia/Tel_Aviv","mode":33188,"size":2861,"sha256":"f11b537da563f2c93dcda9206f3cb54ea87dbe701572cfe159854b4b8f1ef90b"},{"path":"/usr/share/zoneinfo/right/Asia/Thimbu","mode":33188,"size":764,"sha256":"38acdb7ead0a0945764ce021f31292acba206c6361ec57eb56129a52d5efe650"},{"path":"/usr/share/zoneinfo/right/Asia/Thimphu","mode":33188,"size":764,"sha256":"38acdb7ead0a0945764ce021f31292acba206c6361ec57eb56129a52d5efe650"},{"path":"/usr/share/zoneinfo/right/Asia/Tokyo","mode":33188,"size":858,"sha256":"1ecabb9dd5bcee432606c243ffd05fc8f1f50ec8f531dfaf3dd7a872160814f0"},{"path":"/usr/share/zoneinfo/right/Asia/Tomsk","mode":33188,"size":1790,"sha256":"ec986c86975c8d0f95485b5d809100261dd19de6376d960672dd08671e8eb63e"},{"path":"/usr/share/zoneinfo/right/Asia/Ujung_Pandang","mode":33188,"size":828,"sha256":"6bb9b9d31d2f3c57b17a9ec143294ffaa86669e793adf98c5acd1a980d6d4125"},{"path":"/usr/share/zoneinfo/right/Asia/Ulaanbaatar","mode":33188,"size":1456,"sha256":"77dac4fa1d2f3d584ac760f2ae886c14d1c20c321865f5c28602038aeb43b0f4"},{"path":"/usr/share/zoneinfo/right/Asia/Ulan_Bator","mode":33188,"size":1456,"sha256":"77dac4fa1d2f3d584ac760f2ae886c14d1c20c321865f5c28602038aeb43b0f4"},{"path":"/usr/share/zoneinfo/right/Asia/Urumqi","mode":33188,"size":722,"sha256":"c73db62481070869d19d18143892e5fea592a147cc3a230b120d2b0663882591"},{"path":"/usr/share/zoneinfo/right/Asia/Ust-Nera","mode":33188,"size":1825,"sha256":"c7a0a40880eca39a3d0eeb389cb84bf23cb3b97d746989aac07478288fe4cb25"},{"path":"/usr/share/zoneinfo/right/Asia/Vientiane","mode":33188,"size":755,"sha256":"d91fabfc29473f96272f2e96868a44393d6ce11950b7a5ec32eae83dc142b4a4"},{"path":"/usr/share/zoneinfo/right/Asia/Vladivostok","mode":33188,"size":1779,"sha256":"633d4328fec78ef09dc0bf58025da4a365176a1680f4c8c8cf90cef309e65236"},{"path":"/usr/share/zoneinfo/right/Asia/Yakutsk","mode":33188,"size":1778,"sha256":"d1fc7358bb9353f77a5c500910586619b82a7d3a3de096b25f90742eddc07d2d"},{"path":"/usr/share/zoneinfo/right/Asia/Yangon","mode":33188,"size":832,"sha256":"a38bd662f07725a121cbb302b992167054cd598c5127c30514f1fe1fe0c8d70d"},{"path":"/usr/share/zoneinfo/right/Asia/Yekaterinburg","mode":33188,"size":1816,"sha256":"d259b425879f1d3fea283f9ee237e4f11aa2e4bf918fc40cff782cb2fa4a4f36"},{"path":"/usr/share/zoneinfo/right/Asia/Yerevan","mode":33188,"size":1748,"sha256":"5b7792e14dafe5e5cf54fb58169472bf364e7d841a08ef82224fd13c3f3d6b46"},{"path":"/usr/share/zoneinfo/right/Atlantic/Azores","mode":33188,"size":4028,"sha256":"bf6ed07f6b72df9243e62a64bca11608dcf4b7a0ef0231c3c3f819c1e74fdc2a"},{"path":"/usr/share/zoneinfo/right/Atlantic/Bermuda","mode":33188,"size":2544,"sha256":"d6de741b6c7895bfd687374854ea64fb2998d65436d657d27bd4c7c59b351918"},{"path":"/usr/share/zoneinfo/right/Atlantic/Canary","mode":33188,"size":2451,"sha256":"f0bf9911e3c52ec1a10e1b9c0cb94d323c7425614948efc559ffe15c67fb48cd"},{"path":"/usr/share/zoneinfo/right/Atlantic/Cape_Verde","mode":33188,"size":819,"sha256":"ab775c80ae7c0b1b6b02016a7ae7045fc69310869a35ac3027e5f6a900e96f8c"},{"path":"/usr/share/zoneinfo/right/Atlantic/Faeroe","mode":33188,"size":2369,"sha256":"4f5a41b4ae349e1c6466cba14b5afaf7d7b4a9623fc8395173e4d3a2b4a5f90d"},{"path":"/usr/share/zoneinfo/right/Atlantic/Faroe","mode":33188,"size":2369,"sha256":"4f5a41b4ae349e1c6466cba14b5afaf7d7b4a9623fc8395173e4d3a2b4a5f90d"},{"path":"/usr/share/zoneinfo/right/Atlantic/Jan_Mayen","mode":33188,"size":2791,"sha256":"b9f4a8a248c4b945a12640b4be549baaa438a9c3472822028e9f4988cd4e8b63"},{"path":"/usr/share/zoneinfo/right/Atlantic/Madeira","mode":33188,"size":4024,"sha256":"35dedfac50f7e188bdf50bf3e03fd597e822d77b353461bbb60e3ffc3be1b71f"},{"path":"/usr/share/zoneinfo/right/Atlantic/Reykjavik","mode":33188,"size":1728,"sha256":"4a419779c4e933cb9ba204355f1a3649c72d443a95e0a6d81ff506ab467293c0"},{"path":"/usr/share/zoneinfo/right/Atlantic/South_Georgia","mode":33188,"size":699,"sha256":"87c1e145862e19c3591293cebc524c2248485fc6d82c0b9f7f289eac3c665cb2"},{"path":"/usr/share/zoneinfo/right/Atlantic/St_Helena","mode":33188,"size":710,"sha256":"c177f3894cfb7acf27cfefcefd177aebfa1699e409e7fc4cd5a11ef116f8d236"},{"path":"/usr/share/zoneinfo/right/Atlantic/Stanley","mode":33188,"size":1786,"sha256":"e0f88a4e32a223a054780193c34fbcfea7be9ac87493ddc98df5636868a69c44"},{"path":"/usr/share/zoneinfo/right/Australia/ACT","mode":33188,"size":2763,"sha256":"3cb5754502c335e80d639b47a7f36ddda899d8456ebfe72308882ee5ef92a698"},{"path":"/usr/share/zoneinfo/right/Australia/Adelaide","mode":33188,"size":2778,"sha256":"02aaaee74a3e5b3d1629ae41daa5b46da01708d3bb87b3c7100c1e7b8202ab81"},{"path":"/usr/share/zoneinfo/right/Australia/Brisbane","mode":33188,"size":992,"sha256":"ddda440f5a5595a004677523165714a25709a156027554a06dd427d5308d9b18"},{"path":"/usr/share/zoneinfo/right/Australia/Broken_Hill","mode":33188,"size":2814,"sha256":"fd0d2135fb2fa2835646f9e83c23e040bbd8e45b949f3b181925049c7cf419d9"},{"path":"/usr/share/zoneinfo/right/Australia/Canberra","mode":33188,"size":2763,"sha256":"3cb5754502c335e80d639b47a7f36ddda899d8456ebfe72308882ee5ef92a698"},{"path":"/usr/share/zoneinfo/right/Australia/Currie","mode":33188,"size":2763,"sha256":"f37c37574a6bbbebaf7d25eae300f4499741c50b8967335185ba7ee122c56869"},{"path":"/usr/share/zoneinfo/right/Australia/Darwin","mode":33188,"size":863,"sha256":"a7223b77c9ca3ab6de014f4f9b566c79dd3f4161c5ea4223b6ff8608285535d9"},{"path":"/usr/share/zoneinfo/right/Australia/Eucla","mode":33188,"size":1038,"sha256":"422c107c8b5e6a957bdb37b5d7785be3771db0e14bbbf2b7892a9eeb86e92022"},{"path":"/usr/share/zoneinfo/right/Australia/Hobart","mode":33188,"size":2875,"sha256":"b833dd205698e9e4ec4f134c910a46c2c203379594b70fb3dc15dac7d8d15a42"},{"path":"/usr/share/zoneinfo/right/Australia/LHI","mode":33188,"size":2424,"sha256":"7546e925623ccba6e9a112784d57389b98b7cff5bd403e179625e2ee7dbf67e3"},{"path":"/usr/share/zoneinfo/right/Australia/Lindeman","mode":33188,"size":1062,"sha256":"9134536b2b9078c1807e7529de64da0bc34f32f97aea996b769ccaa474c3aa12"},{"path":"/usr/share/zoneinfo/right/Australia/Lord_Howe","mode":33188,"size":2424,"sha256":"7546e925623ccba6e9a112784d57389b98b7cff5bd403e179625e2ee7dbf67e3"},{"path":"/usr/share/zoneinfo/right/Australia/Melbourne","mode":33188,"size":2763,"sha256":"f11ce1fe7a552704c280c6e642ab51a416aff8ad6b9d9c987e90280ce0c6fc3f"},{"path":"/usr/share/zoneinfo/right/Australia/NSW","mode":33188,"size":2763,"sha256":"3cb5754502c335e80d639b47a7f36ddda899d8456ebfe72308882ee5ef92a698"},{"path":"/usr/share/zoneinfo/right/Australia/North","mode":33188,"size":863,"sha256":"a7223b77c9ca3ab6de014f4f9b566c79dd3f4161c5ea4223b6ff8608285535d9"},{"path":"/usr/share/zoneinfo/right/Australia/Perth","mode":33188,"size":1019,"sha256":"dd69002d8273324fcb2dff6a52a11667b34b9cdbd36858d5ccda4f2785b7ef7a"},{"path":"/usr/share/zoneinfo/right/Australia/Queensland","mode":33188,"size":992,"sha256":"ddda440f5a5595a004677523165714a25709a156027554a06dd427d5308d9b18"},{"path":"/usr/share/zoneinfo/right/Australia/South","mode":33188,"size":2778,"sha256":"02aaaee74a3e5b3d1629ae41daa5b46da01708d3bb87b3c7100c1e7b8202ab81"},{"path":"/usr/share/zoneinfo/right/Australia/Sydney","mode":33188,"size":2763,"sha256":"3cb5754502c335e80d639b47a7f36ddda899d8456ebfe72308882ee5ef92a698"},{"path":"/usr/share/zoneinfo/right/Australia/Tasmania","mode":33188,"size":2875,"sha256":"b833dd205698e9e4ec4f134c910a46c2c203379594b70fb3dc15dac7d8d15a42"},{"path":"/usr/share/zoneinfo/right/Australia/Victoria","mode":33188,"size":2763,"sha256":"f11ce1fe7a552704c280c6e642ab51a416aff8ad6b9d9c987e90280ce0c6fc3f"},{"path":"/usr/share/zoneinfo/right/Australia/West","mode":33188,"size":1019,"sha256":"dd69002d8273324fcb2dff6a52a11667b34b9cdbd36858d5ccda4f2785b7ef7a"},{"path":"/usr/share/zoneinfo/right/Australia/Yancowinna","mode":33188,"size":2814,"sha256":"fd0d2135fb2fa2835646f9e83c23e040bbd8e45b949f3b181925049c7cf419d9"},{"path":"/usr/share/zoneinfo/right/Brazil/Acre","mode":33188,"size":1197,"sha256":"90e09a708c3c756baf60fafda6f8a5f3316b8f0f13ae2433bcad860c74bd544c"},{"path":"/usr/share/zoneinfo/right/Brazil/DeNoronha","mode":33188,"size":1277,"sha256":"cc5b5c148b76dc58c925f589124f7f1ac05a52e9bc8f8cb0bf8bbef2b5779c78"},{"path":"/usr/share/zoneinfo/right/Brazil/East","mode":33188,"size":2005,"sha256":"30ef7b506e76ac5286ad4415d7daa8abf0af2b6c63abb540869a8dc1c61f28a0"},{"path":"/usr/share/zoneinfo/right/Brazil/West","mode":33188,"size":1165,"sha256":"c921cc8c1a0a1ed91805b81c0f22d5ee3a78fe3422f6366160c37b03302fd250"},{"path":"/usr/share/zoneinfo/right/CET","mode":33188,"size":2642,"sha256":"a9ab0888ef44577631cf924205405001a436f7d97899c8989907aba1b77a61be"},{"path":"/usr/share/zoneinfo/right/CST6CDT","mode":33188,"size":2834,"sha256":"fc4181f42429479b45e3b5d1e9d8775017957bca5c82fc9530769fcb81b2fe8e"},{"path":"/usr/share/zoneinfo/right/Canada/Atlantic","mode":33188,"size":3978,"sha256":"86c84ef0a21a387fdd0058046268c5eca94c10cb73231638724d344cc478bd10"},{"path":"/usr/share/zoneinfo/right/Canada/Central","mode":33188,"size":3431,"sha256":"a91e3074914af25d44e7428f07b7e15c46a9b1c61adf146d78058bfb95128031"},{"path":"/usr/share/zoneinfo/right/Canada/Eastern","mode":33188,"size":4043,"sha256":"bd1fdaf567be65339c2fe8cadf9e690d0929548cd731edcb41ae7f322885a590"},{"path":"/usr/share/zoneinfo/right/Canada/Mountain","mode":33188,"size":2886,"sha256":"022478c15aee3ef60c10f350122529278adf3954d02e30f78df5ca8d6eb937ee"},{"path":"/usr/share/zoneinfo/right/Canada/Newfoundland","mode":33188,"size":4204,"sha256":"10784794564849767481803ad10924bd7092c041b5e5859dc7cdf883abe13a7e"},{"path":"/usr/share/zoneinfo/right/Canada/Pacific","mode":33188,"size":3441,"sha256":"59f3b401ccdbabb740e3395b75233402d6d2e0590195df1e5d8e73e736158361"},{"path":"/usr/share/zoneinfo/right/Canada/Saskatchewan","mode":33188,"size":1534,"sha256":"7ef7b8f3a4e1baf07289907c77a4218ac0be68c7a24e980940a05cbba77e53c9"},{"path":"/usr/share/zoneinfo/right/Canada/Yukon","mode":33188,"size":2149,"sha256":"656e8559dd8f0f71b49cbd7e39ea69f9b229cd28cbbd26d67c067faeb71e3dcb"},{"path":"/usr/share/zoneinfo/right/Chile/Continental","mode":33188,"size":3073,"sha256":"986a3d87481910c37ff5045ecb26e8d7832333bb9b8bf0cefa8f2518c787fcb5"},{"path":"/usr/share/zoneinfo/right/Chile/EasterIsland","mode":33188,"size":2777,"sha256":"27c072b5550ceea84e801fd932d838d9c6fde3fbe5f3fffd897dcf12f5f36bb1"},{"path":"/usr/share/zoneinfo/right/Cuba","mode":33188,"size":2977,"sha256":"0d4bfd6b414442661f79556ac625c9f30e051af6694be67e3ad312e9e9589c50"},{"path":"/usr/share/zoneinfo/right/EET","mode":33188,"size":2416,"sha256":"7a4178745768032216702f31fa03f676677d5951079d7e17856ab4be0ddc4061"},{"path":"/usr/share/zoneinfo/right/EST","mode":33188,"size":667,"sha256":"e7c90a5d782d8843b78996aaf9cc7d332f29d923e8b41739fa0d523b6675a816"},{"path":"/usr/share/zoneinfo/right/EST5EDT","mode":33188,"size":2834,"sha256":"0f7e22d9f44ba8c1c49034d187a3910eabea89ea5702363f55eadfcd12e01daa"},{"path":"/usr/share/zoneinfo/right/Egypt","mode":33188,"size":2512,"sha256":"a3c84ceb744bbb495b49ef286308143f267da03f75931b82fdcb5c5a3aebcdd8"},{"path":"/usr/share/zoneinfo/right/Eire","mode":33188,"size":4083,"sha256":"406fece907ecec8f7be8a75ca84953fb1d67282e42433f8f559e4def26ea299e"},{"path":"/usr/share/zoneinfo/right/Etc/GMT","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+0","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+1","mode":33188,"size":678,"sha256":"2dfab8b47a9935ec8047b521c8a271ca2f4543ddd8c7e5615c489c3257824140"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+10","mode":33188,"size":679,"sha256":"daf919cae7f8cbe9932a89be91f2054c115838dae240389d4f4567a66287e531"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+11","mode":33188,"size":679,"sha256":"ef109214424a5197b2a034d5a67606ffd2396fe37b464876745541e6ed9ca375"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+12","mode":33188,"size":679,"sha256":"b901dd04cd5aa1e1bc91e16f651751ff45a24c88a3b3236336044dccf7a21244"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+2","mode":33188,"size":678,"sha256":"2d16fb68e998d75ad599d5f6101c45ac83f7dc02e8a4cca6f5fee81fa77ce668"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+3","mode":33188,"size":678,"sha256":"3f6f463bbba4e762a8834597a7033c770d6af14b05a8b703b3d5d014990ea4b7"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+4","mode":33188,"size":678,"sha256":"932f8cf3e71116a6b3c4a73a68e8b9b78ad33772c11c38f6e49bd3b9e3508358"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+5","mode":33188,"size":678,"sha256":"7469abe462d0ecd98bd657ac98e8a420ac3bc5c913a7d1d0b6571b9ad55ad659"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+6","mode":33188,"size":678,"sha256":"516d359bfacd113d911e4a19d93dfb00c8d5a1de3d21b0356f520e4c45471fc9"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+7","mode":33188,"size":678,"sha256":"48e9f1b3cbab9cc818adab2956234adfdf8eeacb51e442221282c073921462fb"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+8","mode":33188,"size":678,"sha256":"b8ac2c2ab11935c312c05c72a665b2567e6df428ee4229e688272e9aa3c71603"},{"path":"/usr/share/zoneinfo/right/Etc/GMT+9","mode":33188,"size":678,"sha256":"66586cb177e807cf1f7f9382f7ffb847f97b579405f6a2a4258f3b601837441f"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-0","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-1","mode":33188,"size":679,"sha256":"3f64722b5d0b9119c26d97bea25b946aa46b440fbd0c5735276049ec0bc9ea9a"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-10","mode":33188,"size":680,"sha256":"364a1c067f561986ce55d2a1c132d394bb12c024b41fd8185498605eb6d68996"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-11","mode":33188,"size":680,"sha256":"3c27112120e1d285b1feaaabd7d6086d82bb20498f8b3b79135345dcfb5beb34"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-12","mode":33188,"size":680,"sha256":"5f7d64bac9608ae4d00f58ce111c849fa5fd10c219dfe0a85d8d56e514fe386f"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-13","mode":33188,"size":680,"sha256":"9349e68a0ac17041b18afe3cdd474c562e9aac289fd76f12f5169b59754825b7"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-14","mode":33188,"size":680,"sha256":"a748a0ca53f5a510a3abb4a62ffbbe3ffc17e01f65cc6af01878c9df8b43b204"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-2","mode":33188,"size":679,"sha256":"41884dfc60a5b6ec4048d7d94db86d44ef512e166200d2de6843218bb97fb3c9"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-3","mode":33188,"size":679,"sha256":"5391c1595cf4e7df4e5fb4a390cab8cbf6c23644c8bf87a8d6fcc7753dd64f36"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-4","mode":33188,"size":679,"sha256":"6e710ab5d40d44ae4b369a01ba839f5b52dd417565bd92ac663585a0372db6e1"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-5","mode":33188,"size":679,"sha256":"b4d14c0621108bb15b9e3a08479291c8afbb960ab9205cbd109cfeebe87465b9"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-6","mode":33188,"size":679,"sha256":"68d638daa5d47e0684ecb49c49fa0eba30e044df0b01655a366e4f2615bebe82"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-7","mode":33188,"size":679,"sha256":"bc003bfc68545e819c20e22e92f08f67caef03822ed8dc60231fe96028aa6072"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-8","mode":33188,"size":679,"sha256":"c32fe342c3ef366d364c0edc9cdeb26a35a9868f599ee5cc05568145121ab2b8"},{"path":"/usr/share/zoneinfo/right/Etc/GMT-9","mode":33188,"size":679,"sha256":"3546d660bbebcf312239764bea8f0c39a91e719d2b8ac3e8bfed0d362d334479"},{"path":"/usr/share/zoneinfo/right/Etc/GMT0","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/Etc/Greenwich","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/Etc/UCT","mode":33188,"size":667,"sha256":"d19fdd5d26a7753518ee9a09ab74a8e4efa9a4e6ed56eff85baabd8af9c0e459"},{"path":"/usr/share/zoneinfo/right/Etc/UTC","mode":33188,"size":667,"sha256":"d19fdd5d26a7753518ee9a09ab74a8e4efa9a4e6ed56eff85baabd8af9c0e459"},{"path":"/usr/share/zoneinfo/right/Etc/Universal","mode":33188,"size":667,"sha256":"d19fdd5d26a7753518ee9a09ab74a8e4efa9a4e6ed56eff85baabd8af9c0e459"},{"path":"/usr/share/zoneinfo/right/Etc/Zulu","mode":33188,"size":667,"sha256":"d19fdd5d26a7753518ee9a09ab74a8e4efa9a4e6ed56eff85baabd8af9c0e459"},{"path":"/usr/share/zoneinfo/right/Europe/Amsterdam","mode":33188,"size":3489,"sha256":"ae32e0cb5a9ea89b38213163daf4feb4840a6b72e82d5464c647d0a618531697"},{"path":"/usr/share/zoneinfo/right/Europe/Andorra","mode":33188,"size":2291,"sha256":"1330f8009adea3c6e5134cdeadaedaa6fbbcd72b2753207ccbb953ccf5001d18"},{"path":"/usr/share/zoneinfo/right/Europe/Astrakhan","mode":33188,"size":1732,"sha256":"bcb19ce7f27da441ddc26ddb5efdb9683ece2df2f013e35333a113bca8d84ac0"},{"path":"/usr/share/zoneinfo/right/Europe/Athens","mode":33188,"size":2811,"sha256":"0c23a856f0e9c47bba55cb81c426eca0d190aea6043b018e2affa55f21b43664"},{"path":"/usr/share/zoneinfo/right/Europe/Belfast","mode":33188,"size":4227,"sha256":"256c78cc8a67c9b7796737d6af67860246715133443319c41c5962d4d4411f6d"},{"path":"/usr/share/zoneinfo/right/Europe/Belgrade","mode":33188,"size":2497,"sha256":"3debded934cdf0c472df38375bd1a69c9135fb21890969bd68a50956e7181e7c"},{"path":"/usr/share/zoneinfo/right/Europe/Berlin","mode":33188,"size":2875,"sha256":"0b4604767edbae4fc43cd24bd96ec235232471fddff9dc15328c0b74d4c3dc90"},{"path":"/usr/share/zoneinfo/right/Europe/Bratislava","mode":33188,"size":2878,"sha256":"1ba4274fd53b61a31041cad12327027a4b536e29e45361f9b9a0708851a7964f"},{"path":"/usr/share/zoneinfo/right/Europe/Brussels","mode":33188,"size":3510,"sha256":"5e8b1eb03d518914baa45eeaf1d19e491fd3ac24319f7f79ce904120bac7ae19"},{"path":"/usr/share/zoneinfo/right/Europe/Bucharest","mode":33188,"size":2761,"sha256":"4052f7958d6994e77da457cc9255749b2df0a6270841d23cb93937d58e1f4ec2"},{"path":"/usr/share/zoneinfo/right/Europe/Budapest","mode":33188,"size":2945,"sha256":"865242b95f7d1177e289a4853ab538079af84710f8f09b4908db5928670e016a"},{"path":"/usr/share/zoneinfo/right/Europe/Busingen","mode":33188,"size":2458,"sha256":"46a95ddb0c5047f5b03c6ebdd2c35f87f59e6719d2a2385134408f826753e60f"},{"path":"/usr/share/zoneinfo/right/Europe/Chisinau","mode":33188,"size":2985,"sha256":"ea169f6577633d68990e74350d1f53c54d309ea1fb461bc235f6dc3c2bfd03c4"},{"path":"/usr/share/zoneinfo/right/Europe/Copenhagen","mode":33188,"size":2700,"sha256":"cc7d0746ef3061d3de714685a821a4781abe813fdc6327f162fc70b0c22d62ac"},{"path":"/usr/share/zoneinfo/right/Europe/Dublin","mode":33188,"size":4083,"sha256":"406fece907ecec8f7be8a75ca84953fb1d67282e42433f8f559e4def26ea299e"},{"path":"/usr/share/zoneinfo/right/Europe/Gibraltar","mode":33188,"size":3601,"sha256":"16fa8d1cb048eb5d4defb961df736ae7db4d477b6f08b9d94572da2303681fe7"},{"path":"/usr/share/zoneinfo/right/Europe/Guernsey","mode":33188,"size":4227,"sha256":"256c78cc8a67c9b7796737d6af67860246715133443319c41c5962d4d4411f6d"},{"path":"/usr/share/zoneinfo/right/Europe/Helsinki","mode":33188,"size":2449,"sha256":"a1894d50d5bc5e541f340d601cd8ababe40da90fa867cc7ed3215be1cd6282de"},{"path":"/usr/share/zoneinfo/right/Europe/Isle_of_Man","mode":33188,"size":4227,"sha256":"256c78cc8a67c9b7796737d6af67860246715133443319c41c5962d4d4411f6d"},{"path":"/usr/share/zoneinfo/right/Europe/Istanbul","mode":33188,"size":2505,"sha256":"d0fd3d19c0e209595df3017696f8dc59d900be1dd6a3a8b354f7798ba6ce1f4d"},{"path":"/usr/share/zoneinfo/right/Europe/Jersey","mode":33188,"size":4227,"sha256":"256c78cc8a67c9b7796737d6af67860246715133443319c41c5962d4d4411f6d"},{"path":"/usr/share/zoneinfo/right/Europe/Kaliningrad","mode":33188,"size":2072,"sha256":"5ec14b617cbe85a326677b570296a68c866c954a2c2d42e19387c06c29c635e3"},{"path":"/usr/share/zoneinfo/right/Europe/Kiev","mode":33188,"size":2637,"sha256":"24c81f9cf9518821df795eb6c2660d1de98a29d658922bec6f70b05dc9f427e7"},{"path":"/usr/share/zoneinfo/right/Europe/Kirov","mode":33188,"size":1702,"sha256":"50f356bc8b1d5232fe2746f29a440b7e4876a011ad0833d7a137c31d1c1721f0"},{"path":"/usr/share/zoneinfo/right/Europe/Lisbon","mode":33188,"size":4009,"sha256":"f8e850961fc42ea64edb30cebaabad27fccda97bdf6cf1047e4051298bdf20d0"},{"path":"/usr/share/zoneinfo/right/Europe/Ljubljana","mode":33188,"size":2497,"sha256":"3debded934cdf0c472df38375bd1a69c9135fb21890969bd68a50956e7181e7c"},{"path":"/usr/share/zoneinfo/right/Europe/London","mode":33188,"size":4227,"sha256":"256c78cc8a67c9b7796737d6af67860246715133443319c41c5962d4d4411f6d"},{"path":"/usr/share/zoneinfo/right/Europe/Luxembourg","mode":33188,"size":3514,"sha256":"af6eb983dfb45c9e363dafb9d26b8466179415e37ef87991b258523a36c18239"},{"path":"/usr/share/zoneinfo/right/Europe/Madrid","mode":33188,"size":3177,"sha256":"01a00debc9c470fe55edfa31568135024d2450ba34c1c88ed16d620b67af5d83"},{"path":"/usr/share/zoneinfo/right/Europe/Malta","mode":33188,"size":3169,"sha256":"80919f93a3dd18f905ec9ecc82797ea80f289fe05795f32bd9390dbed7ff7d05"},{"path":"/usr/share/zoneinfo/right/Europe/Mariehamn","mode":33188,"size":2449,"sha256":"a1894d50d5bc5e541f340d601cd8ababe40da90fa867cc7ed3215be1cd6282de"},{"path":"/usr/share/zoneinfo/right/Europe/Minsk","mode":33188,"size":1905,"sha256":"52c3784ac0b17fb45be32b9c06a10978f4c53763cf97cf1e9f54b16494fc2a84"},{"path":"/usr/share/zoneinfo/right/Europe/Monaco","mode":33188,"size":3493,"sha256":"7bac15b163365f1415bd5830c70e2433d36b70b490a393be07d0562071bdc98c"},{"path":"/usr/share/zoneinfo/right/Europe/Moscow","mode":33188,"size":2084,"sha256":"8e1367300579da7319742b25b9da707131b058482c77e7a707c71aeb60f067ff"},{"path":"/usr/share/zoneinfo/right/Europe/Nicosia","mode":33188,"size":2556,"sha256":"b801d86c6b957dd1affe34a2d19a0c580be861d8ccd283d9f48e2dc991fe3696"},{"path":"/usr/share/zoneinfo/right/Europe/Oslo","mode":33188,"size":2791,"sha256":"b9f4a8a248c4b945a12640b4be549baaa438a9c3472822028e9f4988cd4e8b63"},{"path":"/usr/share/zoneinfo/right/Europe/Paris","mode":33188,"size":3511,"sha256":"6cd62d7d4c3d0be12b47e2e3c026ad0b5513f16e3dbf46d7812f0501c0522def"},{"path":"/usr/share/zoneinfo/right/Europe/Podgorica","mode":33188,"size":2497,"sha256":"3debded934cdf0c472df38375bd1a69c9135fb21890969bd68a50956e7181e7c"},{"path":"/usr/share/zoneinfo/right/Europe/Prague","mode":33188,"size":2878,"sha256":"1ba4274fd53b61a31041cad12327027a4b536e29e45361f9b9a0708851a7964f"},{"path":"/usr/share/zoneinfo/right/Europe/Riga","mode":33188,"size":2775,"sha256":"543f059b0b90d203ac284c74a9eb1a43acfb6f6de2c3f618b9df24b1b53564d8"},{"path":"/usr/share/zoneinfo/right/Europe/Rome","mode":33188,"size":3232,"sha256":"1900f59ffcc6e5d11fca684876c3efdc837d8ac7c0432603a352b1f17a768b06"},{"path":"/usr/share/zoneinfo/right/Europe/Samara","mode":33188,"size":1776,"sha256":"757ea574d61782c57c7a27f4ca052c5277e3009f99dae455b486f7633fe05e17"},{"path":"/usr/share/zoneinfo/right/Europe/San_Marino","mode":33188,"size":3232,"sha256":"1900f59ffcc6e5d11fca684876c3efdc837d8ac7c0432603a352b1f17a768b06"},{"path":"/usr/share/zoneinfo/right/Europe/Sarajevo","mode":33188,"size":2497,"sha256":"3debded934cdf0c472df38375bd1a69c9135fb21890969bd68a50956e7181e7c"},{"path":"/usr/share/zoneinfo/right/Europe/Saratov","mode":33188,"size":1732,"sha256":"d363c02f8c0d79a6b550239df44b5754efc54291da4d85d82e345f8edb3b6f68"},{"path":"/usr/share/zoneinfo/right/Europe/Simferopol","mode":33188,"size":2030,"sha256":"c749271304d25a3772fec2f14e1a9fe29d66a993e88384b4fb8c35305208aa06"},{"path":"/usr/share/zoneinfo/right/Europe/Skopje","mode":33188,"size":2497,"sha256":"3debded934cdf0c472df38375bd1a69c9135fb21890969bd68a50956e7181e7c"},{"path":"/usr/share/zoneinfo/right/Europe/Sofia","mode":33188,"size":2670,"sha256":"2d9a0ae58e5f9d5b678d68e5874b4d4bf0481a5decd3e9a097bed5f172a16cd0"},{"path":"/usr/share/zoneinfo/right/Europe/Stockholm","mode":33188,"size":2458,"sha256":"57c9a0626fe99afad4195a26bdd53a0013d465c876e4970a365196242191009a"},{"path":"/usr/share/zoneinfo/right/Europe/Tallinn","mode":33188,"size":2727,"sha256":"3ce08292fa8bf8241cfc2bd85b05dec3459e3b653a0333720380ef66841e9db1"},{"path":"/usr/share/zoneinfo/right/Europe/Tirane","mode":33188,"size":2638,"sha256":"aecddbe0e431c06b7d90ce8c9be834f2aafeba71716812b98797272f72d54141"},{"path":"/usr/share/zoneinfo/right/Europe/Tiraspol","mode":33188,"size":2985,"sha256":"ea169f6577633d68990e74350d1f53c54d309ea1fb461bc235f6dc3c2bfd03c4"},{"path":"/usr/share/zoneinfo/right/Europe/Ulyanovsk","mode":33188,"size":1816,"sha256":"1805377db5fc2f5733f3b229c5c3744321fc279b46fd004a5d0d7492a8c55f16"},{"path":"/usr/share/zoneinfo/right/Europe/Uzhgorod","mode":33188,"size":2643,"sha256":"7ede029288ea2e0af7da34e57ef3414159d510db5e41db99ef2bd0becff29c72"},{"path":"/usr/share/zoneinfo/right/Europe/Vaduz","mode":33188,"size":2458,"sha256":"46a95ddb0c5047f5b03c6ebdd2c35f87f59e6719d2a2385134408f826753e60f"},{"path":"/usr/share/zoneinfo/right/Europe/Vatican","mode":33188,"size":3232,"sha256":"1900f59ffcc6e5d11fca684876c3efdc837d8ac7c0432603a352b1f17a768b06"},{"path":"/usr/share/zoneinfo/right/Europe/Vienna","mode":33188,"size":2777,"sha256":"e69df04b842a8f784b6fc0adddf418fe2e3e635d7a0f1c60ed35c05c5c7e7b9d"},{"path":"/usr/share/zoneinfo/right/Europe/Vilnius","mode":33188,"size":2739,"sha256":"60409d0bfd11d41ed822fbc0564645c41d63b215b8b1822c369a5af7824631fe"},{"path":"/usr/share/zoneinfo/right/Europe/Volgograd","mode":33188,"size":1732,"sha256":"17a71cd6a317c0b91c3a7f1daaee051a522ac9de2366d985b87f4e4b56f786dd"},{"path":"/usr/share/zoneinfo/right/Europe/Warsaw","mode":33188,"size":3245,"sha256":"2776052936d3361f49da479c0a6d522ea7ec256300cc9263d1011848ab2bb3a9"},{"path":"/usr/share/zoneinfo/right/Europe/Zagreb","mode":33188,"size":2497,"sha256":"3debded934cdf0c472df38375bd1a69c9135fb21890969bd68a50956e7181e7c"},{"path":"/usr/share/zoneinfo/right/Europe/Zaporozhye","mode":33188,"size":2655,"sha256":"67d4c4e23f865eeb4fcc7779563524189dd9852d7547ab5b9374f637f4f3faef"},{"path":"/usr/share/zoneinfo/right/Europe/Zurich","mode":33188,"size":2458,"sha256":"46a95ddb0c5047f5b03c6ebdd2c35f87f59e6719d2a2385134408f826753e60f"},{"path":"/usr/share/zoneinfo/right/GB","mode":33188,"size":4227,"sha256":"256c78cc8a67c9b7796737d6af67860246715133443319c41c5962d4d4411f6d"},{"path":"/usr/share/zoneinfo/right/GB-Eire","mode":33188,"size":4227,"sha256":"256c78cc8a67c9b7796737d6af67860246715133443319c41c5962d4d4411f6d"},{"path":"/usr/share/zoneinfo/right/GMT","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/GMT+0","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/GMT-0","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/GMT0","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/Greenwich","mode":33188,"size":667,"sha256":"da4f5e177e0e5138774896d0b82b59cce878cf3700734a5d6cdfac2f0f96eb28"},{"path":"/usr/share/zoneinfo/right/HST","mode":33188,"size":668,"sha256":"d6c14dcfa90060f656344c7f7078d78fd6046e38d850b78de5f066c0f3c0c655"},{"path":"/usr/share/zoneinfo/right/Hongkong","mode":33188,"size":1771,"sha256":"f4f912297ccc9172c05ffe76746d938e832d85d3154b4638709753c0f4800c7c"},{"path":"/usr/share/zoneinfo/right/Iceland","mode":33188,"size":1728,"sha256":"4a419779c4e933cb9ba204355f1a3649c72d443a95e0a6d81ff506ab467293c0"},{"path":"/usr/share/zoneinfo/right/Indian/Antananarivo","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Indian/Chagos","mode":33188,"size":760,"sha256":"f8cf0c5a28233ce257fb4b7fbcc360677dd2263eac889a65eb02c09e86541d72"},{"path":"/usr/share/zoneinfo/right/Indian/Christmas","mode":33188,"size":700,"sha256":"445dd04f82a28c39962af2578501b9d8cfc0e17ee56630a30c78bbd7e8de7ba1"},{"path":"/usr/share/zoneinfo/right/Indian/Cocos","mode":33188,"size":709,"sha256":"73738c8c7d23555123841d80cf638f6e8e2be52f93c841b54d97edba207f9ad5"},{"path":"/usr/share/zoneinfo/right/Indian/Comoro","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Indian/Kerguelen","mode":33188,"size":722,"sha256":"ac6df2f0f61d25a524ae0c2aa10b663ab852dcbd51e97cec4db54843b8ee916e"},{"path":"/usr/share/zoneinfo/right/Indian/Mahe","mode":33188,"size":722,"sha256":"1c55b3ce226f3071ae02834afd72edb45e2553e95bda7862371aef34d1fa024c"},{"path":"/usr/share/zoneinfo/right/Indian/Maldives","mode":33188,"size":755,"sha256":"f7e3029145d587448a750d43b4dd67a40bc9a6a2499916cd3093fbcc6a4d7b2c"},{"path":"/usr/share/zoneinfo/right/Indian/Mauritius","mode":33188,"size":802,"sha256":"930cd4dc0a8cbbbbebd33c61edf12c5431e3263b3748cdb6ac0c1afba39c8623"},{"path":"/usr/share/zoneinfo/right/Indian/Mayotte","mode":33188,"size":825,"sha256":"ae39f133e4fad735bf5e099f9090b322f84efb7fe050968da196289a3c703905"},{"path":"/usr/share/zoneinfo/right/Indian/Reunion","mode":33188,"size":722,"sha256":"f3460ec007959b0ed112cdc75fd1decf42969ab272cdb157edf9c3a040c6c279"},{"path":"/usr/share/zoneinfo/right/Iran","mode":33188,"size":3164,"sha256":"c5940a0ac0a0fb9c21f747d475f7b30031ec8c2700fbfa1bfd1496724c953715"},{"path":"/usr/share/zoneinfo/right/Israel","mode":33188,"size":2861,"sha256":"f11b537da563f2c93dcda9206f3cb54ea87dbe701572cfe159854b4b8f1ef90b"},{"path":"/usr/share/zoneinfo/right/Jamaica","mode":33188,"size":1047,"sha256":"47ddec901639efbe7268363dcc0d8b92a855372b0cae12720d68cce9a8974fdb"},{"path":"/usr/share/zoneinfo/right/Japan","mode":33188,"size":858,"sha256":"1ecabb9dd5bcee432606c243ffd05fc8f1f50ec8f531dfaf3dd7a872160814f0"},{"path":"/usr/share/zoneinfo/right/Kwajalein","mode":33188,"size":884,"sha256":"f85d2a961799deb5cb0bd7a45974d7cdfbedeac8a3b82330512b0b1ccb7cd8eb"},{"path":"/usr/share/zoneinfo/right/Libya","mode":33188,"size":1195,"sha256":"72bb85f8ac4ec74b2ae92214c047c82f1f39c9c0785d0f54e152b8c1d940adda"},{"path":"/usr/share/zoneinfo/right/MET","mode":33188,"size":2642,"sha256":"735b7a481c6b4024076996235dc00c88eba04788ea0d2320f52f3b6f832e2c5c"},{"path":"/usr/share/zoneinfo/right/MST","mode":33188,"size":667,"sha256":"d7ed7889d7e664fa5f24d3ebca03abc5e6f4c1af886e13b6d057d0aa4009a953"},{"path":"/usr/share/zoneinfo/right/MST7MDT","mode":33188,"size":2834,"sha256":"f5bff9e9551d99b333440822fd3fa74d2bf03b0303585ce0705557b869e47e83"},{"path":"/usr/share/zoneinfo/right/Mexico/BajaNorte","mode":33188,"size":2896,"sha256":"a1a5199868d6aa4c24fef5e908e99e4c6e116d16afc554d25ec431990d8f02da"},{"path":"/usr/share/zoneinfo/right/Mexico/BajaSur","mode":33188,"size":2104,"sha256":"972ebc94965c29a285412a68e853fc7729bd741b5be52edeb9f3b9a1a707ac43"},{"path":"/usr/share/zoneinfo/right/Mexico/General","mode":33188,"size":2158,"sha256":"2b2e4e7d462f693d46142205a03882b383f3cfbc6eaa0a4c514fe71fd5112f12"},{"path":"/usr/share/zoneinfo/right/NZ","mode":33188,"size":3000,"sha256":"c6fa7d47e6fb209806155ca05d2d0721726515ad678714f3197b9daeb9da3a96"},{"path":"/usr/share/zoneinfo/right/NZ-CHAT","mode":33188,"size":2622,"sha256":"7d7cab36a76aa5df26ae237bb5b1f4abb4efbc7eb4807dabe74540ef5187a25d"},{"path":"/usr/share/zoneinfo/right/Navajo","mode":33188,"size":2993,"sha256":"7448c66048e5489a28ecad3adc495351163e62cedff714bec6d15506a9e1f548"},{"path":"/usr/share/zoneinfo/right/PRC","mode":33188,"size":1122,"sha256":"add747558dc8f3175776014d9653cf734a761b95dec62f06a3922bfce9f82b6e"},{"path":"/usr/share/zoneinfo/right/PST8PDT","mode":33188,"size":2834,"sha256":"f08ae6766d50d2008608f2e668ff34560eef0fb62b3e60df8c019e04cb914780"},{"path":"/usr/share/zoneinfo/right/Pacific/Apia","mode":33188,"size":1669,"sha256":"3b8ceeb83ab926790b5ae3dacbf350c1a67f014b0794bcafe42616944d52a1a6"},{"path":"/usr/share/zoneinfo/right/Pacific/Auckland","mode":33188,"size":3000,"sha256":"c6fa7d47e6fb209806155ca05d2d0721726515ad678714f3197b9daeb9da3a96"},{"path":"/usr/share/zoneinfo/right/Pacific/Bougainville","mode":33188,"size":831,"sha256":"f6be590e2ca7b1132a89a2347e6bab35f303881e27a95a3768fbe2044fd2da9b"},{"path":"/usr/share/zoneinfo/right/Pacific/Chatham","mode":33188,"size":2622,"sha256":"7d7cab36a76aa5df26ae237bb5b1f4abb4efbc7eb4807dabe74540ef5187a25d"},{"path":"/usr/share/zoneinfo/right/Pacific/Chuuk","mode":33188,"size":831,"sha256":"9edef2327e3ea2e74d2eb9d2ce91dbfcc72ee9c46541cfd686f0eda9989942c1"},{"path":"/usr/share/zoneinfo/right/Pacific/Easter","mode":33188,"size":2777,"sha256":"27c072b5550ceea84e801fd932d838d9c6fde3fbe5f3fffd897dcf12f5f36bb1"},{"path":"/usr/share/zoneinfo/right/Pacific/Efate","mode":33188,"size":1027,"sha256":"c7062ab08064a9ca13ad2c823b29f7b2d0a04cd7bf4a9e17c7dc75fb0007baff"},{"path":"/usr/share/zoneinfo/right/Pacific/Enderbury","mode":33188,"size":794,"sha256":"8757354f311a09599c3eac732b4cafe172c311a15291a96b95f659038ba025cf"},{"path":"/usr/share/zoneinfo/right/Pacific/Fakaofo","mode":33188,"size":756,"sha256":"250e6d05b76670206d86dbf786f8c671e7ee0e3260fa3cf728246f05e40117f2"},{"path":"/usr/share/zoneinfo/right/Pacific/Fiji","mode":33188,"size":1638,"sha256":"be6db03c46c5dfd1258384c00ccc0137b84b1787cacc6da4e5ada499adcb27c4"},{"path":"/usr/share/zoneinfo/right/Pacific/Funafuti","mode":33188,"size":701,"sha256":"3a9da5b61aad5ea62609b9b7b6c838e38129f7c1722f3c078ad2588aafbe0428"},{"path":"/usr/share/zoneinfo/right/Pacific/Galapagos","mode":33188,"size":803,"sha256":"6d318df273394bf526ef4318eecfc047e55dda60fb4791bda097d0ba7e52a8c8"},{"path":"/usr/share/zoneinfo/right/Pacific/Gambier","mode":33188,"size":721,"sha256":"2d89a421366c5757aa91f50667646b760032b5f4732a53374e4a05b0045d6483"},{"path":"/usr/share/zoneinfo/right/Pacific/Guadalcanal","mode":33188,"size":723,"sha256":"fe837664f234ac8eb7598cc4df8f9bd1df7afc34d9c5905001cfdc3241e2ea73"},{"path":"/usr/share/zoneinfo/right/Pacific/Guam","mode":33188,"size":1065,"sha256":"2e85a11e3769f6576cc0131f7a59d3d145639f527548d59638086ae4b09a1d13"},{"path":"/usr/share/zoneinfo/right/Pacific/Honolulu","mode":33188,"size":878,"sha256":"93c484f1a3546cf33ee6bcbc52494b4e91d7c5d8d6dc9cc6a73751f8d8235cb3"},{"path":"/usr/share/zoneinfo/right/Pacific/Johnston","mode":33188,"size":878,"sha256":"93c484f1a3546cf33ee6bcbc52494b4e91d7c5d8d6dc9cc6a73751f8d8235cb3"},{"path":"/usr/share/zoneinfo/right/Pacific/Kiritimati","mode":33188,"size":798,"sha256":"f33ea162876a1311c2d6a974cf7f079893bdac950dbd180e2cfb107a879ab303"},{"path":"/usr/share/zoneinfo/right/Pacific/Kosrae","mode":33188,"size":921,"sha256":"572fb52c2262c3aeda2aef85157c862a305e99c15a5a673b081a01c9dd89c3ee"},{"path":"/usr/share/zoneinfo/right/Pacific/Kwajalein","mode":33188,"size":884,"sha256":"f85d2a961799deb5cb0bd7a45974d7cdfbedeac8a3b82330512b0b1ccb7cd8eb"},{"path":"/usr/share/zoneinfo/right/Pacific/Majuro","mode":33188,"size":874,"sha256":"6298dff3baf870ed80da5e52a282ffdb0b9ac6ccf2c1a2ed4d910aef532dbf74"},{"path":"/usr/share/zoneinfo/right/Pacific/Marquesas","mode":33188,"size":730,"sha256":"8bddb6881492ed79f799832454b02809ad7922791994b9c19f98094dc4206647"},{"path":"/usr/share/zoneinfo/right/Pacific/Midway","mode":33188,"size":736,"sha256":"c996db6822af6b663b37e0c8750132432169950eed2c24bab4c9f843475b5cb5"},{"path":"/usr/share/zoneinfo/right/Pacific/Nauru","mode":33188,"size":817,"sha256":"7e240f6870254d1f701d3d480248add43b0648f75dff3269d926ea3b2d703a9a"},{"path":"/usr/share/zoneinfo/right/Pacific/Niue","mode":33188,"size":801,"sha256":"2eecd96d4056c59d3db04eea43c3f1cb491398d84732d88a500b13e15624eb57"},{"path":"/usr/share/zoneinfo/right/Pacific/Norfolk","mode":33188,"size":1468,"sha256":"8c5874c6ab78e49f434f7ca29ac0303b59d2dace69ef0e3fdd6bf6a566bfbc6a"},{"path":"/usr/share/zoneinfo/right/Pacific/Noumea","mode":33188,"size":863,"sha256":"5e4a79b64ba530ff85ee0747c693d00efb94d7625cc70a4a99557fcc4fa60ae2"},{"path":"/usr/share/zoneinfo/right/Pacific/Pago_Pago","mode":33188,"size":736,"sha256":"c996db6822af6b663b37e0c8750132432169950eed2c24bab4c9f843475b5cb5"},{"path":"/usr/share/zoneinfo/right/Pacific/Palau","mode":33188,"size":717,"sha256":"fa7e4882188f567514105374c59a5b95bf1c82bfa8216c52fc6f247d57a56cdf"},{"path":"/usr/share/zoneinfo/right/Pacific/Pitcairn","mode":33188,"size":758,"sha256":"05ab1d75088ddcaa01f819e2820a2e84285ee261c574e25f3a1f026f05d440a1"},{"path":"/usr/share/zoneinfo/right/Pacific/Pohnpei","mode":33188,"size":869,"sha256":"68eec56a56e1a4eed4d7cb732995e773a0d46f84c29c55875e24df333e6a6c27"},{"path":"/usr/share/zoneinfo/right/Pacific/Ponape","mode":33188,"size":869,"sha256":"68eec56a56e1a4eed4d7cb732995e773a0d46f84c29c55875e24df333e6a6c27"},{"path":"/usr/share/zoneinfo/right/Pacific/Port_Moresby","mode":33188,"size":723,"sha256":"627805f2b9bf76f41742808c227b3bfd443e2ef73e5eef7162616074aa97e41b"},{"path":"/usr/share/zoneinfo/right/Pacific/Rarotonga","mode":33188,"size":1137,"sha256":"2d1e4a68104638e75fb5cf82daf680d934f965e682e35a04ecc0e518d8f8a097"},{"path":"/usr/share/zoneinfo/right/Pacific/Saipan","mode":33188,"size":1065,"sha256":"2e85a11e3769f6576cc0131f7a59d3d145639f527548d59638086ae4b09a1d13"},{"path":"/usr/share/zoneinfo/right/Pacific/Samoa","mode":33188,"size":736,"sha256":"c996db6822af6b663b37e0c8750132432169950eed2c24bab4c9f843475b5cb5"},{"path":"/usr/share/zoneinfo/right/Pacific/Tahiti","mode":33188,"size":722,"sha256":"344408438702e718bca59faacbd552969b7397bdaf5aedf99e126f50c8233ee3"},{"path":"/usr/share/zoneinfo/right/Pacific/Tarawa","mode":33188,"size":701,"sha256":"f82a0f21667dce26d11673eef99db2d9200f915256c41289afb85689edce34f2"},{"path":"/usr/share/zoneinfo/right/Pacific/Tongatapu","mode":33188,"size":928,"sha256":"bbb8632d8f1d1a120c351694103ee55e7b45193c2aa9bcb5b65e99f8ffee424d"},{"path":"/usr/share/zoneinfo/right/Pacific/Truk","mode":33188,"size":831,"sha256":"9edef2327e3ea2e74d2eb9d2ce91dbfcc72ee9c46541cfd686f0eda9989942c1"},{"path":"/usr/share/zoneinfo/right/Pacific/Wake","mode":33188,"size":701,"sha256":"17180eb8fef967ac24d5492908cce1e90a7b4c578657fbddf0f60a2d832a7745"},{"path":"/usr/share/zoneinfo/right/Pacific/Wallis","mode":33188,"size":701,"sha256":"5fa9d027fcf24e4d9ad77875907d675144b7384bda0ddbedb03fbe44c09a63ab"},{"path":"/usr/share/zoneinfo/right/Pacific/Yap","mode":33188,"size":831,"sha256":"9edef2327e3ea2e74d2eb9d2ce91dbfcc72ee9c46541cfd686f0eda9989942c1"},{"path":"/usr/share/zoneinfo/right/Poland","mode":33188,"size":3245,"sha256":"2776052936d3361f49da479c0a6d522ea7ec256300cc9263d1011848ab2bb3a9"},{"path":"/usr/share/zoneinfo/right/Portugal","mode":33188,"size":4009,"sha256":"f8e850961fc42ea64edb30cebaabad27fccda97bdf6cf1047e4051298bdf20d0"},{"path":"/usr/share/zoneinfo/right/ROC","mode":33188,"size":1330,"sha256":"d5ff02c7a5dc9adb7a5b8de1e492f8ace92d832e8f2f6879265520c47f850078"},{"path":"/usr/share/zoneinfo/right/ROK","mode":33188,"size":1199,"sha256":"6c95b3eee50a28160e185e76e2bab6ec9f28f50e2d9a3166b20c4acfcf4aef1c"},{"path":"/usr/share/zoneinfo/right/Singapore","mode":33188,"size":959,"sha256":"91e407e2266fb1de8a5a90631744cd5b213f2521db783258f2f9f41697517dda"},{"path":"/usr/share/zoneinfo/right/Turkey","mode":33188,"size":2505,"sha256":"d0fd3d19c0e209595df3017696f8dc59d900be1dd6a3a8b354f7798ba6ce1f4d"},{"path":"/usr/share/zoneinfo/right/UCT","mode":33188,"size":667,"sha256":"d19fdd5d26a7753518ee9a09ab74a8e4efa9a4e6ed56eff85baabd8af9c0e459"},{"path":"/usr/share/zoneinfo/right/US/Alaska","mode":33188,"size":2920,"sha256":"b5b62f7337785e26117bbc34ef7976018f021e63eb3e208f8c752d4f949ef2ef"},{"path":"/usr/share/zoneinfo/right/US/Aleutian","mode":33188,"size":2905,"sha256":"6d3e31970fee36399f30950e3f68ce7a5038be38a64547241c2ac97daaccd994"},{"path":"/usr/share/zoneinfo/right/US/Arizona","mode":33188,"size":893,"sha256":"8a89f0e65cd0a0b2edbbf65a7a81441aa91073b133edac17c25c6c9f809b8995"},{"path":"/usr/share/zoneinfo/right/US/Central","mode":33188,"size":4125,"sha256":"94f71253caa6bde6db52f2f5ad3b816df0c2da9af7cc7d4a4abf1b91e391821f"},{"path":"/usr/share/zoneinfo/right/US/East-Indiana","mode":33188,"size":2215,"sha256":"7dfb7b2796f9b9d9a69d402b2e8269a2f834e1d01e2da34af490b2b24c21ace5"},{"path":"/usr/share/zoneinfo/right/US/Eastern","mode":33188,"size":4085,"sha256":"9699b3dbf1b5a2fe33cc0eeb1bae542d83608786c0b1872b07b24adda81556a1"},{"path":"/usr/share/zoneinfo/right/US/Hawaii","mode":33188,"size":878,"sha256":"93c484f1a3546cf33ee6bcbc52494b4e91d7c5d8d6dc9cc6a73751f8d8235cb3"},{"path":"/usr/share/zoneinfo/right/US/Indiana-Starke","mode":33188,"size":2977,"sha256":"ac4c928ad03acaf42f346aa81bf9d269a513adb14a955ff55a5177927832c6a8"},{"path":"/usr/share/zoneinfo/right/US/Michigan","mode":33188,"size":2784,"sha256":"5549176b1eddafbfea4f7156db3872560d9c7085e200706ca281103c7918d1dd"},{"path":"/usr/share/zoneinfo/right/US/Mountain","mode":33188,"size":2993,"sha256":"7448c66048e5489a28ecad3adc495351163e62cedff714bec6d15506a9e1f548"},{"path":"/usr/share/zoneinfo/right/US/Pacific","mode":33188,"size":3385,"sha256":"5f2a6fb2744e29e2a6ac88e89843ce0c74f8934b37d1b35d67e115d5363c9e57"},{"path":"/usr/share/zoneinfo/right/US/Pacific-New","mode":33188,"size":3385,"sha256":"5f2a6fb2744e29e2a6ac88e89843ce0c74f8934b37d1b35d67e115d5363c9e57"},{"path":"/usr/share/zoneinfo/right/US/Samoa","mode":33188,"size":736,"sha256":"c996db6822af6b663b37e0c8750132432169950eed2c24bab4c9f843475b5cb5"},{"path":"/usr/share/zoneinfo/right/UTC","mode":33188,"size":667,"sha256":"d19fdd5d26a7753518ee9a09ab74a8e4efa9a4e6ed56eff85baabd8af9c0e459"},{"path":"/usr/share/zoneinfo/right/Universal","mode":33188,"size":667,"sha256":"d19fdd5d26a7753518ee9a09ab74a8e4efa9a4e6ed56eff85baabd8af9c0e459"},{"path":"/usr/share/zoneinfo/right/W-SU","mode":33188,"size":2084,"sha256":"8e1367300579da7319742b25b9da707131b058482c77e7a707c71aeb60f067ff"},{"path":"/usr/share/zoneinfo/right/WET","mode":33188,"size":2413,"sha256":"e9826478fee66e6f8a7583d9a67d82f114f8a12856b4f4a6bfed5db540c54753"},{"path":"/usr/share/zoneinfo/right/Zulu","mode":33188,"size":667,"sha256":"d19fdd5d26a7753518ee9a09ab74a8e4efa9a4e6ed56eff85baabd8af9c0e459"},{"path":"/usr/share/zoneinfo/tzdata.zi","mode":33188,"size":111486,"sha256":"b926785d5e7510a13fb399a94af494a88c445ec57b74542f2f31bfdbc3ad8da5"},{"path":"/usr/share/zoneinfo/zone.tab","mode":33188,"size":19397,"sha256":"6e527397eeb52ddf95765a42790414758edeed0fee60ed01393114a3aa31433c"},{"path":"/usr/share/zoneinfo/zone1970.tab","mode":33188,"size":17911,"sha256":"d23af26ce4fe8b8c7bda465910956a850ddede07c5466d1b746cdcc5249466db"}]}},{"name":"util-linux","version":"2.32.1-22.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:util-linux:util-linux:2.32.1-22.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:util-linux:2.32.1-22.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/util-linux@0:2.32.1-22.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"util-linux","version":"2.32.1","epoch":0,"architecture":"x86_64","release":"22.el8","sourceRpm":"util-linux-2.32.1-22.el8.src.rpm","size":11560494,"license":"GPLv2 and GPLv2+ and LGPLv2+ and BSD with advertising and Public Domain","vendor":"CentOS","files":[{"path":"/etc/adjtime","mode":33188,"size":12,"sha256":"6aa92cacc25f30a7caacd8cf772d3626f5bd5b3a75ab2dc3e74a5119f56d12df"},{"path":"/etc/mtab","mode":41471,"size":19,"sha256":""},{"path":"/etc/pam.d/login","mode":33188,"size":715,"sha256":"83a11cc8be700a8e2ef107a15350a3f4f2253d554daf4f90149fbea823953cde"},{"path":"/etc/pam.d/remote","mode":33188,"size":640,"sha256":"dd90767b2883bfb2bee6c27acc794bcea58bf3436cc2180ccfca0e822b6c0145"},{"path":"/etc/pam.d/runuser","mode":33188,"size":143,"sha256":"2d430cb6628248953568010427d663f3305856f3cb055955c2239bea226c5280"},{"path":"/etc/pam.d/runuser-l","mode":33188,"size":138,"sha256":"be9329a8b26e3cfd4af879fe60900f646f8188f3fbe491688f23d4d8b491c5b1"},{"path":"/etc/pam.d/su","mode":33188,"size":566,"sha256":"6b08d1c3f556df6bf412834710f949e9adb6d6d566e850918e8f6eb18a5da96a"},{"path":"/etc/pam.d/su-l","mode":33188,"size":137,"sha256":"4d10241676e97e5e8d8935e5c8e8f6cb2f871afb881059715f155909be9ebd77"},{"path":"/usr/bin/cal","mode":33261,"size":67832,"sha256":"fb15b041a156c7dfee6dc780a4c414d233d3028bc1e03653abeb1ef02b4acd15"},{"path":"/usr/bin/chmem","mode":33261,"size":46776,"sha256":"95635f9f124dd1e66e7aea095888ed139d280793afbfef5022fdbabf102a670d"},{"path":"/usr/bin/chrt","mode":33261,"size":38288,"sha256":"2e6d724818c608584c0eb32f75a3b2c996804ce7df8efd4be6bfc8d11ddab54a"},{"path":"/usr/bin/col","mode":33261,"size":29936,"sha256":"3c06989a63e1b0ea770907c775582f2cb79f4a99b8c03ac856007f1e38c11140"},{"path":"/usr/bin/colcrt","mode":33261,"size":17000,"sha256":"b5511e5ba15439cc317b0b67f4d1166d95165b185f47873c6bceb4fc1f85f58d"},{"path":"/usr/bin/colrm","mode":33261,"size":25784,"sha256":"0fa4e5e1c44bc2b0158f5cb118cc0f5955eaf36a5b324afda996cfc3ec12072c"},{"path":"/usr/bin/column","mode":33261,"size":50872,"sha256":"84b239b853047de7d104dd3770230ae33fe056e4ded7d297fe385f2831bc8229"},{"path":"/usr/bin/dmesg","mode":33261,"size":80048,"sha256":"132aba4b0470e219c2ef33b89aad80eac208b94b73ee79fa78ac592870e8fd71"},{"path":"/usr/bin/eject","mode":33261,"size":59432,"sha256":"2b174d103ece8088346de88f39cf34eb8fb930df7ec489a56467c4d98ea1c113"},{"path":"/usr/bin/fallocate","mode":33261,"size":29896,"sha256":"323fd37c3c3ae679666a0619e569bd89a6be30cf54598d5d3ad6a66fcb2ef6e4"},{"path":"/usr/bin/fincore","mode":33261,"size":34064,"sha256":"8b1f58cd5568c42ec8dee03ae60d6315401d06100aae8ef48ddb51d25a5095ae"},{"path":"/usr/bin/findmnt","mode":33261,"size":68416,"sha256":"bb870afd72664d0bf66c893bf910ef3c8d5bfda68183bb96fd7dc4cff950673b"},{"path":"/usr/bin/flock","mode":33261,"size":34224,"sha256":"275d86af7c4fd407e3bcde0cda75879b5d4cc2e30f617695f9dde4d052f38bed"},{"path":"/usr/bin/getopt","mode":33261,"size":21144,"sha256":"a60bf62301737d7b93dc7be35854e31c634a03ab8012ad29bab809c680ce5e88"},{"path":"/usr/bin/hexdump","mode":33261,"size":59144,"sha256":"a67782f195ec81cf1f3bf9b0f7c1693291d7a5cca09e65c9415bcaf210b01cd7"},{"path":"/usr/bin/i386","mode":41471,"size":7,"sha256":""},{"path":"/usr/bin/ionice","mode":33261,"size":29912,"sha256":"22fe2a7e6e2b43bf09c6eafd556e5869d6d92dfe5a19a9bf5423ca3d6aff1e8c"},{"path":"/usr/bin/ipcmk","mode":33261,"size":30072,"sha256":"06ec78242bfb99cd9b5435e3dba4940b37be750f31f8ad01c3bee956b7f0851f"},{"path":"/usr/bin/ipcrm","mode":33261,"size":29936,"sha256":"b072b81e0e768fe62749a51d2a946fbad3745e20efb43cec5aa2a0a493a9ed28"},{"path":"/usr/bin/ipcs","mode":33261,"size":54912,"sha256":"24afbc9281ad0088ff3850a1166c70c1a3114236d3d2691ea565043406b64035"},{"path":"/usr/bin/isosize","mode":33261,"size":25784,"sha256":"2521681082478ae62d1a54c5dff90bc4b3fde8585da0f907be34122cab83af30"},{"path":"/usr/bin/kill","mode":33261,"size":38408,"sha256":"7b0cc7f489f851538b125c6c063fdb8dd2c1a889c4a321e47c151b443437e1c8"},{"path":"/usr/bin/last","mode":33261,"size":50720,"sha256":"d2afc7e0ac2f67c01ce525b17ace7f8d5f498d3b0625cffd43585742be66f92f"},{"path":"/usr/bin/lastb","mode":41471,"size":4,"sha256":""},{"path":"/usr/bin/linux32","mode":41471,"size":7,"sha256":""},{"path":"/usr/bin/linux64","mode":41471,"size":7,"sha256":""},{"path":"/usr/bin/logger","mode":33261,"size":51416,"sha256":"30edd2bdfcfd9fa61761ec104543e43f5cb093e56c176877f088c5748c08616c"},{"path":"/usr/bin/login","mode":33261,"size":42112,"sha256":"cc7eadd626a73d9dbea474490b3608649e59f54ae1513fa447605e5f419f80c2"},{"path":"/usr/bin/look","mode":33261,"size":16960,"sha256":"c8e4f7a950f5f4180906bfaf3786092fe48369d119960db260b9e2a8079721a4"},{"path":"/usr/bin/lsblk","mode":33261,"size":88416,"sha256":"4b22b0c7adea4b3df1d63643a79b09b129dff32a1ec3919ee6ac0d299ab1577b"},{"path":"/usr/bin/lscpu","mode":33261,"size":79736,"sha256":"45030cfe34661eda7730012e16274e9a1d1c449b508e85ad525e066b637e2815"},{"path":"/usr/bin/lsipc","mode":33261,"size":75768,"sha256":"fdd8e0d08183c587f19a478dfcc7846c67bd09953a2be0e3e927772d59676dce"},{"path":"/usr/bin/lslocks","mode":33261,"size":38648,"sha256":"5249f8e2d81465baddb70f66d73b090cc5a12cd97f09ce023bec72a3979310f9"},{"path":"/usr/bin/lslogins","mode":33261,"size":67472,"sha256":"a4d1552ce7b134e8ea43c961cec636987c43bbb0c3a25fa4b3095e063eca861e"},{"path":"/usr/bin/lsmem","mode":33261,"size":46632,"sha256":"9784c10ffd52e74112965e0fc0f6eed014a8390086bb7362d89163f29d5106d7"},{"path":"/usr/bin/lsns","mode":33261,"size":50712,"sha256":"daa96ce17588883c0a94b60cf2dfd9d3166ad9b6d55863d8a2a37904ee3ddcd9"},{"path":"/usr/bin/mcookie","mode":33261,"size":34280,"sha256":"4acb797ded644fbd5c4dc9fcefd22bec661c92204cfd11bf3b58c106f34596fb"},{"path":"/usr/bin/mesg","mode":33261,"size":12856,"sha256":"a072310e737a95db8a8fd52cd49a227d1075bf45df45f53b1786a5207b9c3ac4"},{"path":"/usr/bin/more","mode":33261,"size":46128,"sha256":"69fb3985dfe9b97fd37615759aa7f3450fc719c469385102e4579651529f58a8"},{"path":"/usr/bin/mount","mode":35309,"size":50576,"sha256":"22ce74001b1400ad650a98e6ddaa04965068e40be6638b46cf103575e65c2a84"},{"path":"/usr/bin/mountpoint","mode":33261,"size":16992,"sha256":"60705f40df6782d8acbc6deef80921acdb960ca9167ca44969c8825f40282df8"},{"path":"/usr/bin/namei","mode":33261,"size":34120,"sha256":"c2e4919561b4682beaa394f625dab72720072094a68a2d9e086fc1ae4a8d5b40"},{"path":"/usr/bin/nsenter","mode":33261,"size":34312,"sha256":"0049b8922cf11029dd612926f4bbb218844a61dbb678b6825ae1896054d01169"},{"path":"/usr/bin/prlimit","mode":33261,"size":38664,"sha256":"3c33870a9f0fe5f0e0d2d835706971da15d69aaae94753dbd0c95bd29e68627e"},{"path":"/usr/bin/raw","mode":33261,"size":17008,"sha256":"96303e8069774115f107240083f09e1434f8c07f3dab3f3824ec169ef0bfc229"},{"path":"/usr/bin/rename","mode":33261,"size":17008,"sha256":"4a3349dbbd584aad9a0e351590b35aa7ccdc26ffcf727790dd7a7b2ff557329e"},{"path":"/usr/bin/renice","mode":33261,"size":16976,"sha256":"6191cd3bb34dea859a333357d71fe53d369d58e71d0e5293e34d296ed965b8fb"},{"path":"/usr/bin/rev","mode":33261,"size":12864,"sha256":"871a70be117bf8b9387b6174ab79cbe179f51662ca0cd0ea46367f32a0d8f036"},{"path":"/usr/bin/script","mode":33261,"size":37976,"sha256":"9947c29047c680803c07fd46cb3f185acab685deaf8ba6e1f60e4364be34fb2a"},{"path":"/usr/bin/scriptreplay","mode":33261,"size":29912,"sha256":"f7b8ef8d4dcce145b7e34645ef286be74e992e7e0c3ce5444eee6ade0dc690ca"},{"path":"/usr/bin/setarch","mode":33261,"size":21376,"sha256":"58dbd99e3119b2c3f10e6b3561e4db791b41331bfa8b9856c66df0b62c05d686"},{"path":"/usr/bin/setpriv","mode":33261,"size":42280,"sha256":"fb457b1a25c772fb8346c372baa64fd16533885c8a36c7d08eb1b13601324f40"},{"path":"/usr/bin/setsid","mode":33261,"size":16952,"sha256":"2ada607b98e08e4a31b7e7342d4736971954fb0ebd3280c21683912b73a4316e"},{"path":"/usr/bin/setterm","mode":33261,"size":46424,"sha256":"43c3cc33585d8e24dfd2344b51e8087eb725407ff777a967ad576ae7cc25041b"},{"path":"/usr/bin/su","mode":35309,"size":50448,"sha256":"c2ea1c440e6270197c0ddde7135bff712a81ff66c4fc75d40203e015b0b732d3"},{"path":"/usr/bin/taskset","mode":33261,"size":38360,"sha256":"2dcde82bbba2413b9428ac5d9ddf85f48193175f284c8cf1f436219f6fb153d9"},{"path":"/usr/bin/ul","mode":33261,"size":21192,"sha256":"ddfbab36ef661beeecaf0a66239a480fccde6b3c02dce417f62607892b1e419a"},{"path":"/usr/bin/umount","mode":35309,"size":33760,"sha256":"a4999d2b34870698dca68a176fe11a9f474d69c4de0fa5e93faa01b149a203ae"},{"path":"/usr/bin/uname26","mode":41471,"size":7,"sha256":""},{"path":"/usr/bin/unshare","mode":33261,"size":25752,"sha256":"bf2b0e151e8f8511bde4c0c4e23cc553ea970a5056b99294a9b495151de31ad9"},{"path":"/usr/bin/utmpdump","mode":33261,"size":29608,"sha256":"2b86cddfd1db0ee3a97cf9d42e71ad57dd4d699a53fdc9f01f304f57a108f640"},{"path":"/usr/bin/uuidgen","mode":33261,"size":16960,"sha256":"c417fc638932c9fd73ad2b96c0dfbb2911f12437fc8510246da972c298dee50d"},{"path":"/usr/bin/uuidparse","mode":33261,"size":38256,"sha256":"2d99a312f4cc6a9727274c3ac205276aeee48762760f1608cb18587a1f44012c"},{"path":"/usr/bin/wall","mode":33261,"size":34080,"sha256":"a65c40f636801b2894ac6fb7d183b06016662637b15cfa705c2fb5aae77dfa5a"},{"path":"/usr/bin/wdctl","mode":33261,"size":38104,"sha256":"1048b042c241cb10deeb241be22ff586f55af0ca6d1fd52b40a6c300a771b9ff"},{"path":"/usr/bin/whereis","mode":33261,"size":30192,"sha256":"c2ca6c79f84d2a9662c1524a14d9539d3e7b0101a3c6c6894db193d4d0a39d16"},{"path":"/usr/bin/write","mode":34285,"size":21344,"sha256":"3d75e0cdfbcb33570fdf5c959c865f816c30ae9b26cdc57dae721ef1986d41a6"},{"path":"/usr/bin/x86_64","mode":41471,"size":7,"sha256":""},{"path":"/usr/lib/.build-id/04/0635750b4c70eb6d376dfdb63ca3634ed15a9a","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/04/157312a5545da718d2dff3d2fd5f533c84f217","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/08/5594fc25a814649fc5510d34685f54da5554e5","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/08/7fb8f8451347f5d61134513371ec918c34c705","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/09/0b63d3e6d29c0305cb34ee08f44e0dcd20fa36","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/0a/fd08df3668ac9535462ea97b2148cbe95a20d1","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/0c/35de143717d084a852cc65fc0d8aa01ed0efbb","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/13/13aface4167a737490741e044887ae456f0f42","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/13/9677591109d8138236b03fbdb9ff8c878f5dbc","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/19/b538a8031fd21bbe197bb4f6ae454cc04d10db","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/1a/c13747909cf00528801925803f63b72123136d","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/1b/36ded39d31fff8dd7ef279e0b6fe8d1d355567","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/1b/42218b37c4e90ddc3525eab2d2ff19bfc340d5","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/1b/6e4ea5087f69b622909a251f43e668b9779810","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/1b/cdc2e9989ce26a47afeaf409f099a045bd4777","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/1e/e51ae4a353850248545510118f275980ff4ed2","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/21/59e4f62d674fc817964a0fc388a66086c5857b","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/24/ebbe4371e01fe159eb044069da312d35ef78ea","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/2a/a337eb879cfbbd39ac1fa3c0b50471d766ced5","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/2c/170e5e4dcfa6915aedcaf61991f16b8b2eb35e","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/30/542f35f34b56b934208eb2f5dad3f183f5770b","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/33/64d6d848325bb9030fcf83690993f04afaf358","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/36/0429180e9d0e36c4bde47c8554acf1da13e09b","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/39/f5298dafcfaf115cb996df0e9949ab2b823640","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/3a/891c5fdc048fb980395a0e25a226faac29a65e","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/3b/693b4dbad20c5481a8d6d6047bd58259c75d68","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/3b/6b363221f18c97fc073fc4d71d5209fd96fe2e","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/3c/9be59a14fd8bff1bc7bbd1c8af58e8cde54248","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/3d/b7c8ac44808a28f9c955ad1bed79a7864aa791","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/42/e790b5cee64d19024125c4d7586ee175bcdb08","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/43/75e4977408bfbf873d34fd6af3f96cb14fd6bd","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/46/8a9d4d4a897397c8ab355463475faaa3daef18","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/48/e202535cb00d00b5780540fd80786365060364","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/4b/274e1b57f557cd7fe3c602717f0b5de90b5d32","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/4c/412448f256fb9dce4f96b4f5a2f28e29879a97","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/4e/040f2170b23b29d11809ad2d580cd70d8a821c","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/51/5ff602a1e3b0eb5df167f041d5d8125eaff781","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/56/1f124be43b9f1aea366ba0a972690a0a21755b","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/59/56e940b92022c6001409e1de7e33c16411ddea","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/5b/21d3cd196dc669d4f59ee78f9c429944a9e660","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/60/89d3e57e792c48829796dfa8f5c3b5df3d91a4","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/61/29e1ab7c4c9229b19cedae265548b6cdedf261","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/64/0e778122eb1a6aa63e17868e46a12ab8850cc7","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/66/5c84b64ac7698a1b2da3e6465fd01a0d6eb1df","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/67/58b4cd281449ab08996d1041a8c45e12f18a87","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/6f/22d9db1d3ae6b0e446fbb741d4a4adb94d8f12","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/6f/41cf4a349203d4db84cb5fbf637039e06c7c85","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/6f/529b73bb125ace728c3b4521171d90201e36c3","mode":41471,"size":30,"sha256":""},{"path":"/usr/lib/.build-id/73/1721043e76adc9bd5b0a33644da33b5ae1ec2f","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/74/07cbe21694282330110fa9445205c314868d23","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/7a/57e014e9a14925edfcc4a2a5929181dd63d78f","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/7c/36213e29d576003a02c49fdff1e441b21e244a","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/7d/732069b167252254af4cc48d1baa2c929feae2","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/7f/7a98ad8736cf52c6a3cab1fb12a5f9f4c3b3ab","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/80/0e2ad1ce20e40787cb0241e15a1d12df6a8264","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/84/dfdcb070500e3b33f113eb05056ffa11b0944c","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/8e/7bb208c09ad5e449a2647a66dc345c007533c6","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/91/1c644cb480de9f03bec13141d60c699022917b","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/92/b2ac6375a14617be6512ba19b1dd92bcf35a53","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/93/b4a647983d51bbea442d1030e5170703c88616","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/95/e2cd57b0ed4a89f6911cfad4c78b68d06731f9","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/97/fe8095b354646d15452340d8782db5aa976045","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/98/da68654df32b7041543fe35156209e6482e934","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/9b/130ff247543134ed947884aaa6d24d74c06552","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/a0/e9eecc9e8d0bac04b12c129b20bcc55ed58430","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/a1/de3f394caf28c8a0a5a4178330a709755aa15f","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/a2/90f2658b7af684c4ddd0ed473196993761a1ba","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/a4/b2a895f829c85d3ef32864adc74d6e1861b15a","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/a5/2592a113fd7c690c2cbb91bd984b3413c9fd63","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/a7/5d585c17134eaeef0de32e760e7443aabe2740","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/ab/3519ca5ccaa9bdd00379988b3cf3250203b2b9","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/ab/c2554439fd2748f167fa7ba0845d61cb4b9bff","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/ac/9c0f5f2f06758889834f986de8a392ae4a99ee","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/ad/6cecb46a5d92155f355afe315835fda90ef343","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/b5/1a5d225f52edabe92c88ef61cc5eaa6c6ba9e2","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/b7/0e70997395b378005bf4b209ed7e4a0467cfda","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/be/17c1b9c1cc758cee156eed7784d483ae716855","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/c0/6537f7238c9c1cd0c2c97ed35ad9cd1c31e7d5","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/c8/7db3d7ff52e28a3eb0d11a38536da5c648f09f","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/ca/8e1c4ed4f4f230061b684540612bdb2b967543","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/cb/15fe90fe3b5848aced0f3153242e6b1ea4f5e8","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/.build-id/cb/e2d58fd7744c9f814754449fb3808b136f351b","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/cd/e948cfb744eeb44762902a82726bf4ed080250","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/ce/58b412fd9c3fdc0bbb22676f74c413e5ddcf8b","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/d6/08b7d221892537e23e985b270aefd323b38688","mode":41471,"size":26,"sha256":""},{"path":"/usr/lib/.build-id/d6/1fdddcf02c3ac74fca5d3bf0c90f646c757c0a","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/d7/21de0011b1b582a6018cedbae65b96695d9671","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/db/63bc4ce8ed7f4c434dcd11126865f4cf17e6a9","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/.build-id/de/447c9cc40156e4fc18108629c718ee4539f11f","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/e4/13619c7bf610863dc3d0b6d4789174d6026fca","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/e4/bcf4e119371b3a438c353d19bbb6af6bcb2c02","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/e6/1108203dfef706ecc5d4e39b87bdfd44fb0dd0","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/.build-id/e7/3140cf808114d8f6f6ca061a07cef4ded721ee","mode":41471,"size":28,"sha256":""},{"path":"/usr/lib/.build-id/ec/8c3f30fa4603d145e435eab7f7f5eafc0e27bc","mode":41471,"size":24,"sha256":""},{"path":"/usr/lib/.build-id/ef/d582244167d6bcfb6afc2458099fe2cf6a7385","mode":41471,"size":29,"sha256":""},{"path":"/usr/lib/.build-id/f1/d727964ae59bad597325122e5db1537a4008d4","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/f4/7a37071a04010fd955655daea165dd5ffa4b5a","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/f6/a805334f64215d6ae53eaf80f8d02fc7e44449","mode":41471,"size":23,"sha256":""},{"path":"/usr/lib/.build-id/f7/4f0c6291c44b18af473da143daa31b8780f91c","mode":41471,"size":32,"sha256":""},{"path":"/usr/lib/.build-id/f7/96587a8686f3149bf29826d7054e74a90af632","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/f8/bdbe5ad4678962322c97cf32d2dbb9e04e0bed","mode":41471,"size":25,"sha256":""},{"path":"/usr/lib/.build-id/fb/0512fac5905514263acf054fa948ac7125d6f1","mode":41471,"size":27,"sha256":""},{"path":"/usr/lib/.build-id/ff/bffbac24f78b8d3b23ed8fa5fd35ca4746d619","mode":41471,"size":31,"sha256":""},{"path":"/usr/lib/systemd/system/fstrim.service","mode":33188,"size":96,"sha256":"45997a9848132cff9e480bf39da488729a8c4b4637565e179bf111d861c56857"},{"path":"/usr/lib/systemd/system/fstrim.timer","mode":33188,"size":170,"sha256":"c0207b760f12b3da601be9ffea48872bc446dcd295103563122c3b1eca0faeee"},{"path":"/usr/lib/udev/rules.d/60-raw.rules","mode":33188,"size":326,"sha256":"24a4525569d6417ef2dd04cf9ee5a32fd45b508f7bd87e64c12db249c3ce975a"},{"path":"/usr/sbin/addpart","mode":33261,"size":25464,"sha256":"3395b250e16bf9033a6a2544e2b7391b5a671e7e02fcfabf850d3954693c754f"},{"path":"/usr/sbin/agetty","mode":33261,"size":64056,"sha256":"d250c2051b86e8250f62928dd32be69421892b2bc0e661e8a7fad16ed0ceddf1"},{"path":"/usr/sbin/blkdiscard","mode":33261,"size":29992,"sha256":"fa3777829973e7a9d649dee8ef3d7e05386fcb4f68899a0ed8403b44d4943023"},{"path":"/usr/sbin/blkid","mode":33261,"size":97128,"sha256":"21b148626c64c3780d8256a1f81b731222680137d161aa1f81589bc7046c71b4"},{"path":"/usr/sbin/blkzone","mode":33261,"size":51176,"sha256":"41b6c8ec73a7714a348ebaf2801c7c4b71aafa11e0bf9fd0d11011b0667ec48a"},{"path":"/usr/sbin/blockdev","mode":33261,"size":42528,"sha256":"5274128aeb3b3b6c1c5aee53db002e9b27fdafb8903a9d8f0574c75a1c29cd70"},{"path":"/usr/sbin/cfdisk","mode":33261,"size":101016,"sha256":"8e47ca8aae6f9a7bf99baa7c622923884f489587b1e8d13aa03c72d052238404"},{"path":"/usr/sbin/chcpu","mode":33261,"size":29744,"sha256":"d7ca24d98fd41757e1759f308e06b75b3e941742975151e59d56492accd7aea4"},{"path":"/usr/sbin/clock","mode":41471,"size":7,"sha256":""},{"path":"/usr/sbin/ctrlaltdel","mode":33261,"size":21512,"sha256":"5c060f4eedd742a295a81bb5772bfb51f0b7641e7538443e9af089705c3caace"},{"path":"/usr/sbin/delpart","mode":33261,"size":25456,"sha256":"14c6bf46fcac826c3334658f739deb8f788ec69845293a98415a399695c3859b"},{"path":"/usr/sbin/fdformat","mode":33261,"size":34200,"sha256":"c85e6b28801e456bea841752514cb36f8c118f17b6e86a8e6b29607e62197433"},{"path":"/usr/sbin/fdisk","mode":33261,"size":134288,"sha256":"91933238fa8f82f22db9948a52d1ac276f50edbcbb1c27194c04313a644aad4c"},{"path":"/usr/sbin/findfs","mode":33261,"size":12856,"sha256":"b93ec3566cf3cd8eba35f262df5fbf7f01ddddfa08f6be964e6b69c48e85b309"},{"path":"/usr/sbin/fsck","mode":33261,"size":54984,"sha256":"12cc2c212a202f7ef16bc73f85f35897b32bd65cb1ea60fbb0a60cc053dc9f69"},{"path":"/usr/sbin/fsck.cramfs","mode":33261,"size":42608,"sha256":"9572a45ad6c25d890272eee0684f656a3ad775e8b68d6eec7e25d089d4fe9b1f"},{"path":"/usr/sbin/fsck.minix","mode":33261,"size":101368,"sha256":"9f92901b2424a329becb4e922faaaff8865ea1b1b79b65327d0d2620dfdd3218"},{"path":"/usr/sbin/fsfreeze","mode":33261,"size":16968,"sha256":"5123eee6a4c9bcc96aa33855982260bf8fe7e13ad54fe577afcf0d414ce0e2b3"},{"path":"/usr/sbin/fstrim","mode":33261,"size":46928,"sha256":"974976a8181ad5fe97053ca720a30fdb242792e4bc009c2a3bf06666186c1454"},{"path":"/usr/sbin/hwclock","mode":33261,"size":67040,"sha256":"9de8cad9bbe73911bc924786340cfd6fc45fbf880b85cfcddf042f2b518b1a0d"},{"path":"/usr/sbin/ldattach","mode":33261,"size":34016,"sha256":"a69326b27f79a9003e644367eab25ed0e2205bfb8d61ae28b8b7c111f7952de7"},{"path":"/usr/sbin/losetup","mode":33261,"size":92984,"sha256":"d1922fc3df6265cb4821dbb3f7aa66f37ae51ba40ae153835bf316d861056119"},{"path":"/usr/sbin/mkfs","mode":33261,"size":17000,"sha256":"59696ac618c834f53dc7b937d99b66b55e19c9b04d177089bc7e5cd2719c7674"},{"path":"/usr/sbin/mkfs.cramfs","mode":33261,"size":42488,"sha256":"0a9fe2e88a1013c1f32d0804b01154a4c1a12bbca8ed228826a15477166c9641"},{"path":"/usr/sbin/mkfs.minix","mode":33261,"size":88840,"sha256":"1d19a7a62b92eef565be2e3553a51a5ef4bac2ddc262c579fa96002136623c3e"},{"path":"/usr/sbin/mkswap","mode":33261,"size":88744,"sha256":"a409bf7d87ae7325e13ac9dc25a761ed9a01b2c27424186cb34b7a9fe711ec50"},{"path":"/usr/sbin/nologin","mode":33261,"size":12272,"sha256":"6415f5ee2a3087b95685016e3d5abeb6ea1e151157722f1ef5c9c1237649a166"},{"path":"/usr/sbin/partx","mode":33261,"size":92880,"sha256":"d61a031ac6d543a4eced3e080f683dd590778bc06822fe660bc2bf38272eac81"},{"path":"/usr/sbin/pivot_root","mode":33261,"size":12864,"sha256":"dd5261ffeeb4c7d92d1fbfd27c71effc306e6d32c7d05045e33da35d5aa55f4d"},{"path":"/usr/sbin/readprofile","mode":33261,"size":21160,"sha256":"3a33e16d3fce10d3449d23d000a303c5c46223f80d7e2027361481f02e98b1c4"},{"path":"/usr/sbin/resizepart","mode":33261,"size":42800,"sha256":"169250d5989af6b66cb921c3e41340c883ee75bf31668e9a279779cca462f19b"},{"path":"/usr/sbin/rfkill","mode":33261,"size":55048,"sha256":"ad38aea87c5fbf24546cf5010d75b505b8b35b99ee4855ae8314f89d66e6d22a"},{"path":"/usr/sbin/rtcwake","mode":33261,"size":50752,"sha256":"972a4df2c82d13f6e609978473744e05e90f9fdcd2b83e3c51c12c1a1f402745"},{"path":"/usr/sbin/runuser","mode":33261,"size":50448,"sha256":"1ab05f0d04b85020ba1dce214f393c4bcc98a353dfabca894dbb64f3e3ceb7a8"},{"path":"/usr/sbin/sfdisk","mode":33261,"size":121624,"sha256":"df6e2d7904079ac497a6d2c112669c16a1050815671f5c07db9743a965ab3d26"},{"path":"/usr/sbin/sulogin","mode":33261,"size":51080,"sha256":"0991bb31721e06b3bc9af26fb515d967767e8c565c0ac7201f6b6f0d169c7dd5"},{"path":"/usr/sbin/swaplabel","mode":33261,"size":17216,"sha256":"58a4d90649e24c6dbec9b7967e212e743f535a460655226a6a3900ecc93c24cb"},{"path":"/usr/sbin/swapoff","mode":33261,"size":21480,"sha256":"9230f2dc7360fd4d517fe407f29b206a8877b47da4db7c7ccb4263558e869d70"},{"path":"/usr/sbin/swapon","mode":33261,"size":50800,"sha256":"06330ada7a841831bdf0127b94cf010779796f3640a6a4f950e3e471a55a4e96"},{"path":"/usr/sbin/switch_root","mode":33261,"size":17008,"sha256":"0b1f83dfa43449084fd69393ae8c0176cfeaa17ba64abe2a6471916e6b9706b7"},{"path":"/usr/sbin/wipefs","mode":33261,"size":42368,"sha256":"5739a1afdb5eb4ce00cfb1382e90265bb6457bd018d9bf3b9a16a7192ad00cb3"},{"path":"/usr/sbin/zramctl","mode":33261,"size":101688,"sha256":"13397ba03beedea251420700db89005d4c5ae63cee3af7840d644d0c583b8b7a"},{"path":"/usr/share/bash-completion/completions/addpart","mode":33188,"size":447,"sha256":"61badc8851eb6f1c153df1a07c9c2f3bffa048fbd05d1ef775384087440a08c8"},{"path":"/usr/share/bash-completion/completions/blkdiscard","mode":33188,"size":639,"sha256":"52ae5cec0990942b3e239d9bae331ea237d6dd457575746e382d07fbabf9ad70"},{"path":"/usr/share/bash-completion/completions/blkid","mode":33188,"size":2094,"sha256":"f4ec23b0db103c742d655c8e9dbbe3e2d59f1b711abe6a241c91a8211895e624"},{"path":"/usr/share/bash-completion/completions/blkzone","mode":33188,"size":971,"sha256":"bf20f342237b951779fb457d68cc4bc7900e6db044becb5419efa109b77ffadf"},{"path":"/usr/share/bash-completion/completions/blockdev","mode":33188,"size":726,"sha256":"0e33e84094c213cca2fc2e3ea06efc4a655ef4bb27ae4126943c574b98709767"},{"path":"/usr/share/bash-completion/completions/cal","mode":33188,"size":426,"sha256":"ba7d43682f8dd8eee55591d451aa0b4380e1cd01eb887a91528dbbb9187ed14d"},{"path":"/usr/share/bash-completion/completions/cfdisk","mode":33188,"size":546,"sha256":"2995b77066141f0a0b67dec82d554a20909466eca6a3e8f237eb709b7f5b4c62"},{"path":"/usr/share/bash-completion/completions/chcpu","mode":33188,"size":1510,"sha256":"a33736eafd741e7929ab8c13d1484f19a0874fb5a220dac8c6e4e7d3b2dc6458"},{"path":"/usr/share/bash-completion/completions/chmem","mode":33188,"size":501,"sha256":"6bb1f0dbb7af9f2891badb28f90e7ab9b82647a4b982a284b541968f669f2a9f"},{"path":"/usr/share/bash-completion/completions/chrt","mode":33188,"size":920,"sha256":"1dd13080d71c8d880e628eee89e8f493c979441692ef364e01ca8c8a761d381e"},{"path":"/usr/share/bash-completion/completions/col","mode":33188,"size":460,"sha256":"4d3265f8264768dde09b2962b2b19f1dd23b5283430b64b762d24515dee93cc8"},{"path":"/usr/share/bash-completion/completions/colcrt","mode":33188,"size":484,"sha256":"cfaecdd8f38c8fd02a9a6fe9685dde62da40bafd69412d0da67cfa86af3443e6"},{"path":"/usr/share/bash-completion/completions/colrm","mode":33188,"size":509,"sha256":"0189319a7ac414b0777557a29e5c6ddd32ec3a4db494eea31c193bdf80add723"},{"path":"/usr/share/bash-completion/completions/column","mode":33188,"size":725,"sha256":"232d82bb405518558eece4c5a0889502a5df776b6db7e1e2c9f0c0cb98238955"},{"path":"/usr/share/bash-completion/completions/ctrlaltdel","mode":33188,"size":335,"sha256":"52021091a5554e9b6275cdabbf1820ccd18eff38d8b0094284ef7fb68c38f66f"},{"path":"/usr/share/bash-completion/completions/delpart","mode":33188,"size":526,"sha256":"e337b3898cacda9485085c522d9306a043146cc52c780bbcf2c65b8d366f095a"},{"path":"/usr/share/bash-completion/completions/dmesg","mode":33188,"size":1182,"sha256":"5cd7dd59ef1558c7d5bf8fe58581eb6b173f823b21f1e83598328de2d7695060"},{"path":"/usr/share/bash-completion/completions/eject","mode":33188,"size":1189,"sha256":"3023989370b39ed06207f18a9581de1d9d60482024e2c86135df22459559a410"},{"path":"/usr/share/bash-completion/completions/fallocate","mode":33188,"size":721,"sha256":"f775a5a4e4d051193cfc5dbcc2ba373d5cfe350604f3c4b79372ef4a7e494f02"},{"path":"/usr/share/bash-completion/completions/fdformat","mode":33188,"size":566,"sha256":"d1478a7f29aa6e2ac647acb10a2b1036bf2e2cb98e9627abb43fb1bf6ac561ec"},{"path":"/usr/share/bash-completion/completions/fdisk","mode":33188,"size":1834,"sha256":"2eddd6f947b6246d18959c173aac7112e1e9b2d523ffe852f88011dd2e4836c6"},{"path":"/usr/share/bash-completion/completions/fincore","mode":33188,"size":916,"sha256":"0d66d90486e2f0b6eee9a962adc762cd19f7311b42d344cf47e49ef1261f90e4"},{"path":"/usr/share/bash-completion/completions/findfs","mode":33188,"size":695,"sha256":"ff73ffe3f15cc6ec0bfeed0a2c87b67eb1c9890ec5e7a23d18eab733d16c0df8"},{"path":"/usr/share/bash-completion/completions/findmnt","mode":33188,"size":3154,"sha256":"e7b2684e430a5b9f71ff766866ccd63c1358b568efc6fbdfcbaa4bed35b3ae30"},{"path":"/usr/share/bash-completion/completions/flock","mode":33188,"size":874,"sha256":"4ea2ecf934319c37348fddefdf0f028614ce04cc1840574242bf47219cb0a8c8"},{"path":"/usr/share/bash-completion/completions/fsck","mode":33188,"size":787,"sha256":"feb2b95abe8caac7840120e9575816d9e02dc8d08fe883293211f6f88389dfd8"},{"path":"/usr/share/bash-completion/completions/fsck.cramfs","mode":33188,"size":684,"sha256":"74f9052c2e8991509621e742d39b65beb9489deef2b2b1f7a443f05acf11db46"},{"path":"/usr/share/bash-completion/completions/fsck.minix","mode":33188,"size":383,"sha256":"c80e2696bcb4fb7642418d3aec96f7c2931cdcfdaf245786ee3b6cded99e22fe"},{"path":"/usr/share/bash-completion/completions/fsfreeze","mode":33188,"size":524,"sha256":"7f99f914f660697f78e57850e4e70c027e73a0aa5074a28bd3a5d25c2564b371"},{"path":"/usr/share/bash-completion/completions/fstrim","mode":33188,"size":677,"sha256":"9c36b670fa1b23811490e2b47b6576a4b58f38ded511ed4f3757e7b858e3700e"},{"path":"/usr/share/bash-completion/completions/getopt","mode":33188,"size":815,"sha256":"0ae50ed789c556f2abdabe09362169d385f9facf1bd05c13cf57b3f8e0078a5d"},{"path":"/usr/share/bash-completion/completions/hexdump","mode":33188,"size":1007,"sha256":"4bcab470cac90909b105e525171e7bc0ad8fc60b0d98503f4d46dfad8060cf9e"},{"path":"/usr/share/bash-completion/completions/hwclock","mode":33188,"size":938,"sha256":"3f29aca0683c4b66ee099eb32cbbe0763965ba0de7b5e1d67efbf23db7f93fdd"},{"path":"/usr/share/bash-completion/completions/ionice","mode":33188,"size":1161,"sha256":"8a92b4a98b89f6c3af9baf94aab2cc24f58e0e2c4ffc6e2ea822cdc093d940ff"},{"path":"/usr/share/bash-completion/completions/ipcmk","mode":33188,"size":576,"sha256":"701db74a1133159cf159c9a182a46eb77ecdab618c52e373f432b3924d8e2707"},{"path":"/usr/share/bash-completion/completions/ipcrm","mode":33188,"size":1423,"sha256":"454731bfb20b7be1e41f5b0704536a549ebf7ee755d64bd9ef882b04ae84173d"},{"path":"/usr/share/bash-completion/completions/ipcs","mode":33188,"size":514,"sha256":"c8d2fc0706082e013fdec16a7b7fcc3aadbc0c3e22f87d8a818d9aa95f364acf"},{"path":"/usr/share/bash-completion/completions/isosize","mode":33188,"size":529,"sha256":"0afdd61db90044908eef15ef623eb9e6f4598cdfe581f20b1b812650d961f567"},{"path":"/usr/share/bash-completion/completions/last","mode":33188,"size":949,"sha256":"406ba6772a881f22d10cad9096093673513c8426e81594c44977e1a57e7c4724"},{"path":"/usr/share/bash-completion/completions/ldattach","mode":33188,"size":1472,"sha256":"f2a5396940e79dbdeea768970b2960d067e8a2fb78e9379a1b1b0fa250906595"},{"path":"/usr/share/bash-completion/completions/logger","mode":33188,"size":1553,"sha256":"20a52821ce9e70f58e72f9050e3037aba96986aa39403a7b36bf5fac3de1b2c5"},{"path":"/usr/share/bash-completion/completions/look","mode":33188,"size":683,"sha256":"9266652a2153e29fc80a3716fb3efbddff33a33590eaa20773d0b694e3daf554"},{"path":"/usr/share/bash-completion/completions/losetup","mode":33188,"size":1721,"sha256":"d303360015af85fb1e174b2baded89ee18e4b492e86b4923e9a4d435be03af71"},{"path":"/usr/share/bash-completion/completions/lsblk","mode":33188,"size":1961,"sha256":"32a935615aed4a5f444fbdf1da8364160390bed9eaa4d109515a8269432a01a1"},{"path":"/usr/share/bash-completion/completions/lscpu","mode":33188,"size":1018,"sha256":"2e33c9fd36591d62f19ff4ff4ce1bf4c839dbe6e9445dcd19d7ff16945dadcfe"},{"path":"/usr/share/bash-completion/completions/lsipc","mode":33188,"size":1310,"sha256":"650711cc8c467b10fc463a333d3bba815810ae9cc1dd8b5c8bc0181b9721df82"},{"path":"/usr/share/bash-completion/completions/lslocks","mode":33188,"size":1069,"sha256":"6d06600296ca5b2c343d602e6d8d7680941c9ca29baa79137cf0d9cdaab73b85"},{"path":"/usr/share/bash-completion/completions/lslogins","mode":33188,"size":1704,"sha256":"713c0e99482efd5139818e6f2a3383db05a6b6f9ae2356ab7f6578e95e3c8eb7"},{"path":"/usr/share/bash-completion/completions/lsmem","mode":33188,"size":1054,"sha256":"efaef7d643aaf1e461124891e8799c0415764d0c3b5f1663ee73f1c0d7defac1"},{"path":"/usr/share/bash-completion/completions/lsns","mode":33188,"size":1167,"sha256":"c5daf627bd51f6e97d44f9f905c98b1c3023aaffc12fcd36802636b2872cda1a"},{"path":"/usr/share/bash-completion/completions/mcookie","mode":33188,"size":599,"sha256":"c1460f2f78f58e0195f4dc3af4a5e92925aa23f3f6ec5c73a7565329a7eb8b3b"},{"path":"/usr/share/bash-completion/completions/mesg","mode":33188,"size":412,"sha256":"67d09288e327f405fa72009d7e85b81a70d20c5577ffb8b418b6b0de043e7fc1"},{"path":"/usr/share/bash-completion/completions/mkfs","mode":33188,"size":638,"sha256":"b90a36595a7585f33e27d5028c66fecb8db2f01832240b70527aa93f9d93c486"},{"path":"/usr/share/bash-completion/completions/mkfs.cramfs","mode":33188,"size":821,"sha256":"a33449ad64a9c1e51ad0b82fc6afbb07febd5650842fea214231f399d7f3bf4d"},{"path":"/usr/share/bash-completion/completions/mkfs.minix","mode":33188,"size":714,"sha256":"aa873021ae3d172211a649626f466efd53423970ba15d29d6f5ce4fc5d78fcc9"},{"path":"/usr/share/bash-completion/completions/mkswap","mode":33188,"size":841,"sha256":"e1cf77f54f0bd20cc47638b163a4b4adab20f4901ff4ef296cd2a9e3ebbb6577"},{"path":"/usr/share/bash-completion/completions/more","mode":33188,"size":528,"sha256":"f2a14123adff1db7144fa503b2e939d9383055e7b893a7730e146dd93c328032"},{"path":"/usr/share/bash-completion/completions/mountpoint","mode":33188,"size":487,"sha256":"4b9350fe71eac2b6927a0e0ea228c4d5d809d96320c0c2db233af2c6e522ae94"},{"path":"/usr/share/bash-completion/completions/namei","mode":33188,"size":500,"sha256":"1519a1b96f840f476647daa9d041a7d5db2dde0d80d3c99e973b1eccff8b259d"},{"path":"/usr/share/bash-completion/completions/nsenter","mode":33188,"size":1171,"sha256":"c60762eff4f9768cda50c4e719c869ad6f2d9396f48c3bd4cb6c5bb90e847a3b"},{"path":"/usr/share/bash-completion/completions/partx","mode":33188,"size":1249,"sha256":"f484caf21d33bef1f03dd3b6244295774565dcc516bef24718e4e07d8fad6662"},{"path":"/usr/share/bash-completion/completions/pivot_root","mode":33188,"size":387,"sha256":"e3fd2fed08fe53b1bdf0b344633375273ce54bdb75c65a4383f2bf29aa9868dd"},{"path":"/usr/share/bash-completion/completions/prlimit","mode":33188,"size":1329,"sha256":"feb868f23ea5c5833a4fc9a642b78a83dd186259826304be649e7902086b8f9f"},{"path":"/usr/share/bash-completion/completions/raw","mode":33188,"size":482,"sha256":"f546700af22030dffeefaa6b13e9ebb7c24538adb0941dcb98a9d68a6426640f"},{"path":"/usr/share/bash-completion/completions/readprofile","mode":33188,"size":679,"sha256":"874cf09268bc51c0dd77267ef8e3d9948ff9c8c376a1b9ce911ca135b7baf9a5"},{"path":"/usr/share/bash-completion/completions/rename","mode":33188,"size":655,"sha256":"d540f591b0a59ce27b14cb151f6b110a3dbba6c006052c0501a69fc9140e0938"},{"path":"/usr/share/bash-completion/completions/renice","mode":33188,"size":784,"sha256":"6fdf113c8a43356f2bddaff1613e3f66679f5f0b64d061a30e474f146163569b"},{"path":"/usr/share/bash-completion/completions/resizepart","mode":33188,"size":568,"sha256":"e0692d25787a3625816b07ea00ef66cfeada23fff0016cf0a37efd95ad84b0d5"},{"path":"/usr/share/bash-completion/completions/rev","mode":33188,"size":432,"sha256":"ffab4735212694543267952b527e72f3ee4ac9b0e07d49b432db219bd26a3aae"},{"path":"/usr/share/bash-completion/completions/rfkill","mode":33188,"size":929,"sha256":"98738ba429e47a0a99b9fa3f805eeed2a9f6b42ce43654b2656d51282d2a5087"},{"path":"/usr/share/bash-completion/completions/rtcwake","mode":33188,"size":1081,"sha256":"00d17c7f0f1d58372d1687ddc0004c0758818bc845de2caf1ec65435297b8a9b"},{"path":"/usr/share/bash-completion/completions/runuser","mode":41471,"size":2,"sha256":""},{"path":"/usr/share/bash-completion/completions/script","mode":33188,"size":667,"sha256":"4939f89fc4e6fb5577b1803562c103d8ee43648f1f87a938c6c79a67e5850492"},{"path":"/usr/share/bash-completion/completions/scriptreplay","mode":33188,"size":625,"sha256":"58d1c51c587e26dec022c31a4beaac423f4157b858a35a28dd6d3b4575f1111f"},{"path":"/usr/share/bash-completion/completions/setarch","mode":33188,"size":790,"sha256":"bccea2e0e6fd329c9614c4c04f09093de21ba76595ef093bd70027df28bda533"},{"path":"/usr/share/bash-completion/completions/setpriv","mode":33188,"size":2370,"sha256":"365faac5d98c05818a891f70f487e9d00ad761c4ad383362cadfe8ce3c7bbc53"},{"path":"/usr/share/bash-completion/completions/setsid","mode":33188,"size":440,"sha256":"376e5ac5d2a289c03bf36a8f9a86ae160cffc6693112043bf33d2d4f99614c30"},{"path":"/usr/share/bash-completion/completions/setterm","mode":33188,"size":2591,"sha256":"19ba4c6271e87a588517a67d2c02aae0683b2ab45c047784200e6a435da9248f"},{"path":"/usr/share/bash-completion/completions/sfdisk","mode":33188,"size":2012,"sha256":"37d03e1a9db3c6d7539b46ac99395811c6d33a00c33ad400abff2765e0618bcc"},{"path":"/usr/share/bash-completion/completions/su","mode":33188,"size":864,"sha256":"cfd2d8d2f8c11b25c9c9810aeb1ce2817c17e252a8d0f1e9ee0502cf24008e75"},{"path":"/usr/share/bash-completion/completions/swaplabel","mode":33188,"size":635,"sha256":"1805b9fa1953570fa4bb99339afbb25a6d701ce5a442d22b8ddabe486b46c9c9"},{"path":"/usr/share/bash-completion/completions/swapoff","mode":33188,"size":743,"sha256":"e84478bfbcfb4eb0accf290e7b158085cb0db7f679afade1a270f7e1e731a691"},{"path":"/usr/share/bash-completion/completions/swapon","mode":33188,"size":1529,"sha256":"afe600410af52c122572674bc127d1f21361c9ca457e22dcdb3ffee6ff837ea2"},{"path":"/usr/share/bash-completion/completions/taskset","mode":33188,"size":1207,"sha256":"f1b19ebab71cfd5b7b3082a3ecc59a319f8b14fd90eaf5ce9576a965d89f2907"},{"path":"/usr/share/bash-completion/completions/ul","mode":33188,"size":655,"sha256":"dbf03fa8a7f4e7213f709a811cf2015f4f87f35d5b21a35852c4c5e66d6489b3"},{"path":"/usr/share/bash-completion/completions/unshare","mode":33188,"size":809,"sha256":"716ea1e75c1f6d2bb3480863ccb9f145a222dee237f766901083fc3f0b884644"},{"path":"/usr/share/bash-completion/completions/utmpdump","mode":33188,"size":475,"sha256":"69a8a5a630ce32790499b7690d033c7d73c40c861a5985ca23c4f1585fd69b48"},{"path":"/usr/share/bash-completion/completions/uuidgen","mode":33188,"size":657,"sha256":"d64e54868b437b24aa682bc015f7761fedfe39badf1904691ba1c91035ac9dec"},{"path":"/usr/share/bash-completion/completions/uuidparse","mode":33188,"size":727,"sha256":"c4c0086a5c5b0e45a7c1880a818d6ae7f99fe074c6507ab0c2f1a1149781012d"},{"path":"/usr/share/bash-completion/completions/wall","mode":33188,"size":634,"sha256":"bc527b9f476ec852921e2cbbc9fbfc2ecc4c1677c58103fb88678e25e11528a1"},{"path":"/usr/share/bash-completion/completions/wdctl","mode":33188,"size":1371,"sha256":"d2c3148ba44506574ddfa4cb939d91bd99e8e83b73fbe36119cdba9452e68401"},{"path":"/usr/share/bash-completion/completions/whereis","mode":33188,"size":535,"sha256":"2a040afc44337e73ffcb2b910180aacf09566b784f887e82255a09cc42689d50"},{"path":"/usr/share/bash-completion/completions/wipefs","mode":33188,"size":1192,"sha256":"3850447cb9c3d7e2f2a99f556b88d944cb9b15be6fe9a0d9699ee62242b19412"},{"path":"/usr/share/bash-completion/completions/write","mode":33188,"size":431,"sha256":"f6543a2cbd41ff073f81159a4a5dde495a8dc886a4625fa019a41f93bbec6ce1"},{"path":"/usr/share/bash-completion/completions/zramctl","mode":33188,"size":1273,"sha256":"c5acddf27c9aecf868a9f63cf2f6927ea0235b653198bfc311a629402cbd5ac4"},{"path":"/usr/share/licenses/util-linux/COPYING.BSD-3","mode":33188,"size":1391,"sha256":"9b718a9460fed5952466421235bc79eb49d4e9eacc920d7a9dd6285ab8fd6c6d"},{"path":"/usr/share/licenses/util-linux/COPYING.GPLv2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"},{"path":"/usr/share/licenses/util-linux/COPYING.ISC","mode":33188,"size":697,"sha256":"e53348ce276358e9997014071c5294b36a18c4b34f32f00ee57b9acce0aafd63"},{"path":"/usr/share/licenses/util-linux/COPYING.LGPLv2.1","mode":33188,"size":26530,"sha256":"dc626520dcd53a22f727af3ee42c770e56c97a64fe3adb063799d8ab032fe551"},{"path":"/usr/share/licenses/util-linux/COPYING.UCB","mode":33188,"size":1824,"sha256":"ba7640f00d93e72e92b94b9d71f25ec53bac2f1682f5c4adcccb0018359f60f8"},{"path":"/var/log/lastlog","mode":33204,"size":0,"sha256":""}]}},{"name":"vim-minimal","version":"8.0.1763-13.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:vim-minimal:vim-minimal:8.0.1763-13.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:vim-minimal:8.0.1763-13.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/vim-minimal@2:8.0.1763-13.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"vim-minimal","version":"8.0.1763","epoch":2,"architecture":"x86_64","release":"13.el8","sourceRpm":"vim-8.0.1763-13.el8.src.rpm","size":1420484,"license":"Vim and MIT","vendor":"CentOS","files":[{"path":"/etc/virc","mode":33188,"size":1204,"sha256":"8a94ac63b055207d9fdac097cb4c590d9c5f8fd6d0b1ecdaed5e122ad1cb7d25"},{"path":"/usr/bin/ex","mode":41471,"size":2,"sha256":""},{"path":"/usr/bin/rvi","mode":41471,"size":2,"sha256":""},{"path":"/usr/bin/rview","mode":41471,"size":2,"sha256":""},{"path":"/usr/bin/vi","mode":33261,"size":1413696,"sha256":"956a8911e8eff7fae6871506f26763f26b27c9baa6beed4d1c0702fc613022ba"},{"path":"/usr/bin/view","mode":41471,"size":2,"sha256":""},{"path":"/usr/lib/.build-id/47/5d7ca18267be75ce9b002d0c3be9ba7065aeda","mode":41471,"size":22,"sha256":""}]}},{"name":"xz","version":"5.2.4-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:xz:xz:5.2.4-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:xz:5.2.4-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/xz@0:5.2.4-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"xz","version":"5.2.4","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"xz-5.2.4-3.el8.src.rpm","size":432832,"license":"GPLv2+ and Public Domain","vendor":"CentOS","files":[{"path":"/etc/profile.d/colorxzgrep.csh","mode":33188,"size":162,"sha256":"67e78cc79449a9eacb0be5bfe833f443508bc5602ce81af1847f20f0be1de25a"},{"path":"/etc/profile.d/colorxzgrep.sh","mode":33188,"size":183,"sha256":"0446ca350ab8205a36deeab4c39413a87ea8b61588fe8385658c1083aad8fa3f"},{"path":"/usr/bin/unxz","mode":41471,"size":2,"sha256":""},{"path":"/usr/bin/xz","mode":33261,"size":91432,"sha256":"dd57ef03bc26e855f8290cfca3febd57aa55afa43acdcf50eb9ddcd52a5696aa"},{"path":"/usr/bin/xzcat","mode":41471,"size":2,"sha256":""},{"path":"/usr/bin/xzcmp","mode":41471,"size":6,"sha256":""},{"path":"/usr/bin/xzdec","mode":33261,"size":18376,"sha256":"dae172b90afc082b8d5ea4dc69c771c4f46dc4b7c12f84decf67d378a276ad2c"},{"path":"/usr/bin/xzdiff","mode":33261,"size":6632,"sha256":"78de84e66db69fb76488031b9760567d27bea09cb6a411cb494d914cb96ea53e"},{"path":"/usr/bin/xzegrep","mode":41471,"size":6,"sha256":""},{"path":"/usr/bin/xzfgrep","mode":41471,"size":6,"sha256":""},{"path":"/usr/bin/xzgrep","mode":33261,"size":5628,"sha256":"fbb4431fbf461d43c8a8473d8afd461a3a64c5dc6d3a35dd0b15dca2253ec4e9"},{"path":"/usr/bin/xzless","mode":33261,"size":1802,"sha256":"88046aad2ff0b9507e746278ce5bd1222ccf80f9765a9629463f5119cc459c1f"},{"path":"/usr/bin/xzmore","mode":33261,"size":2161,"sha256":"6ee498368573c3a6c56e45e76cd4374fa593ae3ec3526cf929ec553a3b7f8c55"},{"path":"/usr/lib/.build-id/0e/eb164ebc6f9615f9a7f93f605ea5a51ddaad0e","mode":41471,"size":22,"sha256":""},{"path":"/usr/lib/.build-id/f1/36921a5ce9893143c2041d9200079820a01603","mode":41471,"size":25,"sha256":""},{"path":"/usr/share/doc/xz/COPYING","mode":33188,"size":2775,"sha256":"bcb02973ef6e87ea73d331b3a80df7748407f17efdb784b61b47e0e610d3bb5c"},{"path":"/usr/share/doc/xz/COPYING.GPLv2","mode":33188,"size":18092,"sha256":"8177f97513213526df2cf6184d8ff986c675afb514d4e68a404010521b880643"}]}},{"name":"xz-libs","version":"5.2.4-3.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:xz-libs:xz-libs:5.2.4-3.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:xz-libs:5.2.4-3.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/xz-libs@0:5.2.4-3.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"xz-libs","version":"5.2.4","epoch":0,"architecture":"x86_64","release":"3.el8","sourceRpm":"xz-5.2.4-3.el8.src.rpm","size":194799,"license":"Public Domain","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/4b/9ca720dd420f278183935c63e76f079b4e8295","mode":41471,"size":38,"sha256":""},{"path":"/usr/lib64/liblzma.so.5","mode":41471,"size":16,"sha256":""},{"path":"/usr/lib64/liblzma.so.5.2.4","mode":33261,"size":192024,"sha256":"068e64692eea45539d4f8c7cd65f103a3334efb3f50f41835c3c3ff1e4bd4bb9"},{"path":"/usr/share/doc/xz/COPYING","mode":33188,"size":2775,"sha256":"bcb02973ef6e87ea73d331b3a80df7748407f17efdb784b61b47e0e610d3bb5c"}]}},{"name":"yum","version":"4.2.17-6.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:yum:yum:4.2.17-6.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:yum:4.2.17-6.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/yum@0:4.2.17-6.el8?arch=noarch","metadataType":"RpmMetadata","metadata":{"name":"yum","version":"4.2.17","epoch":0,"architecture":"noarch","release":"6.el8","sourceRpm":"dnf-4.2.17-6.el8.src.rpm","size":70881,"license":"GPLv2+ and GPLv2 and GPL","vendor":"CentOS","files":[{"path":"/etc/dnf/protected.d/yum.conf","mode":33188,"size":4,"sha256":"633e249364390d0039a36eae62b88d487e4dc524fe0a5dd166d955ed77a92524"},{"path":"/etc/yum.conf","mode":41471,"size":12,"sha256":""},{"path":"/etc/yum/pluginconf.d","mode":41471,"size":14,"sha256":""},{"path":"/etc/yum/protected.d","mode":41471,"size":18,"sha256":""},{"path":"/etc/yum/vars","mode":41471,"size":11,"sha256":""},{"path":"/usr/bin/yum","mode":41471,"size":5,"sha256":""}]}},{"name":"zlib","version":"1.2.11-13.el8","type":"rpm","foundBy":"rpmdb-cataloger","locations":[{"path":"/var/lib/rpm/Packages","layerID":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8"}],"licenses":[],"language":"","cpes":["cpe:2.3:a:zlib:zlib:1.2.11-13.el8:*:*:*:*:*:*:*","cpe:2.3:a:*:zlib:1.2.11-13.el8:*:*:*:*:*:*:*"],"purl":"pkg:rpm/centos/zlib@0:1.2.11-13.el8?arch=x86_64","metadataType":"RpmMetadata","metadata":{"name":"zlib","version":"1.2.11","epoch":0,"architecture":"x86_64","release":"13.el8","sourceRpm":"zlib-1.2.11-13.el8.src.rpm","size":195551,"license":"zlib and Boost","vendor":"CentOS","files":[{"path":"/usr/lib/.build-id/5b/d3f8b44029f37d9d34bd6a38f595c397418387","mode":41471,"size":36,"sha256":""},{"path":"/usr/lib64/libz.so.1","mode":41471,"size":14,"sha256":""},{"path":"/usr/lib64/libz.so.1.2.11","mode":33261,"size":95232,"sha256":"2dab0207903748522216f498036d9183b5a406f3568ef924f07ffe51c4368379"},{"path":"/usr/share/licenses/zlib/README","mode":33188,"size":5187,"sha256":"7960b6b1cc63e619abb77acaea5427159605afee8c8b362664f4effc7d7f7d15"}]}}],"source":{"type":"image","target":{"userInput":"centos:8.2.2004","imageID":"sha256:831691599b88ad6cc2a4abbd0e89661a121aff14cfa289ad840fd3946f274f1f","manifestDigest":"sha256:61ffd15907f2d16178b4c05172a71e85f85caffb4532169fc693a3cec2504d6f","mediaType":"application/vnd.docker.distribution.manifest.v2+json","tags":["centos:8.2.2004"],"imageSize":215273207,"scope":"Squashed","layers":[{"mediaType":"application/vnd.docker.image.rootfs.diff.tar.gzip","digest":"sha256:eb29745b8228e1e97c01b1d5c2554a319c00a94d8dd5746a3904222ad65a13f8","size":215273207}],"manifest":"eyJzY2hlbWFWZXJzaW9uIjoyLCJtZWRpYVR5cGUiOiJhcHBsaWNhdGlvbi92bmQuZG9ja2VyLmRpc3RyaWJ1dGlvbi5tYW5pZmVzdC52Mitqc29uIiwiY29uZmlnIjp7Im1lZGlhVHlwZSI6ImFwcGxpY2F0aW9uL3ZuZC5kb2NrZXIuY29udGFpbmVyLmltYWdlLnYxK2pzb24iLCJzaXplIjoyMTc4LCJkaWdlc3QiOiJzaGEyNTY6ODMxNjkxNTk5Yjg4YWQ2Y2MyYTRhYmJkMGU4OTY2MWExMjFhZmYxNGNmYTI4OWFkODQwZmQzOTQ2ZjI3NGYxZiJ9LCJsYXllcnMiOlt7Im1lZGlhVHlwZSI6ImFwcGxpY2F0aW9uL3ZuZC5kb2NrZXIuaW1hZ2Uucm9vdGZzLmRpZmYudGFyLmd6aXAiLCJzaXplIjoyMjI1NzM1NjgsImRpZ2VzdCI6InNoYTI1NjplYjI5NzQ1YjgyMjhlMWU5N2MwMWIxZDVjMjU1NGEzMTljMDBhOTRkOGRkNTc0NmEzOTA0MjIyYWQ2NWExM2Y4In1dfQ==","config":"eyJhcmNoaXRlY3R1cmUiOiJhbWQ2NCIsImNvbmZpZyI6eyJIb3N0bmFtZSI6IiIsIkRvbWFpbm5hbWUiOiIiLCJVc2VyIjoiIiwiQXR0YWNoU3RkaW4iOmZhbHNlLCJBdHRhY2hTdGRvdXQiOmZhbHNlLCJBdHRhY2hTdGRlcnIiOmZhbHNlLCJUdHkiOmZhbHNlLCJPcGVuU3RkaW4iOmZhbHNlLCJTdGRpbk9uY2UiOmZhbHNlLCJFbnYiOlsiUEFUSD0vdXNyL2xvY2FsL3NiaW46L3Vzci9sb2NhbC9iaW46L3Vzci9zYmluOi91c3IvYmluOi9zYmluOi9iaW4iXSwiQ21kIjpbIi9iaW4vYmFzaCJdLCJBcmdzRXNjYXBlZCI6dHJ1ZSwiSW1hZ2UiOiJzaGEyNTY6NzJmZjE3NDhkMzYwZDAwNjljOTE1MDhjYTNmZmRlMGQ3NzQ4OTg5Yzc1ZDE5M2VlZTNiMGU4NWM2MjU1N2VmYSIsIlZvbHVtZXMiOm51bGwsIldvcmtpbmdEaXIiOiIiLCJFbnRyeXBvaW50IjpudWxsLCJPbkJ1aWxkIjpudWxsLCJMYWJlbHMiOnsib3JnLmxhYmVsLXNjaGVtYS5idWlsZC1kYXRlIjoiMjAyMDA2MTEiLCJvcmcubGFiZWwtc2NoZW1hLmxpY2Vuc2UiOiJHUEx2MiIsIm9yZy5sYWJlbC1zY2hlbWEubmFtZSI6IkNlbnRPUyBCYXNlIEltYWdlIiwib3JnLmxhYmVsLXNjaGVtYS5zY2hlbWEtdmVyc2lvbiI6IjEuMCIsIm9yZy5sYWJlbC1zY2hlbWEudmVuZG9yIjoiQ2VudE9TIn19LCJjb250YWluZXIiOiIwYTZiOGNiZGVlNzIxOGQxZGE4NDE0NWU4NjdjOGNlMWMzNmQyMjZhNWNmY2EyMDgxMjVkMDhhYzU2ZjdjNWFmIiwiY29udGFpbmVyX2NvbmZpZyI6eyJIb3N0bmFtZSI6IjBhNmI4Y2JkZWU3MiIsIkRvbWFpbm5hbWUiOiIiLCJVc2VyIjoiIiwiQXR0YWNoU3RkaW4iOmZhbHNlLCJBdHRhY2hTdGRvdXQiOmZhbHNlLCJBdHRhY2hTdGRlcnIiOmZhbHNlLCJUdHkiOmZhbHNlLCJPcGVuU3RkaW4iOmZhbHNlLCJTdGRpbk9uY2UiOmZhbHNlLCJFbnYiOlsiUEFUSD0vdXNyL2xvY2FsL3NiaW46L3Vzci9sb2NhbC9iaW46L3Vzci9zYmluOi91c3IvYmluOi9zYmluOi9iaW4iXSwiQ21kIjpbIi9iaW4vc2giLCItYyIsIiMobm9wKSAiLCJDTUQgW1wiL2Jpbi9iYXNoXCJdIl0sIkFyZ3NFc2NhcGVkIjp0cnVlLCJJbWFnZSI6InNoYTI1Njo3MmZmMTc0OGQzNjBkMDA2OWM5MTUwOGNhM2ZmZGUwZDc3NDg5ODljNzVkMTkzZWVlM2IwZTg1YzYyNTU3ZWZhIiwiVm9sdW1lcyI6bnVsbCwiV29ya2luZ0RpciI6IiIsIkVudHJ5cG9pbnQiOm51bGwsIk9uQnVpbGQiOm51bGwsIkxhYmVscyI6eyJvcmcubGFiZWwtc2NoZW1hLmJ1aWxkLWRhdGUiOiIyMDIwMDYxMSIsIm9yZy5sYWJlbC1zY2hlbWEubGljZW5zZSI6IkdQTHYyIiwib3JnLmxhYmVsLXNjaGVtYS5uYW1lIjoiQ2VudE9TIEJhc2UgSW1hZ2UiLCJvcmcubGFiZWwtc2NoZW1hLnNjaGVtYS12ZXJzaW9uIjoiMS4wIiwib3JnLmxhYmVsLXNjaGVtYS52ZW5kb3IiOiJDZW50T1MifX0sImNyZWF0ZWQiOiIyMDIwLTA2LTE3VDAwOjIyOjI1LjQ3MjgyNjg3WiIsImRvY2tlcl92ZXJzaW9uIjoiMTguMDkuNyIsImhpc3RvcnkiOlt7ImNyZWF0ZWQiOiIyMDIwLTA2LTE3VDAwOjIyOjI0LjkxODIzMzc2MloiLCJjcmVhdGVkX2J5IjoiL2Jpbi9zaCAtYyAjKG5vcCkgQUREIGZpbGU6ODQ3MDBjMTFmY2M5NjlhYzA4ZWYyNWYxMTU1MTNkNzZjN2I3MmE0MTE4YzAxZmJjODZlZjBhNjA1NmZkZWJlYiBpbiAvICJ9LHsiY3JlYXRlZCI6IjIwMjAtMDYtMTdUMDA6MjI6MjUuMjc2MDIxNDM4WiIsImNyZWF0ZWRfYnkiOiIvYmluL3NoIC1jICMobm9wKSAgTEFCRUwgb3JnLmxhYmVsLXNjaGVtYS5zY2hlbWEtdmVyc2lvbj0xLjAgb3JnLmxhYmVsLXNjaGVtYS5uYW1lPUNlbnRPUyBCYXNlIEltYWdlIG9yZy5sYWJlbC1zY2hlbWEudmVuZG9yPUNlbnRPUyBvcmcubGFiZWwtc2NoZW1hLmxpY2Vuc2U9R1BMdjIgb3JnLmxhYmVsLXNjaGVtYS5idWlsZC1kYXRlPTIwMjAwNjExIiwiZW1wdHlfbGF5ZXIiOnRydWV9LHsiY3JlYXRlZCI6IjIwMjAtMDYtMTdUMDA6MjI6MjUuNDcyODI2ODdaIiwiY3JlYXRlZF9ieSI6Ii9iaW4vc2ggLWMgIyhub3ApICBDTUQgW1wiL2Jpbi9iYXNoXCJdIiwiZW1wdHlfbGF5ZXIiOnRydWV9XSwib3MiOiJsaW51eCIsInJvb3RmcyI6eyJ0eXBlIjoibGF5ZXJzIiwiZGlmZl9pZHMiOlsic2hhMjU2OmViMjk3NDViODIyOGUxZTk3YzAxYjFkNWMyNTU0YTMxOWMwMGE5NGQ4ZGQ1NzQ2YTM5MDQyMjJhZDY1YTEzZjgiXX19"}},"distro":{"name":"centos","version":"8","idLike":"rhel fedora"},"descriptor":{"name":"syft","version":"[not provided]"},"schema":{"version":"1.0.1","url":"https://raw.githubusercontent.com/anchore/syft/main/schema/json/schema-1.0.1.json"}} diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/.dockerignore b/ci/tools/openeuler-purl/syft-dev/test/install/.dockerignore new file mode 100644 index 0000000000000000000000000000000000000000..fa29cdfff915566d202c195607a42b9445919261 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/.dockerignore @@ -0,0 +1 @@ +** \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/.gitignore b/ci/tools/openeuler-purl/syft-dev/test/install/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..6e25fa8f106e51b7dd538d35b1291301f821b2ad --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/.gitignore @@ -0,0 +1 @@ +cache/ \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/0_search_for_asset_test.sh b/ci/tools/openeuler-purl/syft-dev/test/install/0_search_for_asset_test.sh new file mode 100755 index 0000000000000000000000000000000000000000..5757cae73203e4d7a36871512f4bc17b6ce38f66 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/0_search_for_asset_test.sh @@ -0,0 +1,40 @@ +. test_harness.sh + +# search for an asset in a release checksums file +test_search_for_asset_release() { + fixture=./test-fixtures/syft_0.36.0_checksums.txt + + # search_for_asset [checksums-file-path] [name] [os] [arch] [format] + + # positive case + actual=$(search_for_asset "${fixture}" "syft" "linux" "amd64" "tar.gz") + assertEquals "syft_0.36.0_linux_amd64.tar.gz" "${actual}" "unable to find release asset" + + # negative cases + actual=$(search_for_asset "${fixture}" "syft" "Linux" "amd64" "tar.gz") + assertEquals "" "${actual}" "found a release asset but did not expect to (os)" + + actual=$(search_for_asset "${fixture}" "syft" "darwin" "amd64" "rpm") + assertEquals "" "${actual}" "found a release asset but did not expect to (format)" + +} + +run_test_case test_search_for_asset_release + + +# search for an asset in a snapshot checksums file +test_search_for_asset_snapshot() { + fixture=./test-fixtures/syft_0.35.1-SNAPSHOT-d461f63_checksums.txt + + # search_for_asset [checksums-file-path] [name] [os] [arch] [format] + + # positive case + actual=$(search_for_asset "${fixture}" "syft" "linux" "amd64" "rpm") + assertEquals "syft_0.35.1-SNAPSHOT-d461f63_linux_amd64.rpm" "${actual}" "unable to find snapshot asset" + + # negative case + actual=$(search_for_asset "${fixture}" "syft" "linux" "amd64" "zip") + assertEquals "" "${actual}" "found a snapshot asset but did not expect to (format)" +} + +run_test_case test_search_for_asset_snapshot diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/1_download_snapshot_asset_test.sh b/ci/tools/openeuler-purl/syft-dev/test/install/1_download_snapshot_asset_test.sh new file mode 100755 index 0000000000000000000000000000000000000000..67e076ee9456792ff6980e73d6f95903b90905aa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/1_download_snapshot_asset_test.sh @@ -0,0 +1,93 @@ +. test_harness.sh + +DOWNLOAD_SNAPSHOT_POSITIVE_CASES=0 + +# helper for asserting test_positive_snapshot_download_asset positive cases +test_positive_snapshot_download_asset() { + os="$1" + arch="$2" + format="$3" + + # for troubleshooting + # log_set_priority 10 + + name=${PROJECT_NAME} + github_download=$(snapshot_download_url) + version=$(snapshot_version) + + tmpdir=$(mktemp -d) + + actual_filepath=$(download_asset "${github_download}" "${tmpdir}" "${name}" "${os}" "${arch}" "${version}" "${format}" ) + + assertFileExists "${actual_filepath}" "download_asset os=${os} arch=${arch} format=${format}" + + assertFilesEqual \ + "$(snapshot_dir)/${name}_${version}_${os}_${arch}.${format}" \ + "${actual_filepath}" \ + "unable to download os=${os} arch=${arch} format=${format}" + + ((DOWNLOAD_SNAPSHOT_POSITIVE_CASES++)) + + rm -rf -- "$tmpdir" +} + + +test_download_snapshot_asset_exercised_all_assets() { + expected=$(snapshot_assets_count) + + assertEquals "${expected}" "${DOWNLOAD_SNAPSHOT_POSITIVE_CASES}" "did not download all possible assets (missing an os/arch/format variant?)" +} + +# helper for asserting download_asset negative cases +test_negative_snapshot_download_asset() { + os="$1" + arch="$2" + format="$3" + + # for troubleshooting + # log_set_priority 10 + + name=${PROJECT_NAME} + github_download=$(snapshot_download_url) + version=$(snapshot_version) + + tmpdir=$(mktemp -d) + + actual_filepath=$(download_asset "${github_download}" "${tmpdir}" "${name}" "${os}" "${arch}" "${version}" "${format}") + + assertEquals "" "${actual_filepath}" "unable to download os=${os} arch=${arch} format=${format}" + + rm -rf -- "$tmpdir" +} + + +worker_pid=$(setup_snapshot_server) +trap 'teardown_snapshot_server ${worker_pid}' EXIT + +# exercise all possible assets +run_test_case test_positive_snapshot_download_asset "linux" "amd64" "tar.gz" +run_test_case test_positive_snapshot_download_asset "linux" "amd64" "rpm" +run_test_case test_positive_snapshot_download_asset "linux" "amd64" "deb" +run_test_case test_positive_snapshot_download_asset "linux" "arm64" "tar.gz" +run_test_case test_positive_snapshot_download_asset "linux" "arm64" "rpm" +run_test_case test_positive_snapshot_download_asset "linux" "arm64" "deb" +run_test_case test_positive_snapshot_download_asset "linux" "ppc64le" "tar.gz" +run_test_case test_positive_snapshot_download_asset "linux" "ppc64le" "rpm" +run_test_case test_positive_snapshot_download_asset "linux" "ppc64le" "deb" +run_test_case test_positive_snapshot_download_asset "linux" "s390x" "tar.gz" +run_test_case test_positive_snapshot_download_asset "linux" "s390x" "rpm" +run_test_case test_positive_snapshot_download_asset "linux" "s390x" "deb" + +run_test_case test_positive_snapshot_download_asset "darwin" "amd64" "tar.gz" +run_test_case test_positive_snapshot_download_asset "darwin" "arm64" "tar.gz" +run_test_case test_positive_snapshot_download_asset "windows" "amd64" "zip" +# note: the mac signing process produces a dmg which is not part of the snapshot process (thus is not exercised here) + +# let's make certain we covered all assets that were expected +run_test_case test_download_snapshot_asset_exercised_all_assets + +# make certain we handle missing assets alright +run_test_case test_negative_snapshot_download_asset "bogus" "amd64" "zip" + +trap - EXIT +teardown_snapshot_server "${worker_pid}" diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/2_download_release_asset_test.sh b/ci/tools/openeuler-purl/syft-dev/test/install/2_download_release_asset_test.sh new file mode 100755 index 0000000000000000000000000000000000000000..fc97b794a9e35f0ebd7333b9ec0855ddda76e5b4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/2_download_release_asset_test.sh @@ -0,0 +1,41 @@ +. test_harness.sh + +test_download_release_asset() { + release="$1" + os="$2" + arch="$3" + format="$4" + expected_mime_type="$5" + + # for troubleshooting + # log_set_priority 10 + + name=${PROJECT_NAME} + version=$(tag_to_version ${release}) + github_download="https://github.com/${OWNER}/${REPO}/releases/download/${release}" + + tmpdir=$(mktemp -d) + + actual_filepath=$(download_asset "${github_download}" "${tmpdir}" "${name}" "${os}" "${arch}" "${version}" "${format}" ) + + assertFileExists "${actual_filepath}" "download_asset os=${os} arch=${arch} format=${format}" + + actual_mime_type=$(file -b --mime-type ${actual_filepath}) + + assertEquals "${expected_mime_type}" "${actual_mime_type}" "unexpected mimetype for os=${os} arch=${arch} format=${format}" + + rm -rf -- "$tmpdir" +} + +# always test against the latest release +release=$(get_release_tag "${OWNER}" "${REPO}" "latest" ) + +# exercise all possible assets against a real github release (based on asset listing from https://github.com/anchore/syft/releases/tag/v0.36.0) +run_test_case test_download_release_asset "${release}" "darwin" "amd64" "tar.gz" "application/gzip" +run_test_case test_download_release_asset "${release}" "darwin" "arm64" "tar.gz" "application/gzip" +run_test_case test_download_release_asset "${release}" "linux" "amd64" "tar.gz" "application/gzip" +run_test_case test_download_release_asset "${release}" "linux" "amd64" "rpm" "application/x-rpm" +run_test_case test_download_release_asset "${release}" "linux" "amd64" "deb" "application/vnd.debian.binary-package" +run_test_case test_download_release_asset "${release}" "linux" "arm64" "tar.gz" "application/gzip" +run_test_case test_download_release_asset "${release}" "linux" "arm64" "rpm" "application/x-rpm" +run_test_case test_download_release_asset "${release}" "linux" "arm64" "deb" "application/vnd.debian.binary-package" diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/3_install_asset_test.sh b/ci/tools/openeuler-purl/syft-dev/test/install/3_install_asset_test.sh new file mode 100755 index 0000000000000000000000000000000000000000..743c75129dab249d7e552bc64a9b7300f67dd28e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/3_install_asset_test.sh @@ -0,0 +1,98 @@ +. test_harness.sh + +INSTALL_ARCHIVE_POSITIVE_CASES=0 + +# helper for asserting install_asset positive cases +test_positive_snapshot_install_asset() { + os="$1" + arch="$2" + format="$3" + + # for troubleshooting + # log_set_priority 10 + + name=${PROJECT_NAME} + binary=$(get_binary_name "${os}" "${arch}" "${PROJECT_NAME}") + github_download=$(snapshot_download_url) + version=$(snapshot_version) + + download_dir=$(mktemp -d) + install_dir=$(mktemp -d) + + download_and_install_asset "${github_download}" "${download_dir}" "${install_dir}" "${name}" "${os}" "${arch}" "${version}" "${format}" "${binary}" + + assertEquals "0" "$?" "download/install did not succeed" + + expected_path="${install_dir}/${binary}" + assertFileExists "${expected_path}" "install_asset os=${os} arch=${arch} format=${format}" + + # directory structure for arch has been updated as of go 1.18 + # https://goreleaser.com/customization/build/#why-is-there-a-_v1-suffix-on-amd64-buildsjk + if [ $arch == "amd64" ]; then + arch="amd64_v1" + fi + + assertFilesEqual \ + "$(snapshot_dir)/${os}-build_${os}_${arch}/${binary}" \ + "${expected_path}" \ + "unable to verify installation of os=${os} arch=${arch} format=${format}" + + ((INSTALL_ARCHIVE_POSITIVE_CASES++)) + + rm -rf -- "$download_dir" + rm -rf -- "$install_dir" +} + +# helper for asserting install_asset negative cases +test_negative_snapshot_install_asset() { + os="$1" + arch="$2" + format="$3" + + # for troubleshooting + # log_set_priority 10 + + name=${PROJECT_NAME} + binary=$(get_binary_name "${os}" "${arch}" "${PROJECT_NAME}") + github_download=$(snapshot_download_url) + version=$(snapshot_version) + + download_dir=$(mktemp -d) + install_dir=$(mktemp -d) + + download_and_install_asset "${github_download}" "${download_dir}" "${install_dir}" "${name}" "${os}" "${arch}" "${version}" "${format}" "${binary}" + + assertNotEquals "0" "$?" "download/install should have failed but did not" + + rm -rf -- "$download_dir" + rm -rf -- "$install_dir" +} + + +test_install_asset_exercised_all_archive_assets() { + expected=$(snapshot_assets_archive_count) + + assertEquals "${expected}" "${INSTALL_ARCHIVE_POSITIVE_CASES}" "did not download all possible archive assets (missing an os/arch/format variant?)" +} + + +worker_pid=$(setup_snapshot_server) +trap 'teardown_snapshot_server ${worker_pid}' EXIT + +# exercise all possible archive assets (not rpm/deb/dmg) against a snapshot build +run_test_case test_positive_snapshot_install_asset "linux" "amd64" "tar.gz" +run_test_case test_positive_snapshot_install_asset "linux" "arm64" "tar.gz" +run_test_case test_positive_snapshot_install_asset "linux" "ppc64le" "tar.gz" +run_test_case test_positive_snapshot_install_asset "linux" "s390x" "tar.gz" +run_test_case test_positive_snapshot_install_asset "darwin" "amd64" "tar.gz" +run_test_case test_positive_snapshot_install_asset "darwin" "arm64" "tar.gz" +run_test_case test_positive_snapshot_install_asset "windows" "amd64" "zip" + +# let's make certain we covered all assets that were expected +run_test_case test_install_asset_exercised_all_archive_assets + +# make certain we handle missing assets alright +run_test_case test_negative_snapshot_install_asset "bogus" "amd64" "zip" + +trap - EXIT +teardown_snapshot_server "${worker_pid}" diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/Makefile b/ci/tools/openeuler-purl/syft-dev/test/install/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..9e74cbe4b0c85874642a2609a23ae624b1216ed7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/Makefile @@ -0,0 +1,127 @@ +NAME=syft + +IMAGE_NAME=$(NAME)-install.sh-env +UBUNTU_IMAGE=$(IMAGE_NAME):ubuntu-20.04 +ALPINE_IMAGE=$(IMAGE_NAME):alpine-3.6 +BUSYBOX_IMAGE=busybox:1.35 + +ENVS=./environments +DOCKER_RUN=docker run --rm -t -w /project/test/install -v $(shell pwd)/../../:/project +UNIT=make unit-local + +# acceptance testing is running the current install.sh against the latest release. Note: this could be a problem down +# the line if there are breaking changes made that don't align with the latest release (but will be OK with the next +# release) +ACCEPTANCE_CMD=sh -c '../../install.sh -b /usr/local/bin && syft version' +# we also want to test against a previous release to ensure that install.sh defers execution to a former install.sh +PREVIOUS_RELEASE=v0.33.0 +ACCEPTANCE_PREVIOUS_RELEASE_CMD=sh -c "../../install.sh -b /usr/local/bin $(PREVIOUS_RELEASE) && syft version" + +# CI cache busting values; change these if you want CI to not use previous stored cache +INSTALL_TEST_CACHE_BUSTER=894d8ca + +define title + @printf '\n≡≡≡[ $(1) ]≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡\n' +endef + +.PHONY: test +test: unit acceptance + +.PHONY: ci-test-mac +ci-test-mac: unit-local acceptance-local + +# note: do not add acceptance-local to this list +.PHONY: acceptance +acceptance: acceptance-ubuntu-20.04 acceptance-alpine-3.6 acceptance-busybox-1.35 + +.PHONY: unit +unit: unit-ubuntu-20.04 + +.PHONY: unit-local +unit-local: + $(call title,unit tests) + @for f in $(shell ls *_test.sh); do echo "Running unit test suite '$${f}'"; bash $${f} || exit 1; done + +.PHONY: acceptance-local +acceptance-local: acceptance-current-release-local acceptance-previous-release-local + +.PHONY: acceptance-current-release-local +acceptance-current-release-local: + $(ACCEPTANCE_CMD) + +.PHONY: acceptance-previous-release-local +acceptance-previous-release-local: + $(ACCEPTANCE_PREVIOUS_RELEASE_CMD) + syft version | grep $(shell echo $(PREVIOUS_RELEASE)| tr -d "v") + +.PHONY: save +save: ubuntu-20.04 alpine-3.6 busybox-1.35 + @mkdir cache || true + docker image save -o cache/ubuntu-env.tar $(UBUNTU_IMAGE) + docker image save -o cache/alpine-env.tar $(ALPINE_IMAGE) + docker image save -o cache/busybox-env.tar $(BUSYBOX_IMAGE) + +.PHONY: load +load: + docker image load -i cache/ubuntu-env.tar + docker image load -i cache/alpine-env.tar + docker image load -i cache/busybox-env.tar + +## UBUNTU ####################################################### + +.PHONY: acceptance-ubuntu-20.04 +acceptance-ubuntu-20.04: ubuntu-20.04 + $(call title,ubuntu:20.04 - acceptance) + $(DOCKER_RUN) $(UBUNTU_IMAGE) \ + $(ACCEPTANCE_CMD) + +.PHONY: unit-ubuntu-20.04 +unit-ubuntu-20.04: ubuntu-20.04 + $(call title,ubuntu:20.04 - unit) + $(DOCKER_RUN) $(UBUNTU_IMAGE) \ + $(UNIT) + +.PHONY: ubuntu-20.04 +ubuntu-20.04: + $(call title,ubuntu:20.04 - build environment) + docker build -t $(UBUNTU_IMAGE) -f $(ENVS)/Dockerfile-ubuntu-20.04 . + +## ALPINE ####################################################### + +# note: unit tests cannot be run with sh (alpine dosn't have bash by default) + +.PHONY: acceptance-alpine-3.6 +acceptance-alpine-3.6: alpine-3.6 + $(call title,alpine:3.6 - acceptance) + $(DOCKER_RUN) $(ALPINE_IMAGE) \ + $(ACCEPTANCE_CMD) + +.PHONY: alpine-3.6 +alpine-3.6: + $(call title,alpine:3.6 - build environment) + docker build -t $(ALPINE_IMAGE) -f $(ENVS)/Dockerfile-alpine-3.6 . + +## BUSYBOX ####################################################### + +# note: unit tests cannot be run with sh (busybox dosn't have bash by default) + +# note: busybox by default will not have cacerts, so you will get TLS warnings (we want to test under these conditions) + +.PHONY: acceptance-busybox-1.35 +acceptance-busybox-1.35: busybox-1.35 + $(call title,busybox-1.35 - acceptance) + $(DOCKER_RUN) $(BUSYBOX_IMAGE) \ + $(ACCEPTANCE_CMD) + @echo "\n*** test note: you should see syft spit out a 'x509: certificate signed by unknown authority' error --this is expected ***" + +.PHONY: busybox-1.35 +busybox-1.35: + $(call title,busybox-1.35 - build environment) + docker pull $(BUSYBOX_IMAGE) + +## For CI ######################################################## + +.PHONY: cache.fingerprint +cache.fingerprint: + $(call title,Install test fixture fingerprint) + @find ./environments/* -type f -exec md5sum {} + | awk '{print $1}' | sort | tee /dev/stderr | md5sum | tee cache.fingerprint && echo "$(INSTALL_TEST_CACHE_BUSTER)" >> cache.fingerprint diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/environments/Dockerfile-alpine-3.6 b/ci/tools/openeuler-purl/syft-dev/test/install/environments/Dockerfile-alpine-3.6 new file mode 100644 index 0000000000000000000000000000000000000000..982e5402996afef751c334c7c6c1c3321290c358 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/environments/Dockerfile-alpine-3.6 @@ -0,0 +1,2 @@ +FROM alpine:3.6 +RUN apk update && apk add python3 wget unzip make ca-certificates \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/environments/Dockerfile-ubuntu-20.04 b/ci/tools/openeuler-purl/syft-dev/test/install/environments/Dockerfile-ubuntu-20.04 new file mode 100644 index 0000000000000000000000000000000000000000..dafb64ed73ddde9e3fc218716be347d9690321d1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/environments/Dockerfile-ubuntu-20.04 @@ -0,0 +1,2 @@ +FROM ubuntu:20.04 +RUN apt update -y && apt install make python3 curl unzip -y \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/github_test.sh b/ci/tools/openeuler-purl/syft-dev/test/install/github_test.sh new file mode 100755 index 0000000000000000000000000000000000000000..29d9ed9c583ebf66c40bc90ef8df6eeaff8bfcb3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/github_test.sh @@ -0,0 +1,68 @@ +. test_harness.sh + +# check that we can extract single json values +test_extract_json_value() { + fixture=./test-fixtures/github-api-syft-v0.36.0-release.json + content=$(cat ${fixture}) + + actual=$(extract_json_value "${content}" "tag_name") + assertEquals "v0.36.0" "${actual}" "unable to find tag_name" + + actual=$(extract_json_value "${content}" "id") + assertEquals "57501596" "${actual}" "unable to find tag_name" +} + +run_test_case test_extract_json_value + + +# check that we can extract github release tag from github api json +test_github_release_tag() { + fixture=./test-fixtures/github-api-syft-v0.36.0-release.json + content=$(cat ${fixture}) + + actual=$(github_release_tag "${content}") + assertEquals "v0.36.0" "${actual}" "unable to find release tag" +} + +run_test_case test_github_release_tag + + +# download a known good github release checksums and compare against a test-fixture +test_download_github_release_checksums() { + tmpdir=$(mktemp -d) + + tag=v0.36.0 + github_download="https://github.com/anchore/syft/releases/download/${tag}" + name=${PROJECT_NAME} + version=$(tag_to_version "${tag}") + + actual_filepath=$(download_github_release_checksums "${github_download}" "${name}" "${version}" "${tmpdir}") + assertFilesEqual \ + "./test-fixtures/syft_0.36.0_checksums.txt" \ + "${actual_filepath}" \ + "unable to find release tag" + + rm -rf -- "$tmpdir" +} + +run_test_case test_download_github_release_checksums + + +# download a checksums file from a locally served-up snapshot directory and compare against the file in the snapshot dir +test_download_github_release_checksums_snapshot() { + tmpdir=$(mktemp -d) + + github_download=$(snapshot_download_url) + name=${PROJECT_NAME} + version=$(snapshot_version) + + actual_filepath=$(download_github_release_checksums "${github_download}" "${name}" "${version}" "${tmpdir}") + assertFilesEqual \ + "$(snapshot_checksums_path)" \ + "${actual_filepath}" \ + "unable to find release tag" + + rm -rf -- "$tmpdir" +} + +run_test_case_with_snapshot_release test_download_github_release_checksums_snapshot \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/github-api-syft-v0.36.0-release.json b/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/github-api-syft-v0.36.0-release.json new file mode 100644 index 0000000000000000000000000000000000000000..ac92c18bd3ec147be91f4ba89d35cfd49968d2e6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/github-api-syft-v0.36.0-release.json @@ -0,0 +1 @@ +{"id":57501596,"tag_name":"v0.36.0","update_url":"/anchore/syft/releases/tag/v0.36.0","update_authenticity_token":"7XbNZgRHpbHegdv-xRlbe84Y983YgyXa3YKWwv_e0ocqTHagsHq5dxCTQUQnuX3vbsgdWQU3A3__hkVNhKGHSg","delete_url":"/anchore/syft/releases/tag/v0.36.0","delete_authenticity_token":"6tLaRtXKUc-zz4tHIwCbbD7CksxIHK5imZE1gnA39oVCe6fYux5a8cPD9J52kGUzM1Hs9JPBjceG7yyszBk_2A","edit_url":"/anchore/syft/releases/edit/v0.36.0"} diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/syft_0.35.1-SNAPSHOT-d461f63_checksums.txt b/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/syft_0.35.1-SNAPSHOT-d461f63_checksums.txt new file mode 100644 index 0000000000000000000000000000000000000000..484ae6594d5c6fccea5cd31570249594d708e739 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/syft_0.35.1-SNAPSHOT-d461f63_checksums.txt @@ -0,0 +1,11 @@ +123745ee29779018ab386223a900f8cc704aa577f57ca43c157147c53c998a77 syft_0.35.1-SNAPSHOT-d461f63_linux_arm64.deb +2083c5ad471028212e5ca72fdd3d60204052dbf3a9148c9579deac6af7865a3a syft_0.35.1-SNAPSHOT-d461f63_linux_arm64.tar.gz +6b95e8b17fdbb5da094c2251c8ee5a8e97e6059b6556308f1ff2b657a6a080bc syft_0.35.1-SNAPSHOT-d461f63_darwin_x86_64.tar.gz +940ea13dceedfcf3cf0ee2be24447123bf7efdb034c9f923e35549537b094aaa syft_0.35.1-SNAPSHOT-d461f63_Windows_x86_64.zip +a96efc4139c79e0ecb526c7ab7c90fc94ee89c871c006c1089eb7c40c345ea65 syft_0.35.1-SNAPSHOT-d461f63_linux_x86_64.tar.gz +b120a661ae5e24edc4b2c7932d5b4c9a54d6a90ceced6ba0acb9984ac45c0a4e syft_0.35.1-SNAPSHOT-d461f63_linux_arm64.rpm +d1bc4ac460d5bd5bc173425e32b974a0a0d06f892bef4ab5b431394063b2963a syft_0.35.1-SNAPSHOT-d461f63_linux_amd64.rpm +d65f963160acdc47a0f037bb42993866696181350e9901b8ad3d79f2dea35939 syft_0.35.1-SNAPSHOT-d461f63_darwin_arm64.zip +d978c2bffaad36ea833203377f808725a4d3f8fd486f15552759f63909b210ba syft_0.35.1-SNAPSHOT-d461f63_darwin_arm64.tar.gz +da76cc564d8e597f9c5b33423d2280eb6bf65ba2f2092d7851cdd67718e0cbe1 syft_0.35.1-SNAPSHOT-d461f63_darwin_amd64.zip +e75f4cbf5c2b05663f49f683f99ed01d8e6ebe0e082631461dceae6641c3103f syft_0.35.1-SNAPSHOT-d461f63_linux_amd64.deb diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/syft_0.36.0_checksums.txt b/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/syft_0.36.0_checksums.txt new file mode 100644 index 0000000000000000000000000000000000000000..676f1c2d673282aa02bb0916390fbabdfdc33ad8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/test-fixtures/syft_0.36.0_checksums.txt @@ -0,0 +1,8 @@ +16541ac64378d4216ac9fe2065d20e188a89e8c9cce4e637940a559daddb213b syft_0.36.0_linux_amd64.rpm +4596fdbb491251f6d8e3be38b64d361a9a35cf6a88da6bdad62c019511ffb1a5 syft_0.36.0_linux_amd64.deb +5a69df410597d8649071b3419c17829f60d9f6f00edc8856b681842c2151f83c syft_0.36.0_linux_amd64.tar.gz +5c06f09d370740fb017c6a51657911a87860450d929fa28a9eff1cf00faac303 syft_0.36.0_darwin_arm64.tar.gz +71403ffa346612f9203ce7657d2d191794a0e4367da355605377b8b5d457b7ef syft_0.36.0_linux_arm64.tar.gz +75989a83f0d361969b5f88f3ee3807ed9ddbdf9fae13b6edce1839cf5952a36c syft_0.36.0_linux_arm64.deb +860b42c5d7d03e484c87e18031e6a473f48d3b088a6268fcf8f9567d5b5c90d3 syft_0.36.0_linux_arm64.rpm +fba022c6fac6f2d2f648295af78f86e873488565e41a252a97efafe75622ccf6 syft_0.36.0_darwin_amd64.tar.gz diff --git a/ci/tools/openeuler-purl/syft-dev/test/install/test_harness.sh b/ci/tools/openeuler-purl/syft-dev/test/install/test_harness.sh new file mode 100644 index 0000000000000000000000000000000000000000..8db34de36ff3e889e9b9cf8b6a48ff2c94b8a686 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/install/test_harness.sh @@ -0,0 +1,190 @@ +# disable using the install.sh entrypoint such that we can unit test +# script functions without invoking main() +TEST_INSTALL_SH=true + +. ../../install.sh +set -u + +echoerr() { + echo "$@" 1>&2 +} + +printferr() { + printf "%s" "$*" >&2 +} + + +assertTrue() { + if eval "$1"; then + echo "assertTrue failed: $2" + exit 2 + fi +} + +assertFalse() { + if eval "$1"; then + echo "assertFalse failed: $2" + exit 2 + fi +} + +assertEquals() { + want=$1 + got=$2 + msg=$3 + if [ "$want" != "$got" ]; then + echo "assertEquals failed: want='$want' got='$got' $msg" + exit 2 + fi +} + +assertFilesDoesNotExist() { + path="$1" + msg=$2 + if [ -f "${path}" ]; then + echo "assertFilesDoesNotExist failed: path exists '$path': $msg" + exit 2 + fi +} + +assertFileExists() { + path="$1" + msg=$2 + if [ ! -f "${path}" ]; then + echo "assertFileExists failed: path does not exist '$path': $msg" + exit 2 + fi +} + +assertFilesEqual() { + want=$1 + got=$2 + msg=$3 + + diff "$1" "$2" + if [ $? -ne 0 ]; then + echo "assertFilesEqual failed: $msg" + exit 2 + fi +} + +assertNotEquals() { + want=$1 + got=$2 + msg=$3 + if [ "$want" = "$got" ]; then + echo "assertNotEquals failed: want='$want' got='$got' $msg" + exit 2 + fi +} + +log_test_case() { + echo " running $@" +} + +run_test_case_with_snapshot_release() { + log_test_case ${@:1} + + worker_pid=$(setup_snapshot_server) + trap "teardown_snapshot_server $worker_pid" EXIT + + # run test function with all arguments + ${@:1} + + trap - EXIT + teardown_snapshot_server "${worker_pid}" +} + +serve_port=8000 + +setup_snapshot_server() { + # if you want to see proof in the logs, feel free to adjust the redirection + python3 -m http.server --directory "$(snapshot_dir)" $serve_port &> /dev/null & + worker_pid=$! + + echoerr "serving up $(snapshot_dir) on port $serve_port" + + echoerr "$(ls -1 $(snapshot_dir) | sed 's/^/ ▕―― /')" + + check_snapshots_server_ready + + echoerr "snapshot server ready! (worker=${worker_pid})" + + echo "$worker_pid" +} + +check_snapshots_server_ready() { + i=0 + until $(curl -m 3 --output /dev/null --silent --head --fail localhost:$serve_port/); do + sleep 1 + ((i=i+1)) + if [ "$i" -gt "30" ]; then + echoerr "could not connect to local snapshot server! bailing..." + exit 1 + fi + printferr '.' + done +} + +teardown_snapshot_server() { + worker_pid="$1" + echoerr "stopping worker=${worker_pid}" + kill "$worker_pid" +} + +snapshot_version() { + partial=$(ls ../../snapshot/*_checksums.txt | grep -o "_.*_checksums.txt") + partial="${partial%_checksums.txt}" + echo "${partial#_}" +} + +snapshot_download_url() { + echo "localhost:${serve_port}" +} + +snapshot_dir() { + echo "../../snapshot" +} + +snapshot_checksums_path() { + echo "$(ls $(snapshot_dir)/*_checksums.txt)" +} + +snapshot_assets_count() { + # example output before wc -l: + + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_linux_arm64.deb + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_linux_arm64.tar.gz + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_linux_amd64.rpm + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_darwin_arm64.tar.gz + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_linux_amd64.deb + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_linux_arm64.rpm + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_darwin_amd64.zip + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_windows_amd64.zip + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_darwin_arm64.zip + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_linux_amd64.tar.gz + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_darwin_amd64.tar.gz + + echo "$(find ../../snapshot -maxdepth 1 -type f | grep 'syft_' | grep -v checksums | wc -l | tr -d '[:space:]')" +} + + +snapshot_assets_archive_count() { + # example output before wc -l: + + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_linux_arm64.tar.gz + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_darwin_arm64.tar.gz + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_darwin_amd64.zip + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_windows_amd64.zip + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_darwin_arm64.zip + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_linux_amd64.tar.gz + # ../../snapshot/syft_0.36.0-SNAPSHOT-e5e847a_darwin_amd64.tar.gz + + echo "$(find ../../snapshot -maxdepth 1 -type f | grep 'syft_' | grep 'tar\|zip' | wc -l | tr -d '[:space:]')" +} + + +run_test_case() { + log_test_case ${@:1} + ${@:1} +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/catalog_packages_cases_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/catalog_packages_cases_test.go new file mode 100644 index 0000000000000000000000000000000000000000..512461105a2a963412010b8cb20f008011a687d9 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/catalog_packages_cases_test.go @@ -0,0 +1,361 @@ +package integration + +import "github.com/anchore/syft/syft/pkg" + +type testCase struct { + name string + pkgType pkg.Type + pkgLanguage pkg.Language + duplicates int + pkgInfo map[string]string +} + +var imageOnlyTestCases = []testCase{ + { + name: "find gemspec packages", + pkgType: pkg.GemPkg, + pkgLanguage: pkg.Ruby, + pkgInfo: map[string]string{ + // specifications in the root specification directory + "bundler": "2.1.4", + // specifications in named directories + "unbundler": "3.1.4", + }, + }, + { + name: "find npm package", + pkgType: pkg.NpmPkg, + pkgLanguage: pkg.JavaScript, + pkgInfo: map[string]string{ + "npm": "6.14.6", + }, + }, + { + name: "find python egg & wheel packages", + pkgType: pkg.PythonPkg, + pkgLanguage: pkg.Python, + pkgInfo: map[string]string{ + "Pygments": "2.6.1", + "requests": "2.22.0", + "somerequests": "3.22.0", + "someotherpkg": "3.19.0", + }, + }, + { + name: "find PHP composer installed.json packages", + pkgType: pkg.PhpComposerPkg, + pkgLanguage: pkg.PHP, + pkgInfo: map[string]string{ + "nikic/fast-route": "v1.3.0", + "psr/container": "2.0.2", + "psr/http-factory": "1.0.1", + }, + }, + { + // When the image is build lib overwrites pkgs/lib causing there to only be two packages + name: "find apkdb packages", + pkgType: pkg.ApkPkg, + pkgInfo: map[string]string{ + "musl-utils": "1.1.24-r2", + "libc-utils": "0.7.2-r0", + }, + }, + { + name: "find java packages excluding pom.xml", // image scans can not include packages that have yet to be installed + pkgType: pkg.JavaPkg, + pkgLanguage: pkg.Java, + pkgInfo: map[string]string{ + "example-java-app-maven": "0.1.0", + "joda-time": "2.9.2", + }, + }, +} + +var dirOnlyTestCases = []testCase{ + { + name: "find gemfile packages", + pkgType: pkg.GemPkg, + pkgLanguage: pkg.Ruby, + pkgInfo: map[string]string{ + "actionmailer": "4.1.1", + "actionpack": "4.1.1", + "actionview": "4.1.1", + "activemodel": "4.1.1", + "activerecord": "4.1.1", + "activesupport": "4.1.1", + "arel": "5.0.1.20140414130214", + "bootstrap-sass": "3.1.1.1", + "builder": "3.2.2", + "coffee-rails": "4.0.1", + "coffee-script": "2.2.0", + "coffee-script-source": "1.7.0", + "erubis": "2.7.0", + "execjs": "2.0.2", + "hike": "1.2.3", + "i18n": "0.6.9", + "jbuilder": "2.0.7", + "jquery-rails": "3.1.0", + "json": "1.8.1", + "kgio": "2.9.2", + "libv8": "3.16.14.3", + "mail": "2.5.4", + "mime-types": "1.25.1", + "minitest": "5.3.4", + "multi_json": "1.10.1", + "mysql2": "0.3.16", + "polyglot": "0.3.4", + "rack": "1.5.2", + "rack-test": "0.6.2", + "rails": "4.1.1", + "railties": "4.1.1", + "raindrops": "0.13.0", + "rake": "10.3.2", + "rdoc": "4.1.1", + "ref": "1.0.5", + "sass": "3.2.19", + "sass-rails": "4.0.3", + "sdoc": "0.4.0", + "spring": "1.1.3", + "sprockets": "2.11.0", + "sprockets-rails": "2.1.3", + "sqlite3": "1.3.9", + "therubyracer": "0.12.1", + "thor": "0.19.1", + "thread_safe": "0.3.3", + "tilt": "1.4.1", + "treetop": "1.4.15", + "turbolinks": "2.2.2", + "tzinfo": "1.2.0", + "uglifier": "2.5.0", + "unicorn": "4.8.3", + }, + }, + { + name: "find javascript npm packages (yarn.lock & package-lock.json)", + pkgType: pkg.NpmPkg, + pkgLanguage: pkg.JavaScript, + pkgInfo: map[string]string{ + "@babel/code-frame": "7.10.4", + "get-stdin": "8.0.0", + }, + }, + { + name: "find python requirements.txt & setup.py package references", + pkgType: pkg.PythonPkg, + pkgLanguage: pkg.Python, + pkgInfo: map[string]string{ + // dir specific test cases + "flask": "4.0.0", + "python-dateutil": "2.8.1", + "python-swiftclient": "3.8.1", + "pytz": "2019.3", + "jsonschema": "2.6.0", + "passlib": "1.7.2", + "mypy": "v0.770", + // common to image and directory + "Pygments": "2.6.1", + "requests": "2.22.0", + "somerequests": "3.22.0", + "someotherpkg": "3.19.0", + }, + }, + { + name: "find golang modules", + pkgType: pkg.GoModulePkg, + pkgLanguage: pkg.Go, + pkgInfo: map[string]string{ + "github.com/bmatcuk/doublestar": "v1.3.1", + }, + }, + { + name: "find conan packages", + pkgType: pkg.ConanPkg, + pkgLanguage: pkg.CPP, + pkgInfo: map[string]string{ + "catch2": "2.13.8", + "docopt.cpp": "0.6.3", + "fmt": "8.1.1", + "spdlog": "1.9.2", + "sdl": "2.0.20", + "fltk": "1.3.8", + }, + }, + { + name: "find rust crates", + pkgType: pkg.RustPkg, + pkgLanguage: pkg.Rust, + pkgInfo: map[string]string{ + "memchr": "2.3.3", + "nom": "4.2.3", + "version_check": "0.1.5", + }, + }, + { + name: "find apkdb packages", + pkgType: pkg.ApkPkg, + duplicates: 2, // when the directory is cataloged we have duplicates between lib/ and pkgs/lib + pkgInfo: map[string]string{ + "musl-utils": "1.1.24-r2", + "libc-utils": "0.7.2-r0", + }, + }, + { + name: "find php composer package", + pkgType: pkg.PhpComposerPkg, + pkgLanguage: pkg.PHP, + pkgInfo: map[string]string{ + "adoy/fastcgi-client": "1.0.2", + "alcaeus/mongo-php-adapter": "1.1.11", + }, + }, + { + name: "find pubspec lock packages", + pkgType: pkg.DartPubPkg, + pkgLanguage: pkg.Dart, + pkgInfo: map[string]string{ + "ansicolor": "1.1.1", + "archive": "2.0.13", + "args": "1.6.0", + "key_binder": "1.11.20", + "ale": "3.3.0", + "analyzer": "0.40.7", + }, + }, + { + name: "find dotnet packages", + pkgType: pkg.DotnetPkg, + pkgLanguage: pkg.Dotnet, + pkgInfo: map[string]string{ + "AWSSDK.Core": "3.7.10.6", + "Microsoft.Extensions.DependencyInjection": "6.0.0", + "Microsoft.Extensions.DependencyInjection.Abstractions": "6.0.0", + "Microsoft.Extensions.Logging": "6.0.0", + "Microsoft.Extensions.Logging.Abstractions": "6.0.0", + "Microsoft.Extensions.Options": "6.0.0", + "Microsoft.Extensions.Primitives": "6.0.0", + "Newtonsoft.Json": "13.0.1", + "Serilog": "2.10.0", + "Serilog.Sinks.Console": "4.0.1", + "System.Diagnostics.DiagnosticSource": "6.0.0", + "System.Runtime.CompilerServices.Unsafe": "6.0.0", + }, + }, + { + name: "find java packages including pom.xml", // directory scans can include packages that have yet to be installed + pkgType: pkg.JavaPkg, + pkgLanguage: pkg.Java, + duplicates: 1, // joda-time is included in both pom.xml AND the .jar collection + pkgInfo: map[string]string{ + "example-java-app-maven": "0.1.0", + "joda-time": "2.9.2", + "junit": "4.12", + }, + }, + { + name: "find cocoapods packages", + pkgType: pkg.CocoapodsPkg, + pkgLanguage: pkg.Swift, + pkgInfo: map[string]string{ + "GlossButtonNode": "3.1.2", + "PINCache": "3.0.3", + "PINCache/Arc-exception-safe": "3.0.3", + "PINCache/Core": "3.0.3", + "PINOperation": "1.2.1", + "PINRemoteImage/Core": "3.0.3", + "PINRemoteImage/iOS": "3.0.3", + "PINRemoteImage/PINCache": "3.0.3", + "Reveal-SDK": "33", + "SwiftGen": "6.5.1", + "Texture": "3.1.0", + "Texture/AssetsLibrary": "3.1.0", + "Texture/Core": "3.1.0", + "Texture/MapKit": "3.1.0", + "Texture/Photos": "3.1.0", + "Texture/PINRemoteImage": "3.1.0", + "Texture/Video": "3.1.0", + "TextureSwiftSupport": "3.13.0", + "TextureSwiftSupport/Components": "3.13.0", + "TextureSwiftSupport/Experiments": "3.13.0", + "TextureSwiftSupport/Extensions": "3.13.0", + "TextureSwiftSupport/LayoutSpecBuilders": "3.13.0", + "TinyConstraints": "4.0.2", + }, + }, + { + name: "find hackage packages", + pkgType: pkg.HackagePkg, + pkgLanguage: pkg.Haskell, + pkgInfo: map[string]string{ + "Cabal": "3.2.1.0", + "Diff": "0.4.1", + "HTTP": "4000.3.16", + "HUnit": "1.6.2.0", + "OneTuple": "0.3.1", + "Only": "0.1", + "PyF": "0.10.2.0", + "QuickCheck": "2.14.2", + "RSA": "2.4.1", + "SHA": "1.6.4.4", + "Spock": "0.14.0.0", + "ShellCheck": "0.8.0", + "colourista": "0.1.0.1", + "language-docker": "11.0.0", + "spdx": "1.0.0.2", + "hspec": "2.9.4", + "hspec-core": "2.9.4", + "hspec-discover": "2.9.4", + "stm": "2.5.0.2", + "configurator-pg": "0.2.6", + "hasql-dynamic-statements": "0.3.1.1", + "hasql-implicits": "0.1.0.4", + "hasql-pool": "0.5.2.2", + "lens-aeson": "1.1.3", + "optparse-applicative": "0.16.1.0", + "protolude": "0.3.2", + "ptr": "0.16.8.2", + }, + }, +} + +var commonTestCases = []testCase{ + { + name: "find alpm packages", + pkgType: pkg.AlpmPkg, + pkgInfo: map[string]string{ + "pacman": "6.0.1-5", + }, + }, + { + name: "find rpmdb packages", + pkgType: pkg.RpmPkg, + pkgInfo: map[string]string{ + "dive": "0.9.2-1", + }, + }, + { + name: "find dpkg packages", + pkgType: pkg.DebPkg, + pkgInfo: map[string]string{ + "apt": "1.8.2", + "dash": "0.5.8-2.4", + "netbase": "5.4", + }, + }, + { + name: "find portage packages", + pkgType: pkg.PortagePkg, + pkgInfo: map[string]string{ + "app-containers/skopeo": "1.5.1", + }, + }, + + { + name: "find jenkins plugins", + pkgType: pkg.JenkinsPluginPkg, + pkgLanguage: pkg.Java, + duplicates: 1, // there is a "example-jenkins-plugin" HPI, and nested within that a JAR of the same name + pkgInfo: map[string]string{ + "example-jenkins-plugin": "1.0-SNAPSHOT", + }, + }, +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/catalog_packages_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/catalog_packages_test.go new file mode 100644 index 0000000000000000000000000000000000000000..3b2cd76931b36bb1cb49ac5f49b37bc2bcf46cab --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/catalog_packages_test.go @@ -0,0 +1,245 @@ +package integration + +import ( + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + + "github.com/anchore/syft/syft/linux" + "github.com/anchore/syft/syft/pkg/cataloger" + "github.com/google/go-cmp/cmp" + + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/anchore/syft/syft/source" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/pkg" +) + +func BenchmarkImagePackageCatalogers(b *testing.B) { + fixtureImageName := "image-pkg-coverage" + imagetest.GetFixtureImage(b, "docker-archive", fixtureImageName) + tarPath := imagetest.GetFixtureImageTarPath(b, fixtureImageName) + + var pc *pkg.Catalog + for _, c := range cataloger.ImageCatalogers(cataloger.DefaultConfig()) { + // in case of future alteration where state is persisted, assume no dependency is safe to reuse + userInput := "docker-archive:" + tarPath + sourceInput, err := source.ParseInput(userInput, "", false) + require.NoError(b, err) + theSource, cleanupSource, err := source.New(*sourceInput, nil, nil) + b.Cleanup(cleanupSource) + if err != nil { + b.Fatalf("unable to get source: %+v", err) + } + + resolver, err := theSource.FileResolver(source.SquashedScope) + if err != nil { + b.Fatalf("unable to get resolver: %+v", err) + } + + theDistro := linux.IdentifyRelease(resolver) + + b.Run(c.Name(), func(b *testing.B) { + for i := 0; i < b.N; i++ { + pc, _, err = cataloger.Catalog(resolver, theDistro, c) + if err != nil { + b.Fatalf("failure during benchmark: %+v", err) + } + } + }) + + b.Logf("catalog for %q number of packages: %d", c.Name(), pc.PackageCount()) + } +} + +func TestPkgCoverageImage(t *testing.T) { + sbom, _ := catalogFixtureImage(t, "image-pkg-coverage", source.SquashedScope, nil) + + observedLanguages := internal.NewStringSet() + definedLanguages := internal.NewStringSet() + for _, l := range pkg.AllLanguages { + definedLanguages.Add(l.String()) + } + + // for image scans we should not expect to see any of the following package types + definedLanguages.Remove(pkg.Go.String()) + definedLanguages.Remove(pkg.Rust.String()) + definedLanguages.Remove(pkg.Dart.String()) + definedLanguages.Remove(pkg.Dotnet.String()) + definedLanguages.Remove(string(pkg.Swift.String())) + definedLanguages.Remove(pkg.CPP.String()) + definedLanguages.Remove(pkg.Haskell.String()) + + observedPkgs := internal.NewStringSet() + definedPkgs := internal.NewStringSet() + for _, p := range pkg.AllPkgs { + definedPkgs.Add(string(p)) + } + + // for image scans we should not expect to see any of the following package types + definedPkgs.Remove(string(pkg.KbPkg)) + definedPkgs.Remove(string(pkg.GoModulePkg)) + definedPkgs.Remove(string(pkg.RustPkg)) + definedPkgs.Remove(string(pkg.DartPubPkg)) + definedPkgs.Remove(string(pkg.DotnetPkg)) + definedPkgs.Remove(string(pkg.CocoapodsPkg)) + definedPkgs.Remove(string(pkg.ConanPkg)) + definedPkgs.Remove(string(pkg.HackagePkg)) + + var cases []testCase + cases = append(cases, commonTestCases...) + cases = append(cases, imageOnlyTestCases...) + + for _, c := range cases { + t.Run(c.name, func(t *testing.T) { + pkgCount := 0 + + for a := range sbom.Artifacts.PackageCatalog.Enumerate(c.pkgType) { + if a.Language.String() != "" { + observedLanguages.Add(a.Language.String()) + } + + observedPkgs.Add(string(a.Type)) + expectedVersion, ok := c.pkgInfo[a.Name] + if !ok { + t.Errorf("unexpected package found: %s", a.Name) + } + + if expectedVersion != a.Version { + t.Errorf("unexpected package version (pkg=%s): %s, expected: %s", a.Name, a.Version, expectedVersion) + } + + if a.Language != c.pkgLanguage { + t.Errorf("bad language (pkg=%+v): %+v", a.Name, a.Language) + } + + if a.Type != c.pkgType { + t.Errorf("bad package type (pkg=%+v): %+v", a.Name, a.Type) + } + pkgCount++ + } + + if pkgCount != len(c.pkgInfo)+c.duplicates { + t.Logf("Discovered packages of type %+v", c.pkgType) + for a := range sbom.Artifacts.PackageCatalog.Enumerate(c.pkgType) { + t.Log(" ", a) + } + t.Fatalf("unexpected package count: %d!=%d", pkgCount, len(c.pkgInfo)) + } + + }) + } + + observedLanguages.Remove(pkg.UnknownLanguage.String()) + definedLanguages.Remove(pkg.UnknownLanguage.String()) + observedPkgs.Remove(string(pkg.UnknownPkg)) + definedPkgs.Remove(string(pkg.UnknownPkg)) + + // ensure that integration test cases stay in sync with the available catalogers + if diff := cmp.Diff(definedLanguages, observedLanguages); diff != "" { + t.Errorf("language coverage incomplete (languages=%d, coverage=%d)", len(definedLanguages), len(observedLanguages)) + t.Errorf("definedLanguages mismatch observedLanguages (-want +got):\n%s", diff) + } + + if diff := cmp.Diff(definedPkgs, observedPkgs); diff != "" { + t.Errorf("package coverage incomplete (packages=%d, coverage=%d)", len(definedPkgs), len(observedPkgs)) + t.Errorf("definedPkgs mismatch observedPkgs (-want +got):\n%s", diff) + } +} + +func TestPkgCoverageDirectory(t *testing.T) { + sbom, _ := catalogDirectory(t, "test-fixtures/image-pkg-coverage") + + observedLanguages := internal.NewStringSet() + definedLanguages := internal.NewStringSet() + for _, l := range pkg.AllLanguages { + definedLanguages.Add(l.String()) + } + + observedPkgs := internal.NewStringSet() + definedPkgs := internal.NewStringSet() + for _, p := range pkg.AllPkgs { + definedPkgs.Add(string(p)) + } + + var cases []testCase + cases = append(cases, commonTestCases...) + cases = append(cases, dirOnlyTestCases...) + + for _, test := range cases { + t.Run(test.name, func(t *testing.T) { + actualPkgCount := 0 + + for actualPkg := range sbom.Artifacts.PackageCatalog.Enumerate(test.pkgType) { + observedLanguages.Add(actualPkg.Language.String()) + observedPkgs.Add(string(actualPkg.Type)) + + expectedVersion, ok := test.pkgInfo[actualPkg.Name] + if !ok { + t.Errorf("unexpected package found: %s", actualPkg.Name) + } + + if expectedVersion != actualPkg.Version { + t.Errorf("unexpected package version (pkg=%s): %s", actualPkg.Name, actualPkg.Version) + } + + if actualPkg.Language != test.pkgLanguage { + t.Errorf("bad language (pkg=%+v): %+v", actualPkg.Name, actualPkg.Language) + } + + if actualPkg.Type != test.pkgType { + t.Errorf("bad package type (pkg=%+v): %+v", actualPkg.Name, actualPkg.Type) + } + actualPkgCount++ + } + + if actualPkgCount != len(test.pkgInfo)+test.duplicates { + for actualPkg := range sbom.Artifacts.PackageCatalog.Enumerate(test.pkgType) { + t.Log(" ", actualPkg) + } + t.Fatalf("unexpected package count: %d!=%d", actualPkgCount, len(test.pkgInfo)) + } + + }) + } + + observedLanguages.Remove(pkg.UnknownLanguage.String()) + definedLanguages.Remove(pkg.UnknownLanguage.String()) + observedPkgs.Remove(string(pkg.UnknownPkg)) + definedPkgs.Remove(string(pkg.UnknownPkg)) + + // for directory scans we should not expect to see any of the following package types + definedPkgs.Remove(string(pkg.KbPkg)) + + // ensure that integration test commonTestCases stay in sync with the available catalogers + if len(observedLanguages) < len(definedLanguages) { + t.Errorf("language coverage incomplete (languages=%d, coverage=%d)", len(definedLanguages), len(observedLanguages)) + } + + if len(observedPkgs) < len(definedPkgs) { + t.Errorf("package coverage incomplete (packages=%d, coverage=%d)", len(definedPkgs), len(observedPkgs)) + } +} + +func TestPkgCoverageCatalogerConfiguration(t *testing.T) { + // Check that cataloger configuration can be used to run a cataloger on a source + // for which that cataloger isn't enabled by defauly + sbom, _ := catalogFixtureImage(t, "image-pkg-coverage", source.SquashedScope, []string{"rust"}) + + observedLanguages := internal.NewStringSet() + definedLanguages := internal.NewStringSet() + definedLanguages.Add("rust") + + for actualPkg := range sbom.Artifacts.PackageCatalog.Enumerate() { + observedLanguages.Add(actualPkg.Language.String()) + } + + assert.Equal(t, definedLanguages, observedLanguages) + + // Verify that rust isn't actually an image cataloger + c := cataloger.DefaultConfig() + c.Catalogers = []string{"rust"} + assert.Len(t, cataloger.ImageCatalogers(c), 0) +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/convert_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/convert_test.go new file mode 100644 index 0000000000000000000000000000000000000000..1efed8a5a7a68c309152861022609aae00e253b3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/convert_test.go @@ -0,0 +1,74 @@ +package integration + +import ( + "context" + "io/ioutil" + "os" + "testing" + + "github.com/anchore/syft/cmd/syft/cli/convert" + "github.com/anchore/syft/internal/config" + "github.com/anchore/syft/internal/formats/cyclonedxjson" + "github.com/anchore/syft/internal/formats/cyclonedxxml" + "github.com/anchore/syft/internal/formats/spdx22json" + "github.com/anchore/syft/internal/formats/spdx22tagvalue" + "github.com/anchore/syft/internal/formats/syftjson" + "github.com/anchore/syft/internal/formats/table" + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/sbom" + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/require" +) + +var convertibleFormats = []sbom.Format{ + syftjson.Format(), + spdx22json.Format(), + spdx22tagvalue.Format(), + cyclonedxjson.Format(), + cyclonedxxml.Format(), +} + +// TestConvertCmd tests if the converted SBOM is a valid document according +// to spec. +// TODO: This test can, but currently does not, check the converted SBOM content. It +// might be useful to do that in the future, once we gather a better understanding of +// what users expect from the convert command. +func TestConvertCmd(t *testing.T) { + for _, format := range convertibleFormats { + t.Run(format.ID().String(), func(t *testing.T) { + sbom, _ := catalogFixtureImage(t, "image-pkg-coverage", source.SquashedScope, nil) + format := syft.FormatByID(syftjson.ID) + + f, err := ioutil.TempFile("", "test-convert-sbom-") + require.NoError(t, err) + defer func() { + os.Remove(f.Name()) + }() + + err = format.Encode(f, sbom) + require.NoError(t, err) + + ctx := context.Background() + app := &config.Application{Outputs: []string{format.ID().String()}} + + // stdout reduction of test noise + rescue := os.Stdout // keep backup of the real stdout + os.Stdout, _ = os.OpenFile(os.DevNull, os.O_APPEND|os.O_WRONLY, os.ModeAppend) + defer func() { + os.Stdout = rescue + }() + + err = convert.Run(ctx, app, []string{f.Name()}) + require.NoError(t, err) + file, err := ioutil.ReadFile(f.Name()) + require.NoError(t, err) + + formatFound := syft.IdentifyFormat(file) + if format.ID() == table.ID { + require.Nil(t, formatFound) + return + } + require.Equal(t, format.ID(), formatFound.ID()) + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/distro_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/distro_test.go new file mode 100644 index 0000000000000000000000000000000000000000..07360f6ebfbe5ecac1e0a348c6bbf666ac7c3a69 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/distro_test.go @@ -0,0 +1,26 @@ +package integration + +import ( + "testing" + + "github.com/anchore/syft/syft/source" + + "github.com/stretchr/testify/assert" + + "github.com/anchore/syft/syft/linux" +) + +func TestDistroImage(t *testing.T) { + sbom, _ := catalogFixtureImage(t, "image-distro-id", source.SquashedScope, nil) + + expected := &linux.Release{ + PrettyName: "BusyBox v1.31.1", + Name: "busybox", + ID: "busybox", + IDLike: []string{"busybox"}, + Version: "1.31.1", + VersionID: "1.31.1", + } + + assert.Equal(t, expected, sbom.Artifacts.LinuxDistribution) +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/encode_decode_cycle_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/encode_decode_cycle_test.go new file mode 100644 index 0000000000000000000000000000000000000000..bc9f0b4151e06d1217806e26465c6261730def30 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/encode_decode_cycle_test.go @@ -0,0 +1,102 @@ +package integration + +import ( + "bytes" + "fmt" + "regexp" + "testing" + + "github.com/anchore/syft/internal/formats/cyclonedxjson" + "github.com/anchore/syft/internal/formats/cyclonedxxml" + "github.com/anchore/syft/internal/formats/syftjson" + "github.com/anchore/syft/syft/source" + "github.com/google/go-cmp/cmp" + + "github.com/anchore/syft/syft/sbom" + "github.com/stretchr/testify/require" + + "github.com/anchore/syft/syft" + + "github.com/sergi/go-diff/diffmatchpatch" + + "github.com/stretchr/testify/assert" +) + +// TestEncodeDecodeEncodeCycleComparison is testing for differences in how SBOM documents get encoded on multiple cycles. +// By encoding and decoding the sbom we can compare the differences between the set of resulting objects. However, +// this requires specific comparisons being done, and select redactions/omissions being made. Additionally, there are +// already unit tests on each format encoder-decoder for properly functioning comparisons in depth, so there is no need +// to do an object-to-object comparison. For this reason this test focuses on a bytes-to-bytes comparison after an +// encode-decode-encode loop which will detect lossy behavior in both directions. +func TestEncodeDecodeEncodeCycleComparison(t *testing.T) { + // use second image for relationships + images := []string{"image-pkg-coverage", "image-owning-package"} + tests := []struct { + formatOption sbom.FormatID + redactor func(in []byte) []byte + json bool + }{ + { + formatOption: syftjson.ID, + redactor: func(in []byte) []byte { + in = regexp.MustCompile("\"(id|parent)\": \"[^\"]+\",").ReplaceAll(in, []byte{}) + return in + }, + json: true, + }, + { + formatOption: cyclonedxjson.ID, + redactor: func(in []byte) []byte { + in = regexp.MustCompile("\"(timestamp|serialNumber|bom-ref)\": \"[^\"]+\",").ReplaceAll(in, []byte{}) + return in + }, + json: true, + }, + { + formatOption: cyclonedxxml.ID, + redactor: func(in []byte) []byte { + in = regexp.MustCompile("(serialNumber|bom-ref)=\"[^\"]+\"").ReplaceAll(in, []byte{}) + in = regexp.MustCompile("[^<]+").ReplaceAll(in, []byte{}) + return in + }, + }, + } + + for _, test := range tests { + t.Run(fmt.Sprintf("%s", test.formatOption), func(t *testing.T) { + for _, image := range images { + originalSBOM, _ := catalogFixtureImage(t, image, source.SquashedScope, nil) + + format := syft.FormatByID(test.formatOption) + require.NotNil(t, format) + + by1, err := syft.Encode(originalSBOM, format) + assert.NoError(t, err) + + newSBOM, newFormat, err := syft.Decode(bytes.NewReader(by1)) + assert.NoError(t, err) + assert.Equal(t, format.ID(), newFormat.ID()) + + by2, err := syft.Encode(*newSBOM, format) + assert.NoError(t, err) + + if test.redactor != nil { + by1 = test.redactor(by1) + by2 = test.redactor(by2) + } + + if test.json { + s1 := string(by1) + s2 := string(by2) + if diff := cmp.Diff(s1, s2); diff != "" { + t.Errorf("Encode/Decode mismatch (-want +got):\n%s", diff) + } + } else if !assert.True(t, bytes.Equal(by1, by2)) { + dmp := diffmatchpatch.New() + diffs := dmp.DiffMain(string(by1), string(by2), true) + t.Errorf("diff: %s", dmp.DiffPrettyText(diffs)) + } + } + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/license_list_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/license_list_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e0e384123b87782df6345195cf5fed9ddf8c6613 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/license_list_test.go @@ -0,0 +1,36 @@ +package integration + +import ( + "encoding/json" + "net/http" + "testing" + + "github.com/anchore/syft/internal/spdxlicense" + "github.com/stretchr/testify/assert" +) + +func TestSPDXLicenseListIsTheLatest(t *testing.T) { + resp, err := http.Get("https://spdx.org/licenses/licenses.json") + if err != nil { + t.Fatalf("unable to get licenses list: %+v", err) + } + + type licenseList struct { + Version string `json:"licenseListVersion"` + Licenses []struct { + ID string `json:"licenseId"` + Name string `json:"name"` + Text string `json:"licenseText"` + Deprecated bool `json:"isDeprecatedLicenseId"` + OSIApproved bool `json:"isOsiApproved"` + SeeAlso []string `json:"seeAlso"` + } `json:"licenses"` + } + + var latest licenseList + if err = json.NewDecoder(resp.Body).Decode(&latest); err != nil { + t.Fatalf("unable to decode license list: %+v", err) + } + + assert.Equal(t, latest.Version, spdxlicense.Version) +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/mariner_distroless_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/mariner_distroless_test.go new file mode 100644 index 0000000000000000000000000000000000000000..b54c1c073d927b2e4a76dabbdacc550efe1130c7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/mariner_distroless_test.go @@ -0,0 +1,22 @@ +package integration + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +func TestMarinerDistroless(t *testing.T) { + sbom, _ := catalogFixtureImage(t, "image-mariner-distroless", source.SquashedScope, nil) + + expectedPkgs := 12 + actualPkgs := 0 + for range sbom.Artifacts.PackageCatalog.Enumerate(pkg.RpmPkg) { + actualPkgs += 1 + } + + if actualPkgs != expectedPkgs { + t.Errorf("unexpected number of RPM packages: %d != %d", expectedPkgs, actualPkgs) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/node_packages_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/node_packages_test.go new file mode 100644 index 0000000000000000000000000000000000000000..071b96a56fce9e7fc842da72518ece5f8745cd5c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/node_packages_test.go @@ -0,0 +1,54 @@ +package integration + +import ( + "reflect" + "strings" + "testing" + + "github.com/anchore/syft/internal" + "github.com/anchore/syft/syft/pkg" +) + +func TestNpmPackageLockDirectory(t *testing.T) { + sbom, _ := catalogDirectory(t, "test-fixtures/npm-lock") + + foundPackages := internal.NewStringSet() + + for actualPkg := range sbom.Artifacts.PackageCatalog.Enumerate(pkg.NpmPkg) { + for _, actualLocation := range actualPkg.Locations.ToSlice() { + if strings.Contains(actualLocation.RealPath, "node_modules") { + t.Errorf("found packages from package-lock.json in node_modules: %s", actualLocation) + } + } + foundPackages.Add(actualPkg.Name) + } + + // ensure that integration test commonTestCases stay in sync with the available catalogers + const expectedPackageCount = 6 + if len(foundPackages) != expectedPackageCount { + t.Errorf("found the wrong set of npm package-lock.json packages (expected: %d, actual: %d)", expectedPackageCount, len(foundPackages)) + } +} + +func TestYarnPackageLockDirectory(t *testing.T) { + sbom, _ := catalogDirectory(t, "test-fixtures/yarn-lock") + + foundPackages := internal.NewStringSet() + expectedPackages := internal.NewStringSet("async@0.9.2", "async@3.2.3", "merge-objects@1.0.5", "should-type@1.3.0", "@4lolo/resize-observer-polyfill@1.5.2") + + for actualPkg := range sbom.Artifacts.PackageCatalog.Enumerate(pkg.NpmPkg) { + for _, actualLocation := range actualPkg.Locations.ToSlice() { + if strings.Contains(actualLocation.RealPath, "node_modules") { + t.Errorf("found packages from yarn.lock in node_modules: %s", actualLocation) + } + } + foundPackages.Add(actualPkg.Name + "@" + actualPkg.Version) + } + + // ensure that integration test commonTestCases stay in sync with the available catalogers + if len(foundPackages) != len(expectedPackages) { + t.Errorf("found the wrong set of yarn.lock packages (expected: %d, actual: %d)", len(expectedPackages), len(foundPackages)) + } else if !reflect.DeepEqual(foundPackages, expectedPackages) { + t.Errorf("found the wrong set of yarn.lock packages (expected: %+q, actual: %+q)", expectedPackages.ToSlice(), foundPackages.ToSlice()) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/package_deduplication_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/package_deduplication_test.go new file mode 100644 index 0000000000000000000000000000000000000000..4e9171b18f89ee68a1e82f463cce29b1e66b96e6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/package_deduplication_test.go @@ -0,0 +1,87 @@ +//go:build !arm64 + +package integration + +import ( + "fmt" + "testing" + + "github.com/anchore/syft/syft/source" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" +) + +func TestPackageDeduplication(t *testing.T) { + tests := []struct { + scope source.Scope + packageCount int + instanceCount map[string]int + locationCount map[string]int + }{ + { + scope: source.AllLayersScope, + packageCount: 172, // without deduplication this would be 618 + instanceCount: map[string]int{ + "basesystem": 1, + "wget": 1, + "curl": 2, // upgraded in the image + "vsftpd": 1, + "httpd": 1, + }, + locationCount: map[string]int{ + "basesystem-10.0-7.el7.centos": 4, + "curl-7.29.0-59.el7": 1, // from base image + "curl-7.29.0-59.el7_9.1": 3, // upgrade + "wget-1.14-18.el7_6.1": 3, + "vsftpd-3.0.2-29.el7_9": 2, + "httpd-2.4.6-97.el7.centos.5": 1, + }, + }, + { + scope: source.SquashedScope, + packageCount: 170, + instanceCount: map[string]int{ + "basesystem": 1, + "wget": 1, + "curl": 1, // upgraded, but the most recent + "vsftpd": 1, + "httpd": 1, + }, + locationCount: map[string]int{ + "basesystem-10.0-7.el7.centos": 1, + "curl-7.29.0-59.el7_9.1": 1, // upgrade + "wget-1.14-18.el7_6.1": 1, + "vsftpd-3.0.2-29.el7_9": 1, + "httpd-2.4.6-97.el7.centos.5": 1, + }, + }, + } + + for _, tt := range tests { + t.Run(string(tt.scope), func(t *testing.T) { + sbom, _ := catalogFixtureImage(t, "image-vertical-package-dups", tt.scope, nil) + + assert.Equal(t, tt.packageCount, sbom.Artifacts.PackageCatalog.PackageCount()) + for name, expectedInstanceCount := range tt.instanceCount { + pkgs := sbom.Artifacts.PackageCatalog.PackagesByName(name) + + // with multiple packages with the same name, something is wrong (or this is the wrong fixture) + require.Len(t, pkgs, expectedInstanceCount) + for _, p := range pkgs { + nameVersion := fmt.Sprintf("%s-%s", name, p.Version) + expectedLocationCount, ok := tt.locationCount[nameVersion] + if !ok { + t.Fatalf("missing name-version: %s", nameVersion) + } + + // we should see merged locations (assumption, there was 1 location for each package) + assert.Len(t, p.Locations.ToSlice(), expectedLocationCount) + + // all paths should match + assert.Len(t, p.Locations.CoordinateSet().Paths(), 1) + } + } + + }) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/package_ownership_relationship_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/package_ownership_relationship_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e85cd88db43c3156126a21272202fd11a3e4ed1c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/package_ownership_relationship_test.go @@ -0,0 +1,48 @@ +package integration + +import ( + "bytes" + "encoding/json" + "testing" + + "github.com/anchore/syft/syft/source" + + "github.com/anchore/syft/internal/formats/syftjson" + syftjsonModel "github.com/anchore/syft/internal/formats/syftjson/model" +) + +func TestPackageOwnershipRelationships(t *testing.T) { + + // ensure that the json encoder is applying artifact ownership with an image that has expected ownership relationships + tests := []struct { + fixture string + }{ + { + fixture: "image-owning-package", + }, + } + + for _, test := range tests { + t.Run(test.fixture, func(t *testing.T) { + sbom, _ := catalogFixtureImage(t, test.fixture, source.SquashedScope, nil) + + output := bytes.NewBufferString("") + err := syftjson.Format().Encode(output, sbom) + if err != nil { + t.Fatalf("unable to present: %+v", err) + } + + var doc syftjsonModel.Document + decoder := json.NewDecoder(output) + if err := decoder.Decode(&doc); err != nil { + t.Fatalf("unable to decode json doc: %+v", err) + } + + if len(doc.ArtifactRelationships) == 0 { + t.Errorf("expected to find relationships between packages but found none") + } + + }) + } + +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/regression_apk_scanner_buffer_size_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/regression_apk_scanner_buffer_size_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e6fdf58dd0c4c3edfdd8719261c9d33d37344560 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/regression_apk_scanner_buffer_size_test.go @@ -0,0 +1,25 @@ +package integration + +import ( + "testing" + + "github.com/anchore/syft/syft/source" + + "github.com/anchore/syft/syft/pkg" +) + +func TestRegression212ApkBufferSize(t *testing.T) { + // This is a regression test for issue #212 (https://github.com/anchore/syft/issues/212) in which the apk db could + // not be processed due to a scanner buffer that was too small + sbom, _ := catalogFixtureImage(t, "image-large-apk-data", source.SquashedScope, nil) + + expectedPkgs := 58 + actualPkgs := 0 + for range sbom.Artifacts.PackageCatalog.Enumerate(pkg.ApkPkg) { + actualPkgs += 1 + } + + if actualPkgs != expectedPkgs { + t.Errorf("unexpected number of APK packages: %d != %d", expectedPkgs, actualPkgs) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/regression_go_bin_scanner_arch_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/regression_go_bin_scanner_arch_test.go new file mode 100644 index 0000000000000000000000000000000000000000..a0ae70c8526832afcb4192412ac525335f3218fb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/regression_go_bin_scanner_arch_test.go @@ -0,0 +1,50 @@ +package integration + +import ( + "strings" + "testing" + + "github.com/anchore/syft/syft/source" + + "github.com/anchore/syft/syft/pkg" +) + +func TestRegressionGoArchDiscovery(t *testing.T) { + const ( + expectedELFPkg = 4 + expectedWINPkg = 4 + expectedMACOSPkg = 4 + ) + // This is a regression test to make sure the way we detect go binary packages + // stays consistent and reproducible as the tool chain evolves + sbom, _ := catalogFixtureImage(t, "image-go-bin-arch-coverage", source.SquashedScope, nil) + + var actualELF, actualWIN, actualMACOS int + + for p := range sbom.Artifacts.PackageCatalog.Enumerate(pkg.GoModulePkg) { + for _, l := range p.Locations.ToSlice() { + switch { + case strings.Contains(l.RealPath, "elf"): + actualELF++ + case strings.Contains(l.RealPath, "win"): + actualWIN++ + case strings.Contains(l.RealPath, "macos"): + actualMACOS++ + default: + + } + } + } + + if actualELF != expectedELFPkg { + t.Errorf("unexpected number of elf packages: %d != %d", expectedELFPkg, actualELF) + } + + if actualWIN != expectedWINPkg { + t.Errorf("unexpected number of win packages: %d != %d", expectedWINPkg, actualWIN) + } + + if actualMACOS != expectedMACOSPkg { + t.Errorf("unexpected number of macos packages: %d != %d", expectedMACOSPkg, actualMACOS) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/regression_java_no_main_package_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/regression_java_no_main_package_test.go new file mode 100644 index 0000000000000000000000000000000000000000..102271ec8c93e75fc88997c3f02f0930e9a767be --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/regression_java_no_main_package_test.go @@ -0,0 +1,11 @@ +package integration + +import ( + "testing" + + "github.com/anchore/syft/syft/source" +) + +func TestRegressionJavaNoMainPackage(t *testing.T) { // Regression: https://github.com/anchore/syft/issues/252 + catalogFixtureImage(t, "image-java-no-main-package", source.SquashedScope, nil) +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/rust_audit_binary_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/rust_audit_binary_test.go new file mode 100644 index 0000000000000000000000000000000000000000..d97c9c7388712149973d4f4c7737e73440d2b4ca --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/rust_audit_binary_test.go @@ -0,0 +1,22 @@ +package integration + +import ( + "testing" + + "github.com/anchore/syft/syft/pkg" + "github.com/anchore/syft/syft/source" +) + +func TestRustAudit(t *testing.T) { + sbom, _ := catalogFixtureImage(t, "image-rust-auditable", source.SquashedScope, []string{"all"}) + + expectedPkgs := 2 + actualPkgs := 0 + for range sbom.Artifacts.PackageCatalog.Enumerate(pkg.RustPkg) { + actualPkgs += 1 + } + + if actualPkgs != expectedPkgs { + t.Errorf("unexpected number of Rust packages: %d != %d", expectedPkgs, actualPkgs) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/sqlite_rpmdb_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/sqlite_rpmdb_test.go new file mode 100644 index 0000000000000000000000000000000000000000..73b78045104bd04c33ca4ba5254c92081a661252 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/sqlite_rpmdb_test.go @@ -0,0 +1,25 @@ +package integration + +import ( + "testing" + + "github.com/anchore/syft/syft/source" + + "github.com/anchore/syft/syft/pkg" +) + +func TestSqliteRpm(t *testing.T) { + // This is a regression test for issue #469 (https://github.com/anchore/syft/issues/469). Recent RPM + // based distribution store package data in an sqlite database + sbom, _ := catalogFixtureImage(t, "image-sqlite-rpmdb", source.SquashedScope, nil) + + expectedPkgs := 139 + actualPkgs := 0 + for range sbom.Artifacts.PackageCatalog.Enumerate(pkg.RpmPkg) { + actualPkgs += 1 + } + + if actualPkgs != expectedPkgs { + t.Errorf("unexpected number of RPM packages: %d != %d", expectedPkgs, actualPkgs) + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/.gitignore b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..6878560211946e76ef7e2d8990727921f2cc27e6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/.gitignore @@ -0,0 +1,7 @@ +# we should strive to not commit blobs to the repo and strive to keep the build process of how blobs are acquired in-repo. +# this blob is generated from syft/syft/catalogers/java/test-fixtures/java-builds , however, preserving the build process +# twice in the repo seems redundant (even via symlink). Given that the fixture is a few kilobytes in size, the build process is already +# captured, and integration tests should only be testing if jars can be discovered (not necessarily depth in java detection +# functionality), committing it seems like an acceptable exception. +!image-pkg-coverage/pkgs/java/*.jar +!image-pkg-coverage/pkgs/java/*.hpi diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-distro-id/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-distro-id/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..400d030326f61eeab468775c22ede5ed3de9642c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-distro-id/Dockerfile @@ -0,0 +1,3 @@ +FROM busybox:1.31.1 + + diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..7b252568c8c1ed3100921e309be861289a16e7f3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/Dockerfile @@ -0,0 +1,16 @@ +FROM golang:latest as builder +WORKDIR /app +COPY go.sum go.mod app.go ./ + +RUN GOOS=linux go build -o elf . +RUN GOOS=windows go build -o win . +RUN GOOS=darwin go build -o macos . + +FROM scratch + +WORKDIR /tmp +COPY --from=builder /app/elf / +COPY --from=builder /app/win / +COPY --from=builder /app/macos / + +ENTRYPOINT ["/elf"] diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/app.go b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/app.go new file mode 100644 index 0000000000000000000000000000000000000000..8747558d66485172d666efdb0109037f39b82d3c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/app.go @@ -0,0 +1,18 @@ +//build:ignore +package main + +import ( + "fmt" + "os" + + "golang.org/x/net/html" + "golang.org/x/term" +) + +var test = html.ErrBufferExceeded + +func main() { + t := term.NewTerminal(os.Stdout, "foo") + t.Write([]byte("hello anchore")) + t.Write([]byte(fmt.Sprintf("%v", test))) +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/go.mod b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/go.mod new file mode 100644 index 0000000000000000000000000000000000000000..4add6f7dc058293d367f24bb552d4d4ba76cf2ea --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/go.mod @@ -0,0 +1,14 @@ +module github.com/anchore/test + +go 1.17 + +require ( + golang.org/x/net v0.0.0-20211006190231-62292e806868 + golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 +) + +require golang.org/x/sys v0.0.0-20211006194710-c8a6f5223071 // indirect + +exclude golang.org/x/net v0.0.0-20211005215030-d2e5035098b3 + +replace golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 => golang.org/x/term v0.0.0-20210916214954-140adaaadfaf diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/go.sum b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/go.sum new file mode 100644 index 0000000000000000000000000000000000000000..832264401b67ff5f96892be7f7c098a66a251ab7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/go.sum @@ -0,0 +1,12 @@ +golang.org/x/net v0.0.0-20211006190231-62292e806868 h1:KlOXYy8wQWTUJYFgkUI40Lzr06ofg5IRXUK5C7qZt1k= +golang.org/x/net v0.0.0-20211006190231-62292e806868/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211006194710-c8a6f5223071 h1:PjhxBct4MZii8FFR8+oeS7QOvxKOTZXgk63EU2XpfJE= +golang.org/x/sys v0.0.0-20211006194710-c8a6f5223071/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= +golang.org/x/term v0.0.0-20210916214954-140adaaadfaf h1:Ihq/mm/suC88gF8WFcVwk+OV6Tq+wyA1O0E5UEvDglI= +golang.org/x/term v0.0.0-20210916214954-140adaaadfaf/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= +golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/test b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/test new file mode 100755 index 0000000000000000000000000000000000000000..a2387312562844e39ced0d635336a8782b974a99 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-go-bin-arch-coverage/test differ diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-java-no-main-package/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-java-no-main-package/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..7e1ac4de7ec37ec10d9ef3923bbd8b3e9de24c4b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-java-no-main-package/Dockerfile @@ -0,0 +1,23 @@ +FROM jenkins/jenkins:2.346.3-slim-jdk17 + +USER root + +WORKDIR /usr/share/jenkins + +RUN mkdir tmp + +WORKDIR /usr/share/jenkins/tmp + +RUN apt-get update 2>&1 > /dev/null && apt-get install -y less zip 2>&1 > /dev/null + +RUN unzip ../jenkins.war 2>&1 > /dev/null + +RUN rm -f ./META-INF/MANIFEST.MF + +WORKDIR /usr/share/jenkins + +RUN rm -rf jenkins.war + +RUN cd ./tmp && zip -r ../jenkins.war . && cd .. + +RUN rm -rf ./tmp diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-large-apk-data/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-large-apk-data/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..8187870a863224cbc58435fab1f81b7bc00dbb9e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-large-apk-data/Dockerfile @@ -0,0 +1,8 @@ +FROM alpine@sha256:d9a7354e3845ea8466bb00b22224d9116b183e594527fb5b6c3d30bc01a20378 + +# we keep these unpinned so that if alpine +# changes our integration tests can adapt +RUN apk add --no-cache \ + tzdata \ + vim \ + alpine-sdk diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-mariner-distroless/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-mariner-distroless/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..6a6e08f61cc3a489c534f9507a446230480a0605 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-mariner-distroless/Dockerfile @@ -0,0 +1 @@ +FROM mcr.microsoft.com/cbl-mariner/distroless/base:2.0.202205275@sha256:f550c5428df17b145851ad75983aca6d613ad4b51ca7983b2a83e67d0ac91a5d diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-owning-package/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-owning-package/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..37346c9c79004399c84d31ab457e3a118b664c4e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-owning-package/Dockerfile @@ -0,0 +1,3 @@ +FROM ubuntu:20.04 +# this covers rpm-python +RUN apt-get update && apt-get install -y python-pil=6.2.1-3 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..2f838567b4cb636a3b2c49cd53a0473aa88645c6 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/Dockerfile @@ -0,0 +1,5 @@ +FROM scratch +COPY pkgs/ . +# we duplicate to show a package count difference between all-layers and squashed scopes +COPY lib lib +COPY etc/ . \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/cocoapods/Podfile.lock b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/cocoapods/Podfile.lock new file mode 100644 index 0000000000000000000000000000000000000000..4d82d8ef2d125220bf715a00051d5ae8536b0465 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/cocoapods/Podfile.lock @@ -0,0 +1,92 @@ +PODS: + - GlossButtonNode (3.1.2): + - Texture/Core (~> 3) + - TextureSwiftSupport (>= 3.10.0) + - PINCache (3.0.3): + - PINCache/Arc-exception-safe (= 3.0.3) + - PINCache/Core (= 3.0.3) + - PINCache/Arc-exception-safe (3.0.3): + - PINCache/Core + - PINCache/Core (3.0.3): + - PINOperation (~> 1.2.1) + - PINOperation (1.2.1) + - PINRemoteImage/Core (3.0.3): + - PINOperation + - PINRemoteImage/iOS (3.0.3): + - PINRemoteImage/Core + - PINRemoteImage/PINCache (3.0.3): + - PINCache (~> 3.0.3) + - PINRemoteImage/Core + - Reveal-SDK (33) + - SwiftGen (6.5.1) + - Texture (3.1.0): + - Texture/AssetsLibrary (= 3.1.0) + - Texture/Core (= 3.1.0) + - Texture/MapKit (= 3.1.0) + - Texture/Photos (= 3.1.0) + - Texture/PINRemoteImage (= 3.1.0) + - Texture/Video (= 3.1.0) + - Texture/AssetsLibrary (3.1.0): + - Texture/Core + - Texture/Core (3.1.0) + - Texture/MapKit (3.1.0): + - Texture/Core + - Texture/Photos (3.1.0): + - Texture/Core + - Texture/PINRemoteImage (3.1.0): + - PINRemoteImage/iOS (~> 3.0.0) + - PINRemoteImage/PINCache + - Texture/Core + - Texture/Video (3.1.0): + - Texture/Core + - TextureSwiftSupport (3.13.0): + - Texture/Core (>= 3) + - TextureSwiftSupport/Components (= 3.13.0) + - TextureSwiftSupport/Experiments (= 3.13.0) + - TextureSwiftSupport/Extensions (= 3.13.0) + - TextureSwiftSupport/LayoutSpecBuilders (= 3.13.0) + - TextureSwiftSupport/Components (3.13.0): + - Texture/Core (>= 3) + - TextureSwiftSupport/LayoutSpecBuilders + - TextureSwiftSupport/Experiments (3.13.0): + - Texture/Core (>= 3) + - TextureSwiftSupport/Extensions (3.13.0): + - Texture/Core (>= 3) + - TextureSwiftSupport/LayoutSpecBuilders (3.13.0): + - Texture/Core (>= 3) + - TinyConstraints (4.0.2) + +DEPENDENCIES: + - GlossButtonNode + - Reveal-SDK + - SwiftGen + - Texture + - TextureSwiftSupport + - TinyConstraints + +SPEC REPOS: + trunk: + - GlossButtonNode + - PINCache + - PINOperation + - PINRemoteImage + - Reveal-SDK + - SwiftGen + - Texture + - TextureSwiftSupport + - TinyConstraints + +SPEC CHECKSUMS: + GlossButtonNode: 4ea1197a744f2fb5fb875fe31caf17ded4762e8f + PINCache: 7a8fc1a691173d21dbddbf86cd515de6efa55086 + PINOperation: 00c935935f1e8cf0d1e2d6b542e75b88fc3e5e20 + PINRemoteImage: f1295b29f8c5e640e25335a1b2bd9d805171bd01 + Reveal-SDK: effba1c940b8337195563c425a6b5862ec875caa + SwiftGen: a6d22010845f08fe18fbdf3a07a8e380fd22e0ea + Texture: 2e8ab2519452515f7f5a520f5a8f7e0a413abfa3 + TextureSwiftSupport: c515c7927fab92d0d9485f49b885b8c5de34fbfb + TinyConstraints: 7b7ccc0c485bb3bb47082138ff28bc33cd49897f + +PODFILE CHECKSUM: 07aa55f54421f6e6d3a920c11716a89fc9243d1b + +COCOAPODS: 1.11.2 diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/composer/composer.lock b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/composer/composer.lock new file mode 100644 index 0000000000000000000000000000000000000000..b9388fd7b370c6406176e47efc7a343ede88a98b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/composer/composer.lock @@ -0,0 +1,298 @@ +{ + "_readme": [ + "This file locks the dependencies of your project to a known state", + "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", + "This file is @generated automatically" + ], + "content-hash": "746ba78c06aef0cf954135ea909f9eb9", + "packages": [ + { + "name": "adoy/fastcgi-client", + "version": "1.0.2", + "source": { + "type": "git", + "url": "https://github.com/adoy/PHP-FastCGI-Client.git", + "reference": "6d9a552f0206a1db7feb442824540aa6c55e5b27" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/adoy/PHP-FastCGI-Client/zipball/6d9a552f0206a1db7feb442824540aa6c55e5b27", + "reference": "6d9a552f0206a1db7feb442824540aa6c55e5b27", + "shasum": "" + }, + "type": "library", + "autoload": { + "psr-0": { + "Adoy\\FastCGI\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Pierrick Charron", + "email": "pierrick@adoy.net" + } + ], + "description": "Lightweight, single file FastCGI client for PHP.", + "keywords": [ + "fastcgi", + "fcgi" + ], + "time": "2019-12-11T13:49:21+00:00" + }, + { + "name": "alcaeus/mongo-php-adapter", + "version": "1.1.11", + "source": { + "type": "git", + "url": "https://github.com/alcaeus/mongo-php-adapter.git", + "reference": "43b6add94c8b4cb9890d662cba4c0defde733dcf" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/alcaeus/mongo-php-adapter/zipball/43b6add94c8b4cb9890d662cba4c0defde733dcf", + "reference": "43b6add94c8b4cb9890d662cba4c0defde733dcf", + "shasum": "" + }, + "require": { + "ext-ctype": "*", + "ext-hash": "*", + "ext-mongodb": "^1.2.0", + "mongodb/mongodb": "^1.0.1", + "php": "^5.6 || ^7.0" + }, + "provide": { + "ext-mongo": "1.6.14" + }, + "require-dev": { + "phpunit/phpunit": "^5.7.27 || ^6.0 || ^7.0", + "squizlabs/php_codesniffer": "^3.2" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.1.x-dev" + } + }, + "autoload": { + "psr-0": { + "Mongo": "lib/Mongo" + }, + "psr-4": { + "Alcaeus\\MongoDbAdapter\\": "lib/Alcaeus/MongoDbAdapter" + }, + "files": [ + "lib/Mongo/functions.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "alcaeus", + "email": "alcaeus@alcaeus.org" + }, + { + "name": "Olivier Lechevalier", + "email": "olivier.lechevalier@gmail.com" + } + ], + "description": "Adapter to provide ext-mongo interface on top of mongo-php-libary", + "keywords": [ + "database", + "mongodb" + ], + "time": "2019-11-11T20:47:32+00:00" + } + ], + "packages-dev": [ + { + "name": "behat/gherkin", + "version": "v4.6.2", + "source": { + "type": "git", + "url": "https://github.com/Behat/Gherkin.git", + "reference": "51ac4500c4dc30cbaaabcd2f25694299df666a31" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/Behat/Gherkin/zipball/51ac4500c4dc30cbaaabcd2f25694299df666a31", + "reference": "51ac4500c4dc30cbaaabcd2f25694299df666a31", + "shasum": "" + }, + "require": { + "php": ">=5.3.1" + }, + "require-dev": { + "phpunit/phpunit": "~4.5|~5", + "symfony/phpunit-bridge": "~2.7|~3|~4", + "symfony/yaml": "~2.3|~3|~4" + }, + "suggest": { + "symfony/yaml": "If you want to parse features, represented in YAML files" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.4-dev" + } + }, + "autoload": { + "psr-0": { + "Behat\\Gherkin": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Konstantin Kudryashov", + "email": "ever.zet@gmail.com", + "homepage": "http://everzet.com" + } + ], + "description": "Gherkin DSL parser for PHP 5.3", + "homepage": "http://behat.org/", + "keywords": [ + "BDD", + "Behat", + "Cucumber", + "DSL", + "gherkin", + "parser" + ], + "time": "2020-03-17T14:03:26+00:00" + }, + { + "name": "codeception/codeception", + "version": "4.1.6", + "source": { + "type": "git", + "url": "https://github.com/Codeception/Codeception.git", + "reference": "5515b6a6c6f1e1c909aaff2e5f3a15c177dfd1a9" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/Codeception/Codeception/zipball/5515b6a6c6f1e1c909aaff2e5f3a15c177dfd1a9", + "reference": "5515b6a6c6f1e1c909aaff2e5f3a15c177dfd1a9", + "shasum": "" + }, + "require": { + "behat/gherkin": "^4.4.0", + "codeception/lib-asserts": "^1.0", + "codeception/phpunit-wrapper": ">6.0.15 <6.1.0 | ^6.6.1 | ^7.7.1 | ^8.1.1 | ^9.0", + "codeception/stub": "^2.0 | ^3.0", + "ext-curl": "*", + "ext-json": "*", + "ext-mbstring": "*", + "guzzlehttp/psr7": "~1.4", + "php": ">=5.6.0 <8.0", + "symfony/console": ">=2.7 <6.0", + "symfony/css-selector": ">=2.7 <6.0", + "symfony/event-dispatcher": ">=2.7 <6.0", + "symfony/finder": ">=2.7 <6.0", + "symfony/yaml": ">=2.7 <6.0" + }, + "require-dev": { + "codeception/module-asserts": "*@dev", + "codeception/module-cli": "*@dev", + "codeception/module-db": "*@dev", + "codeception/module-filesystem": "*@dev", + "codeception/module-phpbrowser": "*@dev", + "codeception/specify": "~0.3", + "codeception/util-universalframework": "*@dev", + "monolog/monolog": "~1.8", + "squizlabs/php_codesniffer": "~2.0", + "symfony/process": ">=2.7 <6.0", + "vlucas/phpdotenv": "^2.0 | ^3.0 | ^4.0" + }, + "suggest": { + "codeception/specify": "BDD-style code blocks", + "codeception/verify": "BDD-style assertions", + "hoa/console": "For interactive console functionality", + "stecman/symfony-console-completion": "For BASH autocompletion", + "symfony/phpunit-bridge": "For phpunit-bridge support" + }, + "bin": [ + "codecept" + ], + "type": "library", + "extra": { + "branch-alias": [] + }, + "autoload": { + "psr-4": { + "Codeception\\": "src/Codeception", + "Codeception\\Extension\\": "ext" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Bodnarchuk", + "email": "davert@mail.ua", + "homepage": "http://codegyre.com" + } + ], + "description": "BDD-style testing framework", + "homepage": "http://codeception.com/", + "keywords": [ + "BDD", + "TDD", + "acceptance testing", + "functional testing", + "unit testing" + ], + "time": "2020-06-07T16:31:51+00:00" + } + ], + "aliases": [], + "minimum-stability": "stable", + "stability-flags": { + "intelligence/bt-base": 20, + "intelligence/bt-common": 20, + "intelligence/bt-lib-tools": 20, + "intelligence/ci-lib-cache": 20, + "intelligence/ci-lib-client": 20, + "intelligence/ci-lib-contributed": 20, + "intelligence/ci-lib-eav": 20, + "intelligence/ci-lib-report": 20, + "intelligence/git-leaks-elastic-client": 20, + "intelligence/phishing-elastic-client": 20, + "libs/gib-sso-client": 20, + "mozhin/phplib": 20 + }, + "prefer-stable": false, + "prefer-lowest": false, + "platform": { + "php": "^7.4.0", + "ext-amqp": "^1.9", + "ext-ctype": "*", + "ext-curl": "^7.4", + "ext-date": "^7.4", + "ext-fileinfo": "*", + "ext-geoip": "^1.1", + "ext-gettext": "*", + "ext-iconv": "*", + "ext-imagick": "^3.4", + "ext-imap": "^7.4", + "ext-intl": "^7.4", + "ext-json": "*", + "ext-mbstring": "^7.4", + "ext-mongodb": "^1.4", + "ext-mysqli": "^7.4", + "ext-pdo_mysql": "^7.4", + "ext-redis": ">=3.1" + }, + "platform-dev": [] +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/conan/conanfile.txt b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/conan/conanfile.txt new file mode 100644 index 0000000000000000000000000000000000000000..c265b1328f21908b3d2672e6fb1be11b3f19cca4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/conan/conanfile.txt @@ -0,0 +1,12 @@ +# Docs at https://docs.conan.io/en/latest/reference/conanfile_txt.html + +[requires] +catch2/2.13.8 +docopt.cpp/0.6.3 +fmt/8.1.1 +spdlog/1.9.2 +sdl/2.0.20 +fltk/1.3.8 + +[generators] +cmake_find_package_multi diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/etc/os-release b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/etc/os-release new file mode 100644 index 0000000000000000000000000000000000000000..e07dd980dbf0e957cc2fc48a0c423505623ec643 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/etc/os-release @@ -0,0 +1,12 @@ +NAME="Ubuntu" +VERSION="20.04 LTS (Focal Fossa)" +ID=ubuntu +ID_LIKE=debian +PRETTY_NAME="Ubuntu 20.04 LTS" +VERSION_ID="20.04" +HOME_URL="https://www.ubuntu.com/" +SUPPORT_URL="https://help.ubuntu.com/" +BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/" +PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy" +VERSION_CODENAME=focal +UBUNTU_CODENAME=focal diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/cabal.project.freeze b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/cabal.project.freeze new file mode 100644 index 0000000000000000000000000000000000000000..f206bbb46716c075a408decce0f55ca7bcabf2d0 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/cabal.project.freeze @@ -0,0 +1,16 @@ +active-repositories: hackage.haskell.org:merge +constraints: any.Cabal ==3.2.1.0, + any.Diff ==0.4.1, + any.HUnit ==1.6.2.0, + any.OneTuple ==0.3.1, + tls +compat -hans +network, + any.Only ==0.1, + any.PyF ==0.10.2.0, + any.QuickCheck ==2.14.2, + semigroups +binary +bytestring -bytestring-builder +containers +deepseq +hashable +tagged +template-haskell +text +transformers +unordered-containers, + any.RSA ==2.4.1, + any.SHA ==1.6.4.4, + void -safe, + any.Spock ==0.14.0.0, + +index-state: hackage.haskell.org 2022-07-07T01:01:53Z diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/stack.yaml b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/stack.yaml new file mode 100644 index 0000000000000000000000000000000000000000..8c05906e1b01d759f87186336e32023409fd3a3a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/stack.yaml @@ -0,0 +1,16 @@ +flags: {} +extra-package-dbs: [] +packages: + - . +resolver: lts-18.28 +extra-deps: + - ShellCheck-0.8.0@sha256:353c9322847b661e4c6f7c83c2acf8e5c08b682fbe516c7d46c29605937543df,3297 + - colourista-0.1.0.1@sha256:98353ee0e2f5d97d2148513f084c1cd37dfda03e48aa9dd7a017c9d9c0ba710e,3307 + - language-docker-11.0.0@sha256:3406ff0c1d592490f53ead8cf2cd22bdf3d79fd125ccaf3add683f6d71c24d55,3883 + - spdx-1.0.0.2@sha256:7dfac9b454ff2da0abb7560f0ffbe00ae442dd5cb76e8be469f77e6988a70fed,2008 + - hspec-2.9.4@sha256:658a6a74d5a70c040edd6df2a12228c6d9e63082adaad1ed4d0438ad082a0ef3,1709 + - hspec-core-2.9.4@sha256:a126e9087409fef8dcafcd2f8656456527ac7bb163ed4d9cb3a57589042a5fe8,6498 + - hspec-discover-2.9.4@sha256:fbcf49ecfc3d4da53e797fd0275264cba776ffa324ee223e2a3f4ec2d2c9c4a6,2165 + - stm-2.5.0.2@sha256:e4dc6473faaa75fbd7eccab4e3ee1d651d75bb0e49946ef0b8b751ccde771a55,2314 +ghc-options: + "$everything": -haddock diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/stack.yaml.lock b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/stack.yaml.lock new file mode 100644 index 0000000000000000000000000000000000000000..a185422556e28502cef265f7ed4e7aa435b48cbb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/hackage/stack.yaml.lock @@ -0,0 +1,75 @@ +# This file was autogenerated by Stack. +# You should not edit this file by hand. +# For more information, please see the documentation at: +# https://docs.haskellstack.org/en/stable/lock_files + +packages: +- completed: + hackage: HTTP-4000.3.16@sha256:6042643c15a0b43e522a6693f1e322f05000d519543a84149cb80aeffee34f71,5947 + pantry-tree: + size: 1428 + sha256: b73a7f6d21cf20bbf819e19039409c9010efb5000d2b72cdd8fd67a9027c14e8 + original: + hackage: HTTP-4000.3.16@sha256:6042643c15a0b43e522a6693f1e322f05000d519543a84149cb80aeffee34f71,5947 +- completed: + hackage: configurator-pg-0.2.6@sha256:cd9b06a458428e493a4d6def725af7ab1ab0fef678fbd871f9586fc7f9aa70be,2849 + pantry-tree: + size: 2463 + sha256: 97efe7a22afc93033bda5adcffdabc0f1c30dc32b2c3ba02114ce7cd74c942fd + original: + hackage: configurator-pg-0.2.6@sha256:cd9b06a458428e493a4d6def725af7ab1ab0fef678fbd871f9586fc7f9aa70be,2849 +- completed: + hackage: hasql-dynamic-statements-0.3.1.1@sha256:2cfe6e75990e690f595a87cbe553f2e90fcd738610f6c66749c81cc4396b2cc4,2675 + pantry-tree: + size: 595 + sha256: b84ae10a5c776f88f546df73bc957a35e61056400b7e805dad0b254612907e97 + original: + hackage: hasql-dynamic-statements-0.3.1.1@sha256:2cfe6e75990e690f595a87cbe553f2e90fcd738610f6c66749c81cc4396b2cc4,2675 +- completed: + hackage: hasql-implicits-0.1.0.4@sha256:0848d3cbc9d94e1e539948fa0be4d0326b26335034161bf8076785293444ca6f,1361 + pantry-tree: + size: 264 + sha256: d49af8f8749ab7039fa668af4b78f997f7fa2928b4aded6798f573a3d08e76a0 + original: + hackage: hasql-implicits-0.1.0.4@sha256:0848d3cbc9d94e1e539948fa0be4d0326b26335034161bf8076785293444ca6f,1361 +- completed: + hackage: hasql-pool-0.5.2.2@sha256:b56d4dea112d97a2ef4b2749508c0ca646828cb2d77b827e8dc433d249bb2062,2438 + pantry-tree: + size: 412 + sha256: 2741a33f947d28b4076c798c20c1f646beecd21f5eaf522c8256cbeb34d4d6d0 + original: + hackage: hasql-pool-0.5.2.2@sha256:b56d4dea112d97a2ef4b2749508c0ca646828cb2d77b827e8dc433d249bb2062,2438 +- completed: + hackage: lens-aeson-1.1.3@sha256:52c8eaecd2d1c2a969c0762277c4a8ee72c339a686727d5785932e72ef9c3050,1764 + pantry-tree: + size: 541 + sha256: b31392b78f2a03111c805f4400007778eb93b49f998ab41dfbebaaf9b5526bad + original: + hackage: lens-aeson-1.1.3@sha256:52c8eaecd2d1c2a969c0762277c4a8ee72c339a686727d5785932e72ef9c3050,1764 +- completed: + hackage: optparse-applicative-0.16.1.0@sha256:418c22ed6a19124d457d96bc66bd22c93ac22fad0c7100fe4972bbb4ac989731,4982 + pantry-tree: + size: 2979 + sha256: dd092d843091c08691485d68a1908517079b1bc6f3d73928f37635a19dc27fc1 + original: + hackage: optparse-applicative-0.16.1.0@sha256:418c22ed6a19124d457d96bc66bd22c93ac22fad0c7100fe4972bbb4ac989731,4982 +- completed: + hackage: protolude-0.3.2@sha256:2a38b3dad40d238ab644e234b692c8911423f9d3ed0e36b62287c4a698d92cd1,2240 + pantry-tree: + size: 1594 + sha256: a36d2912ac552d950ba4476de7d950b56b82dd28e48b9f4d0efee938f10bc525 + original: + hackage: protolude-0.3.2@sha256:2a38b3dad40d238ab644e234b692c8911423f9d3ed0e36b62287c4a698d92cd1,2240 +- completed: + hackage: ptr-0.16.8.2@sha256:708ebb95117f2872d2c5a554eb6804cf1126e86abe793b2673f913f14e5eb1ac,3959 + pantry-tree: + size: 1303 + sha256: 557c438345de19f82bf01d676100da2a191ef06f624e7a4b90b09ac17cbb52a5 + original: + hackage: ptr-0.16.8.2@sha256:708ebb95117f2872d2c5a554eb6804cf1126e86abe793b2673f913f14e5eb1ac,3959 +snapshots: +- completed: + size: 618951 + url: https://raw.githubusercontent.com/commercialhaskell/stackage-snapshots/master/lts/19/14.yaml + sha256: 4c31d4ef975b0211078862566aedf3b82b6cea569fc2cde4c72a51e5a8d236ce + original: lts-19.14 diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/dart/pubspec.lock b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/dart/pubspec.lock new file mode 100644 index 0000000000000000000000000000000000000000..c7b912f1aefc8d55726d5007112903b5f162d3bb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/dart/pubspec.lock @@ -0,0 +1,49 @@ +# Generated by pub +# See https://dart.dev/tools/pub/glossary#lockfile +packages: + ale: + dependency: transitive + description: + name: ale + url: "https://pub.hosted.org" + source: hosted + version: "3.3.0" + analyzer: + dependency: transitive + description: + name: analyzer + url: "https://pub.dartlang.org" + source: hosted + version: "0.40.7" + ansicolor: + dependency: transitive + description: + name: ansicolor + url: "https://pub.dartlang.org" + source: hosted + version: "1.1.1" + archive: + dependency: transitive + description: + name: archive + url: "https://pub.dartlang.org" + source: hosted + version: "2.0.13" + args: + dependency: transitive + description: + name: args + url: "https://pub.dartlang.org" + source: hosted + version: "1.6.0" + key_binder: + dependency: "direct main" + description: + path: "." + ref: HEAD + resolved-ref: "3f7b3a6350e73c7dcac45301c0e18fbd42af02f7" + url: "git@github.com:Workiva/key_binder.git" + source: git + version: "1.11.20" +sdks: + dart: ">=2.12.0 <3.0.0" diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/dotnet/TestLibrary.deps.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/dotnet/TestLibrary.deps.json new file mode 100644 index 0000000000000000000000000000000000000000..a429ec4094da8fd4192edf75028340ac0ca98447 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/dotnet/TestLibrary.deps.json @@ -0,0 +1,235 @@ +{ + "runtimeTarget": { + "name": ".NETCoreApp,Version=v6.0", + "signature": "" + }, + "compilationOptions": {}, + "targets": { + ".NETCoreApp,Version=v6.0": { + "TestLibrary/1.0.0": { + "dependencies": { + "Microsoft.Extensions.DependencyInjection": "6.0.0", + "Microsoft.Extensions.Logging": "6.0.0", + "Newtonsoft.Json": "13.0.1", + "Serilog": "2.10.0", + "Serilog.Sinks.Console": "4.0.1", + "TestCommon": "1.0.0" + }, + "runtime": { + "TestLibrary.dll": {} + } + }, + "AWSSDK.Core/3.7.10.6": { + "runtime": { + "lib/netcoreapp3.1/AWSSDK.Core.dll": { + "assemblyVersion": "3.3.0.0", + "fileVersion": "3.7.10.6" + } + } + }, + "Microsoft.Extensions.DependencyInjection/6.0.0": { + "dependencies": { + "Microsoft.Extensions.DependencyInjection.Abstractions": "6.0.0", + "System.Runtime.CompilerServices.Unsafe": "6.0.0" + }, + "runtime": { + "lib/net6.0/Microsoft.Extensions.DependencyInjection.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.DependencyInjection.Abstractions/6.0.0": { + "runtime": { + "lib/net6.0/Microsoft.Extensions.DependencyInjection.Abstractions.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.Logging/6.0.0": { + "dependencies": { + "Microsoft.Extensions.DependencyInjection": "6.0.0", + "Microsoft.Extensions.DependencyInjection.Abstractions": "6.0.0", + "Microsoft.Extensions.Logging.Abstractions": "6.0.0", + "Microsoft.Extensions.Options": "6.0.0", + "System.Diagnostics.DiagnosticSource": "6.0.0" + }, + "runtime": { + "lib/netstandard2.1/Microsoft.Extensions.Logging.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.Logging.Abstractions/6.0.0": { + "runtime": { + "lib/net6.0/Microsoft.Extensions.Logging.Abstractions.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.Options/6.0.0": { + "dependencies": { + "Microsoft.Extensions.DependencyInjection.Abstractions": "6.0.0", + "Microsoft.Extensions.Primitives": "6.0.0" + }, + "runtime": { + "lib/netstandard2.1/Microsoft.Extensions.Options.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Microsoft.Extensions.Primitives/6.0.0": { + "dependencies": { + "System.Runtime.CompilerServices.Unsafe": "6.0.0" + }, + "runtime": { + "lib/net6.0/Microsoft.Extensions.Primitives.dll": { + "assemblyVersion": "6.0.0.0", + "fileVersion": "6.0.21.52210" + } + } + }, + "Newtonsoft.Json/13.0.1": { + "runtime": { + "lib/netstandard2.0/Newtonsoft.Json.dll": { + "assemblyVersion": "13.0.0.0", + "fileVersion": "13.0.1.25517" + } + } + }, + "Serilog/2.10.0": { + "runtime": { + "lib/netstandard2.1/Serilog.dll": { + "assemblyVersion": "2.0.0.0", + "fileVersion": "2.10.0.0" + } + } + }, + "Serilog.Sinks.Console/4.0.1": { + "dependencies": { + "Serilog": "2.10.0" + }, + "runtime": { + "lib/net5.0/Serilog.Sinks.Console.dll": { + "assemblyVersion": "4.0.1.0", + "fileVersion": "4.0.1.0" + } + } + }, + "System.Diagnostics.DiagnosticSource/6.0.0": { + "dependencies": { + "System.Runtime.CompilerServices.Unsafe": "6.0.0" + } + }, + "System.Runtime.CompilerServices.Unsafe/6.0.0": {}, + "TestCommon/1.0.0": { + "dependencies": { + "AWSSDK.Core": "3.7.10.6" + }, + "runtime": { + "TestCommon.dll": {} + } + } + } + }, + "libraries": { + "TestLibrary/1.0.0": { + "type": "project", + "serviceable": false, + "sha512": "" + }, + "AWSSDK.Core/3.7.10.6": { + "type": "package", + "serviceable": true, + "sha512": "sha512-kHBB+QmosVaG6DpngXQ8OlLVVNMzltNITfsRr68Z90qO7dSqJ2EHNd8dtBU1u3AQQLqqFHOY0lfmbpexeH6Pew==", + "path": "awssdk.core/3.7.10.6", + "hashPath": "awssdk.core.3.7.10.6.nupkg.sha512" + }, + "Microsoft.Extensions.DependencyInjection/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-k6PWQMuoBDGGHOQTtyois2u4AwyVcIwL2LaSLlTZQm2CYcJ1pxbt6jfAnpWmzENA/wfrYRI/X9DTLoUkE4AsLw==", + "path": "microsoft.extensions.dependencyinjection/6.0.0", + "hashPath": "microsoft.extensions.dependencyinjection.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.DependencyInjection.Abstractions/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-xlzi2IYREJH3/m6+lUrQlujzX8wDitm4QGnUu6kUXTQAWPuZY8i+ticFJbzfqaetLA6KR/rO6Ew/HuYD+bxifg==", + "path": "microsoft.extensions.dependencyinjection.abstractions/6.0.0", + "hashPath": "microsoft.extensions.dependencyinjection.abstractions.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.Logging/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-eIbyj40QDg1NDz0HBW0S5f3wrLVnKWnDJ/JtZ+yJDFnDj90VoPuoPmFkeaXrtu+0cKm5GRAwoDf+dBWXK0TUdg==", + "path": "microsoft.extensions.logging/6.0.0", + "hashPath": "microsoft.extensions.logging.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.Logging.Abstractions/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-/HggWBbTwy8TgebGSX5DBZ24ndhzi93sHUBDvP1IxbZD7FDokYzdAr6+vbWGjw2XAfR2EJ1sfKUotpjHnFWPxA==", + "path": "microsoft.extensions.logging.abstractions/6.0.0", + "hashPath": "microsoft.extensions.logging.abstractions.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.Options/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-dzXN0+V1AyjOe2xcJ86Qbo233KHuLEY0njf/P2Kw8SfJU+d45HNS2ctJdnEnrWbM9Ye2eFgaC5Mj9otRMU6IsQ==", + "path": "microsoft.extensions.options/6.0.0", + "hashPath": "microsoft.extensions.options.6.0.0.nupkg.sha512" + }, + "Microsoft.Extensions.Primitives/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-9+PnzmQFfEFNR9J2aDTfJGGupShHjOuGw4VUv+JB044biSHrnmCIMD+mJHmb2H7YryrfBEXDurxQ47gJZdCKNQ==", + "path": "microsoft.extensions.primitives/6.0.0", + "hashPath": "microsoft.extensions.primitives.6.0.0.nupkg.sha512" + }, + "Newtonsoft.Json/13.0.1": { + "type": "package", + "serviceable": true, + "sha512": "sha512-ppPFpBcvxdsfUonNcvITKqLl3bqxWbDCZIzDWHzjpdAHRFfZe0Dw9HmA0+za13IdyrgJwpkDTDA9fHaxOrt20A==", + "path": "newtonsoft.json/13.0.1", + "hashPath": "newtonsoft.json.13.0.1.nupkg.sha512" + }, + "Serilog/2.10.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-+QX0hmf37a0/OZLxM3wL7V6/ADvC1XihXN4Kq/p6d8lCPfgkRdiuhbWlMaFjR9Av0dy5F0+MBeDmDdRZN/YwQA==", + "path": "serilog/2.10.0", + "hashPath": "serilog.2.10.0.nupkg.sha512" + }, + "Serilog.Sinks.Console/4.0.1": { + "type": "package", + "serviceable": true, + "sha512": "sha512-apLOvSJQLlIbKlbx+Y2UDHSP05kJsV7mou+fvJoRGs/iR+jC22r8cuFVMjjfVxz/AD4B2UCltFhE1naRLXwKNw==", + "path": "serilog.sinks.console/4.0.1", + "hashPath": "serilog.sinks.console.4.0.1.nupkg.sha512" + }, + "System.Diagnostics.DiagnosticSource/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-frQDfv0rl209cKm1lnwTgFPzNigy2EKk1BS3uAvHvlBVKe5cymGyHO+Sj+NLv5VF/AhHsqPIUUwya5oV4CHMUw==", + "path": "system.diagnostics.diagnosticsource/6.0.0", + "hashPath": "system.diagnostics.diagnosticsource.6.0.0.nupkg.sha512" + }, + "System.Runtime.CompilerServices.Unsafe/6.0.0": { + "type": "package", + "serviceable": true, + "sha512": "sha512-/iUeP3tq1S0XdNNoMz5C9twLSrM/TH+qElHkXWaPvuNOt+99G75NrV0OS2EqHx5wMN7popYjpc8oTjC1y16DLg==", + "path": "system.runtime.compilerservices.unsafe/6.0.0", + "hashPath": "system.runtime.compilerservices.unsafe.6.0.0.nupkg.sha512" + }, + "TestCommon/1.0.0": { + "type": "project", + "serviceable": false, + "sha512": "" + } + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/go/go.mod b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/go/go.mod new file mode 100644 index 0000000000000000000000000000000000000000..4edcf7e8b29f88c15eeefb0ac46e226c0d3f5221 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/go/go.mod @@ -0,0 +1,7 @@ +module github.com/anchore/syft + +go 1.14 + +require ( + github.com/bmatcuk/doublestar v1.3.1 +) diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/example-java-app-maven-0.1.0.jar b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/example-java-app-maven-0.1.0.jar new file mode 100644 index 0000000000000000000000000000000000000000..5531378393435ab456f8c7c63257c96ea10a4b46 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/example-java-app-maven-0.1.0.jar differ diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/example-jenkins-plugin.hpi b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/example-jenkins-plugin.hpi new file mode 100644 index 0000000000000000000000000000000000000000..fc1f16d2f3e5d09f2de6f49396c50e17cd3ae8a9 Binary files /dev/null and b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/example-jenkins-plugin.hpi differ diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/generate-fixtures.md b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/generate-fixtures.md new file mode 100644 index 0000000000000000000000000000000000000000..249a210231d9a456f88ec09826e2009c3f03819a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/generate-fixtures.md @@ -0,0 +1 @@ +See the syft/cataloger/java/test-fixtures/java-builds dir to generate test fixtures and copy to here manually. \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/pom.xml b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/pom.xml new file mode 100644 index 0000000000000000000000000000000000000000..4ab76d1d914b056b5854312c5b2f01b57ddd365c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/java/pom.xml @@ -0,0 +1,59 @@ + + + 4.0.0 + + org.anchore + example-java-app-maven + jar + 0.1.0 + + + 1.8 + 1.8 + + + + + + joda-time + joda-time + 2.9.2 + + + + + junit + junit + 4.12 + test + + + + + + + + org.apache.maven.plugins + maven-shade-plugin + 2.1 + + + package + + shade + + + + + hello.HelloWorld + + + + + + + + + + diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/package-json/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/package-json/package.json new file mode 100644 index 0000000000000000000000000000000000000000..aba48c6bd3d3c0254bedb0e681f0b08bbe212a0f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/package-json/package.json @@ -0,0 +1,314 @@ +{ + "version": "6.14.6", + "name": "npm", + "description": "a package manager for JavaScript", + "keywords": [ + "install", + "modules", + "package manager", + "package.json" + ], + "preferGlobal": true, + "config": { + "publishtest": false + }, + "homepage": "https://docs.npmjs.com/", + "author": "Isaac Z. Schlueter (http://blog.izs.me)", + "repository": { + "type": "git", + "url": "https://github.com/npm/cli" + }, + "bugs": { + "url": "https://npm.community/c/bugs" + }, + "directories": { + "bin": "./bin", + "doc": "./doc", + "lib": "./lib", + "man": "./man" + }, + "main": "./lib/npm.js", + "bin": { + "npm": "./bin/npm-cli.js", + "npx": "./bin/npx-cli.js" + }, + "dependencies": { + "JSONStream": "^1.3.5", + "abbrev": "~1.1.1", + "ansicolors": "~0.3.2", + "ansistyles": "~0.1.3", + "aproba": "^2.0.0", + "archy": "~1.0.0", + "bin-links": "^1.1.7", + "bluebird": "^3.5.5", + "byte-size": "^5.0.1", + "cacache": "^12.0.3", + "call-limit": "^1.1.1", + "chownr": "^1.1.4", + "ci-info": "^2.0.0", + "cli-columns": "^3.1.2", + "cli-table3": "^0.5.1", + "cmd-shim": "^3.0.3", + "columnify": "~1.5.4", + "config-chain": "^1.1.12", + "detect-indent": "~5.0.0", + "detect-newline": "^2.1.0", + "dezalgo": "~1.0.3", + "editor": "~1.0.0", + "figgy-pudding": "^3.5.1", + "find-npm-prefix": "^1.0.2", + "fs-vacuum": "~1.2.10", + "fs-write-stream-atomic": "~1.0.10", + "gentle-fs": "^2.3.0", + "glob": "^7.1.6", + "graceful-fs": "^4.2.4", + "has-unicode": "~2.0.1", + "hosted-git-info": "^2.8.8", + "iferr": "^1.0.2", + "infer-owner": "^1.0.4", + "inflight": "~1.0.6", + "inherits": "^2.0.4", + "ini": "^1.3.5", + "init-package-json": "^1.10.3", + "is-cidr": "^3.0.0", + "json-parse-better-errors": "^1.0.2", + "lazy-property": "~1.0.0", + "libcipm": "^4.0.7", + "libnpm": "^3.0.1", + "libnpmaccess": "^3.0.2", + "libnpmhook": "^5.0.3", + "libnpmorg": "^1.0.1", + "libnpmsearch": "^2.0.2", + "libnpmteam": "^1.0.2", + "libnpx": "^10.2.2", + "lock-verify": "^2.1.0", + "lockfile": "^1.0.4", + "lodash._baseuniq": "~4.6.0", + "lodash.clonedeep": "~4.5.0", + "lodash.union": "~4.6.0", + "lodash.uniq": "~4.5.0", + "lodash.without": "~4.4.0", + "lru-cache": "^5.1.1", + "meant": "~1.0.1", + "mississippi": "^3.0.0", + "mkdirp": "^0.5.5", + "move-concurrently": "^1.0.1", + "node-gyp": "^5.1.0", + "nopt": "^4.0.3", + "normalize-package-data": "^2.5.0", + "npm-audit-report": "^1.3.2", + "npm-cache-filename": "~1.0.2", + "npm-install-checks": "^3.0.2", + "npm-lifecycle": "^3.1.4", + "npm-package-arg": "^6.1.1", + "npm-packlist": "^1.4.8", + "npm-pick-manifest": "^3.0.2", + "npm-profile": "^4.0.4", + "npm-registry-fetch": "^4.0.5", + "npm-user-validate": "~1.0.0", + "npmlog": "~4.1.2", + "once": "~1.4.0", + "opener": "^1.5.1", + "osenv": "^0.1.5", + "pacote": "^9.5.12", + "path-is-inside": "~1.0.2", + "promise-inflight": "~1.0.1", + "qrcode-terminal": "^0.12.0", + "query-string": "^6.8.2", + "qw": "~1.0.1", + "read": "~1.0.7", + "read-cmd-shim": "^1.0.5", + "read-installed": "~4.0.3", + "read-package-json": "^2.1.1", + "read-package-tree": "^5.3.1", + "readable-stream": "^3.6.0", + "readdir-scoped-modules": "^1.1.0", + "request": "^2.88.0", + "retry": "^0.12.0", + "rimraf": "^2.7.1", + "safe-buffer": "^5.1.2", + "semver": "^5.7.1", + "sha": "^3.0.0", + "slide": "~1.1.6", + "sorted-object": "~2.0.1", + "sorted-union-stream": "~2.1.3", + "ssri": "^6.0.1", + "stringify-package": "^1.0.1", + "tar": "^4.4.13", + "text-table": "~0.2.0", + "tiny-relative-date": "^1.3.0", + "uid-number": "0.0.6", + "umask": "~1.1.0", + "unique-filename": "^1.1.1", + "unpipe": "~1.0.0", + "update-notifier": "^2.5.0", + "uuid": "^3.3.3", + "validate-npm-package-license": "^3.0.4", + "validate-npm-package-name": "~3.0.0", + "which": "^1.3.1", + "worker-farm": "^1.7.0", + "write-file-atomic": "^2.4.3" + }, + "bundleDependencies": [ + "abbrev", + "ansicolors", + "ansistyles", + "aproba", + "archy", + "bin-links", + "bluebird", + "byte-size", + "cacache", + "call-limit", + "chownr", + "ci-info", + "cli-columns", + "cli-table3", + "cmd-shim", + "columnify", + "config-chain", + "debuglog", + "detect-indent", + "detect-newline", + "dezalgo", + "editor", + "figgy-pudding", + "find-npm-prefix", + "fs-vacuum", + "fs-write-stream-atomic", + "gentle-fs", + "glob", + "graceful-fs", + "has-unicode", + "hosted-git-info", + "iferr", + "imurmurhash", + "infer-owner", + "inflight", + "inherits", + "ini", + "init-package-json", + "is-cidr", + "json-parse-better-errors", + "JSONStream", + "lazy-property", + "libcipm", + "libnpm", + "libnpmaccess", + "libnpmhook", + "libnpmorg", + "libnpmsearch", + "libnpmteam", + "libnpx", + "lock-verify", + "lockfile", + "lodash._baseindexof", + "lodash._baseuniq", + "lodash._bindcallback", + "lodash._cacheindexof", + "lodash._createcache", + "lodash._getnative", + "lodash.clonedeep", + "lodash.restparam", + "lodash.union", + "lodash.uniq", + "lodash.without", + "lru-cache", + "meant", + "mississippi", + "mkdirp", + "move-concurrently", + "node-gyp", + "nopt", + "normalize-package-data", + "npm-audit-report", + "npm-cache-filename", + "npm-install-checks", + "npm-lifecycle", + "npm-package-arg", + "npm-packlist", + "npm-pick-manifest", + "npm-profile", + "npm-registry-fetch", + "npm-user-validate", + "npmlog", + "once", + "opener", + "osenv", + "pacote", + "path-is-inside", + "promise-inflight", + "qrcode-terminal", + "query-string", + "qw", + "read-cmd-shim", + "read-installed", + "read-package-json", + "read-package-tree", + "read", + "readable-stream", + "readdir-scoped-modules", + "request", + "retry", + "rimraf", + "safe-buffer", + "semver", + "sha", + "slide", + "sorted-object", + "sorted-union-stream", + "ssri", + "stringify-package", + "tar", + "text-table", + "tiny-relative-date", + "uid-number", + "umask", + "unique-filename", + "unpipe", + "update-notifier", + "uuid", + "validate-npm-package-license", + "validate-npm-package-name", + "which", + "worker-farm", + "write-file-atomic" + ], + "devDependencies": { + "deep-equal": "^1.0.1", + "get-stream": "^4.1.0", + "licensee": "^7.0.3", + "marked": "^0.6.3", + "marked-man": "^0.6.0", + "npm-registry-couchapp": "^2.7.4", + "npm-registry-mock": "^1.3.1", + "require-inject": "^1.4.4", + "sprintf-js": "^1.1.2", + "standard": "^11.0.1", + "tacks": "^1.3.0", + "tap": "^12.7.0", + "tar-stream": "^2.1.0" + }, + "scripts": { + "dumpconf": "env | grep npm | sort | uniq", + "prepare": "node bin/npm-cli.js rebuild && node bin/npm-cli.js --no-audit --no-timing prune --prefix=. --no-global && rimraf test/*/*/node_modules && make -j4 mandocs", + "preversion": "bash scripts/update-authors.sh && git add AUTHORS && git commit -m \"update AUTHORS\" || true", + "licenses": "licensee --production --errors-only", + "tap": "tap -J --timeout 300 --no-esm", + "tap-cover": "tap -J --nyc-arg=--cache --coverage --timeout 600 --no-esm", + "lint": "standard", + "pretest": "npm run lint", + "test": "npm run test-tap --", + "test:nocleanup": "NO_TEST_CLEANUP=1 npm run test --", + "sudotest": "sudo npm run tap -- \"test/tap/*.js\"", + "sudotest:nocleanup": "sudo NO_TEST_CLEANUP=1 npm run tap -- \"test/tap/*.js\"", + "posttest": "rimraf test/npm_cache*", + "test-coverage": "npm run tap-cover -- \"test/tap/*.js\" \"test/network/*.js\"", + "test-tap": "npm run tap -- \"test/tap/*.js\" \"test/network/*.js\"", + "test-node": "tap --timeout 240 \"test/tap/*.js\" \"test/network/*.js\"" + }, + "license": "Artistic-2.0", + "engines": { + "node": "6 >=6.2.0 || 8 || >=9.3.0" + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/package-lock/package-lock.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/package-lock/package-lock.json new file mode 100644 index 0000000000000000000000000000000000000000..9eb8f4cf89241498a9a0b8760456927a9b627321 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/package-lock/package-lock.json @@ -0,0 +1,11 @@ +{ + "requires": true, + "lockfileVersion": 1, + "dependencies": { + "get-stdin": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-8.0.0.tgz", + "integrity": "sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg==" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/yarn/yarn.lock b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/yarn/yarn.lock new file mode 100644 index 0000000000000000000000000000000000000000..a97627b6c6da8f5271600ab782f9dacbb1104390 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/javascript/yarn/yarn.lock @@ -0,0 +1,12 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +"@babel/code-frame@^7.0.0", "@babel/code-frame@^7.10.4": + version "7.10.4" + resolved "https://registry.yarnpkg.com/@babel/code-frame/-/code-frame-7.10.4.tgz#168da1a36e90da68ae8d49c0f1b48c7c6249213a" + integrity sha512-vG6SvB6oYEhvgisZNFRmRCUkLz11c7rp+tbNTynGqc6mS1d5ATd/sGyV6W0KZZnXRKMTzZDRgQT3Ou9jhpAfUg== + dependencies: + "@babel/highlight" "^7.10.4" + + diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/php/vendor/composer/installed.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/php/vendor/composer/installed.json new file mode 100644 index 0000000000000000000000000000000000000000..39af3b5de960678ec22a78b5121ca0281be528d3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/php/vendor/composer/installed.json @@ -0,0 +1,173 @@ +{ + "packages": [ + { + "name": "nikic/fast-route", + "version": "v1.3.0", + "version_normalized": "1.3.0.0", + "source": { + "type": "git", + "url": "https://github.com/nikic/FastRoute.git", + "reference": "181d480e08d9476e61381e04a71b34dc0432e812" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/nikic/FastRoute/zipball/181d480e08d9476e61381e04a71b34dc0432e812", + "reference": "181d480e08d9476e61381e04a71b34dc0432e812", + "shasum": "" + }, + "require": { + "php": ">=5.4.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.8.35|~5.7" + }, + "time": "2018-02-13T20:26:39+00:00", + "type": "library", + "installation-source": "dist", + "autoload": { + "psr-4": { + "FastRoute\\": "src/" + }, + "files": [ + "src/functions.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Nikita Popov", + "email": "nikic@php.net" + } + ], + "description": "Fast request router for PHP", + "keywords": [ + "router", + "routing" + ], + "support": { + "issues": "https://github.com/nikic/FastRoute/issues", + "source": "https://github.com/nikic/FastRoute/tree/master" + }, + "install-path": "../nikic/fast-route" + }, + { + "name": "psr/container", + "version": "2.0.2", + "version_normalized": "2.0.2.0", + "source": { + "type": "git", + "url": "https://github.com/php-fig/container.git", + "reference": "c71ecc56dfe541dbd90c5360474fbc405f8d5963" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/container/zipball/c71ecc56dfe541dbd90c5360474fbc405f8d5963", + "reference": "c71ecc56dfe541dbd90c5360474fbc405f8d5963", + "shasum": "" + }, + "require": { + "php": ">=7.4.0" + }, + "time": "2021-11-05T16:47:00+00:00", + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0.x-dev" + } + }, + "installation-source": "dist", + "autoload": { + "psr-4": { + "Psr\\Container\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "https://www.php-fig.org/" + } + ], + "description": "Common Container Interface (PHP FIG PSR-11)", + "homepage": "https://github.com/php-fig/container", + "keywords": [ + "PSR-11", + "container", + "container-interface", + "container-interop", + "psr" + ], + "support": { + "issues": "https://github.com/php-fig/container/issues", + "source": "https://github.com/php-fig/container/tree/2.0.2" + }, + "install-path": "../psr/container" + }, + { + "name": "psr/http-factory", + "version": "1.0.1", + "version_normalized": "1.0.1.0", + "source": { + "type": "git", + "url": "https://github.com/php-fig/http-factory.git", + "reference": "12ac7fcd07e5b077433f5f2bee95b3a771bf61be" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/http-factory/zipball/12ac7fcd07e5b077433f5f2bee95b3a771bf61be", + "reference": "12ac7fcd07e5b077433f5f2bee95b3a771bf61be", + "shasum": "" + }, + "require": { + "php": ">=7.0.0", + "psr/http-message": "^1.0" + }, + "time": "2019-04-30T12:38:16+00:00", + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "installation-source": "dist", + "autoload": { + "psr-4": { + "Psr\\Http\\Message\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "description": "Common interfaces for PSR-7 HTTP message factories", + "keywords": [ + "factory", + "http", + "message", + "psr", + "psr-17", + "psr-7", + "request", + "response" + ], + "support": { + "source": "https://github.com/php-fig/http-factory/tree/master" + }, + "install-path": "../psr/http-factory" + } + ], + "dev": true, + "dev-package-names": [] +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/METADATA b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/METADATA new file mode 100644 index 0000000000000000000000000000000000000000..924780dfd45ab61f303185f3fa4d969ec2c336aa --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/METADATA @@ -0,0 +1,47 @@ +Metadata-Version: 2.1 +Name: Pygments +Version: 2.6.1 +Summary: Pygments is a syntax highlighting package written in Python. +Home-page: https://pygments.org/ +Author: Georg Brandl +Author-email: georg@python.org +License: BSD License +Keywords: syntax highlighting +Platform: any +Classifier: License :: OSI Approved :: BSD License +Classifier: Intended Audience :: Developers +Classifier: Intended Audience :: End Users/Desktop +Classifier: Intended Audience :: System Administrators +Classifier: Development Status :: 6 - Mature +Classifier: Programming Language :: Python +Classifier: Programming Language :: Python :: 3 +Classifier: Programming Language :: Python :: 3.5 +Classifier: Programming Language :: Python :: 3.6 +Classifier: Programming Language :: Python :: 3.7 +Classifier: Programming Language :: Python :: 3.8 +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Programming Language :: Python :: Implementation :: PyPy +Classifier: Operating System :: OS Independent +Classifier: Topic :: Text Processing :: Filters +Classifier: Topic :: Utilities +Requires-Python: >=3.5 + + +Pygments +~~~~~~~~ + +Pygments is a syntax highlighting package written in Python. + +It is a generic syntax highlighter suitable for use in code hosting, forums, +wikis or other applications that need to prettify source code. Highlights +are: + +* a wide range of over 500 languages and other text formats is supported +* special attention is paid to details, increasing quality by a fair amount +* support for new languages and formats are added easily +* a number of output formats, presently HTML, LaTeX, RTF, SVG, all image formats that PIL supports and ANSI sequences +* it is usable as a command-line tool and as a library + +:copyright: Copyright 2006-2019 by the Pygments team, see AUTHORS. +:license: BSD, see LICENSE for details. + diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/RECORD b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/RECORD new file mode 100644 index 0000000000000000000000000000000000000000..af233f3909e37867e75c53d9e578405d8d0ad286 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/RECORD @@ -0,0 +1,5 @@ +../../../bin/pygmentize,sha256=dDhv_U2jiCpmFQwIRHpFRLAHUO4R1jIJPEvT_QYTFp8,220 +Pygments-2.6.1.dist-info/AUTHORS,sha256=PVpa2_Oku6BGuiUvutvuPnWGpzxqFy2I8-NIrqCvqUY,8449 +Pygments-2.6.1.dist-info/RECORD,, +pygments/__pycache__/__init__.cpython-38.pyc,, +pygments/util.py,sha256=586xXHiJGGZxqk5PMBu3vBhE68DLuAe5MBARWrSPGxA,10778 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/top_level.txt b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/top_level.txt new file mode 100644 index 0000000000000000000000000000000000000000..1e09fdb905661b12c39d33fa1f4548c807d6a330 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/dist-info/top_level.txt @@ -0,0 +1 @@ +top-level-pkg \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/egg-info/PKG-INFO b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/egg-info/PKG-INFO new file mode 100644 index 0000000000000000000000000000000000000000..a73770668150c2bea1b4d7b807aeb058b18ebcc8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/egg-info/PKG-INFO @@ -0,0 +1,134 @@ +Metadata-Version: 2.1 +Name: requests +Version: 2.22.0 +Summary: Python HTTP for Humans. +Home-page: http://python-requests.org +Author: Kenneth Reitz +Author-email: me@kennethreitz.org +License: Apache 2.0 +Description: Requests: HTTP for Humans™ + ========================== + + [![image](https://img.shields.io/pypi/v/requests.svg)](https://pypi.org/project/requests/) + [![image](https://img.shields.io/pypi/l/requests.svg)](https://pypi.org/project/requests/) + [![image](https://img.shields.io/pypi/pyversions/requests.svg)](https://pypi.org/project/requests/) + [![codecov.io](https://codecov.io/github/requests/requests/coverage.svg?branch=master)](https://codecov.io/github/requests/requests) + [![image](https://img.shields.io/github/contributors/requests/requests.svg)](https://github.com/requests/requests/graphs/contributors) + [![image](https://img.shields.io/badge/Say%20Thanks-!-1EAEDB.svg)](https://saythanks.io/to/kennethreitz) + + Requests is the only *Non-GMO* HTTP library for Python, safe for human + consumption. + + ![image](https://farm5.staticflickr.com/4317/35198386374_1939af3de6_k_d.jpg) + + Behold, the power of Requests: + + ``` {.sourceCode .python} + >>> import requests + >>> r = requests.get('https://api.github.com/user', auth=('user', 'pass')) + >>> r.status_code + 200 + >>> r.headers['content-type'] + 'application/json; charset=utf8' + >>> r.encoding + 'utf-8' + >>> r.text + u'{"type":"User"...' + >>> r.json() + {u'disk_usage': 368627, u'private_gists': 484, ...} + ``` + + See [the similar code, sans Requests](https://gist.github.com/973705). + + [![image](https://raw.githubusercontent.com/requests/requests/master/docs/_static/requests-logo-small.png)](http://docs.python-requests.org/) + + Requests allows you to send *organic, grass-fed* HTTP/1.1 requests, + without the need for manual labor. There's no need to manually add query + strings to your URLs, or to form-encode your POST data. Keep-alive and + HTTP connection pooling are 100% automatic, thanks to + [urllib3](https://github.com/shazow/urllib3). + + Besides, all the cool kids are doing it. Requests is one of the most + downloaded Python packages of all time, pulling in over 11,000,000 + downloads every month. You don't want to be left out! + + Feature Support + --------------- + + Requests is ready for today's web. + + - International Domains and URLs + - Keep-Alive & Connection Pooling + - Sessions with Cookie Persistence + - Browser-style SSL Verification + - Basic/Digest Authentication + - Elegant Key/Value Cookies + - Automatic Decompression + - Automatic Content Decoding + - Unicode Response Bodies + - Multipart File Uploads + - HTTP(S) Proxy Support + - Connection Timeouts + - Streaming Downloads + - `.netrc` Support + - Chunked Requests + + Requests officially supports Python 2.7 & 3.4–3.7, and runs great on + PyPy. + + Installation + ------------ + + To install Requests, simply use [pipenv](http://pipenv.org/) (or pip, of + course): + + ``` {.sourceCode .bash} + $ pipenv install requests + ✨🍰✨ + ``` + + Satisfaction guaranteed. + + Documentation + ------------- + + Fantastic documentation is available at + , for a limited time only. + + How to Contribute + ----------------- + + 1. Become more familiar with the project by reading our [Contributor's Guide](http://docs.python-requests.org/en/latest/dev/contributing/) and our [development philosophy](http://docs.python-requests.org/en/latest/dev/philosophy/). + 2. Check for open issues or open a fresh issue to start a discussion + around a feature idea or a bug. There is a [Contributor + Friendly](https://github.com/requests/requests/issues?direction=desc&labels=Contributor+Friendly&page=1&sort=updated&state=open) + tag for issues that should be ideal for people who are not very + familiar with the codebase yet. + 3. Fork [the repository](https://github.com/requests/requests) on + GitHub to start making your changes to the **master** branch (or + branch off of it). + 4. Write a test which shows that the bug was fixed or that the feature + works as expected. + 5. Send a pull request and bug the maintainer until it gets merged and + published. :) Make sure to add yourself to + [AUTHORS](https://github.com/requests/requests/blob/master/AUTHORS.rst). + + +Platform: UNKNOWN +Classifier: Development Status :: 5 - Production/Stable +Classifier: Intended Audience :: Developers +Classifier: Natural Language :: English +Classifier: License :: OSI Approved :: Apache Software License +Classifier: Programming Language :: Python +Classifier: Programming Language :: Python :: 2 +Classifier: Programming Language :: Python :: 2.7 +Classifier: Programming Language :: Python :: 3 +Classifier: Programming Language :: Python :: 3.5 +Classifier: Programming Language :: Python :: 3.6 +Classifier: Programming Language :: Python :: 3.7 +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Programming Language :: Python :: Implementation :: PyPy +Requires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.* +Description-Content-Type: text/markdown +Provides-Extra: security +Provides-Extra: socks \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/egg-info/top_level.txt b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/egg-info/top_level.txt new file mode 100644 index 0000000000000000000000000000000000000000..1e09fdb905661b12c39d33fa1f4548c807d6a330 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/egg-info/top_level.txt @@ -0,0 +1 @@ +top-level-pkg \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/requirements-dev.txt b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/requirements-dev.txt new file mode 100644 index 0000000000000000000000000000000000000000..16c74e8b57525721872c22981cb4b3d407bdf04a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/requirements-dev.txt @@ -0,0 +1,2 @@ +jsonschema==2.6.0 +passlib==1.7.2 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/requirements.txt b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/requirements.txt new file mode 100644 index 0000000000000000000000000000000000000000..cb93b3b55fddd09c9789a3bd269257a67e21ec0e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/requirements.txt @@ -0,0 +1,3 @@ +flask==4.0.0 +# this is an ignored line + diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/test-requirements.txt b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/test-requirements.txt new file mode 100644 index 0000000000000000000000000000000000000000..6f32e8e00300e32152750c61dec04c048a7951dc --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/requires/test-requirements.txt @@ -0,0 +1,3 @@ +python-dateutil==2.8.1 +python-swiftclient==3.8.1 +pytz==2019.3 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/setup/setup.py b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/setup/setup.py new file mode 100644 index 0000000000000000000000000000000000000000..6ebfd67fbf59fb0cf2e3e36a11ac283a4fa64f4b --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/setup/setup.py @@ -0,0 +1,42 @@ +from setuptools import setup + +# TODO: if py gets upgrade to >=1.6, +# remove _width_of_current_line in terminal.py +INSTALL_REQUIRES = [ + "py>=1.5.0", + "packaging", + "attrs>=17.4.0", # should match oldattrs tox env. + "more-itertools>=4.0.0", + 'atomicwrites>=1.0;sys_platform=="win32"', + 'pathlib2>=2.2.0;python_version<"3.6"', + 'colorama;sys_platform=="win32"', + "pluggy>=0.12,<1.0", + 'importlib-metadata>=0.12;python_version<"3.8"', + "wcwidth", +] + + +def main(): + setup( + use_scm_version={"write_to": "src/_pytest/_version.py"}, + setup_requires=["setuptools-scm", "setuptools>=40.0"], + package_dir={"": "src"}, + extras_require={ + "testing": [ + "argcomplete", + "hypothesis>=3.56", + "mock", + "nose", + "requests", + "xmlschema", + ], + "checkqa-mypy": [ + "mypy==v0.770", # keep this in sync with .pre-commit-config.yaml. + ], + }, + install_requires=INSTALL_REQUIRES, + ) + + +if __name__ == "__main__": + main() diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/somerequests-3.22.0.dist-info/METADATA b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/somerequests-3.22.0.dist-info/METADATA new file mode 100644 index 0000000000000000000000000000000000000000..ddc02219bef8e7874e132dfe928bba58a4d215af --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/somerequests-3.22.0.dist-info/METADATA @@ -0,0 +1,26 @@ +Metadata-Version: 2.1 +Name: somerequests +Version: 3.22.0 +Summary: stuff +Home-page: stuff +Author: Georg Brandl +Author-email: georg@python.org +License: BSD License +Platform: any +Classifier: License :: OSI Approved :: BSD License +Classifier: Intended Audience :: Developers +Classifier: Intended Audience :: End Users/Desktop +Classifier: Intended Audience :: System Administrators +Classifier: Development Status :: 6 - Mature +Classifier: Programming Language :: Python +Classifier: Programming Language :: Python :: 3 +Classifier: Programming Language :: Python :: 3.5 +Classifier: Programming Language :: Python :: 3.6 +Classifier: Programming Language :: Python :: 3.7 +Classifier: Programming Language :: Python :: 3.8 +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Programming Language :: Python :: Implementation :: PyPy +Classifier: Operating System :: OS Independent +Classifier: Topic :: Text Processing :: Filters +Classifier: Topic :: Utilities +Requires-Python: >=3.5 \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/somerequests-3.22.0.dist-info/top_level.txt b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/somerequests-3.22.0.dist-info/top_level.txt new file mode 100644 index 0000000000000000000000000000000000000000..1e09fdb905661b12c39d33fa1f4548c807d6a330 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/python/somerequests-3.22.0.dist-info/top_level.txt @@ -0,0 +1 @@ +top-level-pkg \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/Gemfile.lock b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/Gemfile.lock new file mode 100644 index 0000000000000000000000000000000000000000..b5aa45cbc106e6868ea10bb073c03fe4961cc82e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/Gemfile.lock @@ -0,0 +1,149 @@ +GEM + remote: https://rubygems.org/ + specs: + actionmailer (4.1.1) + actionpack (= 4.1.1) + actionview (= 4.1.1) + mail (~> 2.5.4) + actionpack (4.1.1) + actionview (= 4.1.1) + activesupport (= 4.1.1) + rack (~> 1.5.2) + rack-test (~> 0.6.2) + actionview (4.1.1) + activesupport (= 4.1.1) + builder (~> 3.1) + erubis (~> 2.7.0) + activemodel (4.1.1) + activesupport (= 4.1.1) + builder (~> 3.1) + activerecord (4.1.1) + activemodel (= 4.1.1) + activesupport (= 4.1.1) + arel (~> 5.0.0) + activesupport (4.1.1) + i18n (~> 0.6, >= 0.6.9) + json (~> 1.7, >= 1.7.7) + minitest (~> 5.1) + thread_safe (~> 0.1) + tzinfo (~> 1.1) + arel (5.0.1.20140414130214) + bootstrap-sass (3.1.1.1) + sass (~> 3.2) + builder (3.2.2) + coffee-rails (4.0.1) + coffee-script (>= 2.2.0) + railties (>= 4.0.0, < 5.0) + coffee-script (2.2.0) + coffee-script-source + execjs + coffee-script-source (1.7.0) + erubis (2.7.0) + execjs (2.0.2) + hike (1.2.3) + i18n (0.6.9) + jbuilder (2.0.7) + activesupport (>= 3.0.0, < 5) + multi_json (~> 1.2) + jquery-rails (3.1.0) + railties (>= 3.0, < 5.0) + thor (>= 0.14, < 2.0) + json (1.8.1) + kgio (2.9.2) + libv8 (3.16.14.3) + mail (2.5.4) + mime-types (~> 1.16) + treetop (~> 1.4.8) + mime-types (1.25.1) + minitest (5.3.4) + multi_json (1.10.1) + mysql2 (0.3.16) + polyglot (0.3.4) + rack (1.5.2) + rack-test (0.6.2) + rack (>= 1.0) + rails (4.1.1) + actionmailer (= 4.1.1) + actionpack (= 4.1.1) + actionview (= 4.1.1) + activemodel (= 4.1.1) + activerecord (= 4.1.1) + activesupport (= 4.1.1) + bundler (>= 1.3.0, < 2.0) + railties (= 4.1.1) + sprockets-rails (~> 2.0) + railties (4.1.1) + actionpack (= 4.1.1) + activesupport (= 4.1.1) + rake (>= 0.8.7) + thor (>= 0.18.1, < 2.0) + raindrops (0.13.0) + rake (10.3.2) + rdoc (4.1.1) + json (~> 1.4) + ref (1.0.5) + sass (3.2.19) + sass-rails (4.0.3) + railties (>= 4.0.0, < 5.0) + sass (~> 3.2.0) + sprockets (~> 2.8, <= 2.11.0) + sprockets-rails (~> 2.0) + sdoc (0.4.0) + json (~> 1.8) + rdoc (~> 4.0, < 5.0) + spring (1.1.3) + sprockets (2.11.0) + hike (~> 1.2) + multi_json (~> 1.0) + rack (~> 1.0) + tilt (~> 1.1, != 1.3.0) + sprockets-rails (2.1.3) + actionpack (>= 3.0) + activesupport (>= 3.0) + sprockets (~> 2.8) + sqlite3 (1.3.9) + therubyracer (0.12.1) + libv8 (~> 3.16.14.0) + ref + thor (0.19.1) + thread_safe (0.3.3) + tilt (1.4.1) + treetop (1.4.15) + polyglot + polyglot (>= 0.3.1) + turbolinks (2.2.2) + coffee-rails + tzinfo (1.2.0) + thread_safe (~> 0.1) + uglifier (2.5.0) + execjs (>= 0.3.0) + json (>= 1.8.0) + unicorn (4.8.3) + kgio (~> 2.6) + rack + raindrops (~> 0.7) + +BAD-SECTION + bad-entry (5.5.5) + bad-kgio (~> 2.6) + bad-rack + bad-raindrops (~> 0.7) + +PLATFORMS + ruby + +DEPENDENCIES + bootstrap-sass + coffee-rails (~> 4.0.0) + jbuilder (~> 2.0) + jquery-rails + mysql2 (~> 0.3.16) + rails (= 4.1.1) + sass-rails (~> 4.0.3) + sdoc (~> 0.4.0) + spring + sqlite3 + therubyracer + turbolinks + uglifier (>= 1.3.0) + unicorn \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/specifications/bundler.gemspec b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/specifications/bundler.gemspec new file mode 100644 index 0000000000000000000000000000000000000000..450b81096b67fdc2597425f29a7e314ef9701ae1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/specifications/bundler.gemspec @@ -0,0 +1,25 @@ +# frozen_string_literal: true +# -*- encoding: utf-8 -*- +# stub: bundler 2.1.4 ruby lib + +Gem::Specification.new do |s| + s.name = "bundler".freeze + s.version = "2.1.4" + + s.required_rubygems_version = Gem::Requirement.new(">= 2.5.2".freeze) if s.respond_to? :required_rubygems_version= + s.require_paths = ["lib".freeze] + s.authors = ["Andr\u00E9 Arko".freeze, "Samuel Giddins".freeze, "Colby Swandale".freeze, "Hiroshi Shibata".freeze, "David Rodr\u00EDguez".freeze, "Grey Baker".f + s.bindir = "exe".freeze + s.date = "2020-01-05" + s.description = "Bundler manages an application's dependencies through its entire life, across many machines, systematically and repeatably".freeze + s.email = ["team@bundler.io".freeze] + s.executables = ["bundle".freeze, "bundler".freeze] + s.files = ["exe/bundle".freeze, "exe/bundler".freeze] + s.homepage = "https://bundler.io".freeze + s.licenses = ["MIT".freeze] + s.required_ruby_version = Gem::Requirement.new(">= 2.3.0".freeze) + s.rubygems_version = "3.1.2".freeze + s.summary = "The best way to manage your application's dependencies".freeze + + s.installed_by_version = "3.1.2" if s.respond_to? :installed_by_version + end \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/specifications/default/unbundler.gemspec b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/specifications/default/unbundler.gemspec new file mode 100644 index 0000000000000000000000000000000000000000..f5f493c617e3de5170f1c911fb581ef4e533655d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/ruby/specifications/default/unbundler.gemspec @@ -0,0 +1,25 @@ +# frozen_string_literal: true +# -*- encoding: utf-8 -*- +# stub: unbundler 2.1.4 ruby lib + +Gem::Specification.new do |s| + s.name = "unbundler".freeze + s.version = "3.1.4" + + s.required_rubygems_version = Gem::Requirement.new(">= 2.5.2".freeze) if s.respond_to? :required_rubygems_version= + s.require_paths = ["lib".freeze] + s.authors = ["Andr\u00E9 Arko".freeze, "Samuel Giddins".freeze, "Colby Swandale".freeze, "Hiroshi Shibata".freeze, "David Rodr\u00EDguez".freeze, "Grey Baker".f + s.bindir = "exe".freeze + s.date = "2020-01-05" + s.description = "Bundler manages an application's dependencies through its entire life, across many machines, systematically and repeatably".freeze + s.email = ["team@unbundler.io".freeze] + s.executables = ["unbundle".freeze, "unbundler".freeze] + s.files = ["exe/unbundle".freeze, "exe/unbundler".freeze] + s.homepage = "https://unbundler.io".freeze + s.licenses = ["MIT".freeze] + s.required_ruby_version = Gem::Requirement.new(">= 2.3.0".freeze) + s.rubygems_version = "3.1.2".freeze + s.summary = "The best way to manage your application's dependencies".freeze + + s.installed_by_version = "3.1.2" if s.respond_to? :installed_by_version + end \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/rust/Cargo.lock b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/rust/Cargo.lock new file mode 100644 index 0000000000000000000000000000000000000000..f2a838632ba4053482a68d414b18550829348fd7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-pkg-coverage/pkgs/rust/Cargo.lock @@ -0,0 +1,25 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. + +[[package]] +name = "memchr" +version = "2.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3728d817d99e5ac407411fa471ff9800a778d88a24685968b36824eaf4bee400" + +[[package]] +name = "nom" +version = "4.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2ad2a91a8e869eeb30b9cb3119ae87773a8f4ae617f41b1eb9c154b2905f7bd6" +dependencies = [ + "memchr", + "version_check", +] + +[[package]] +name = "version_check" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "914b1a6776c4c929a602fafd8bc742e06365d4bcbe48c30f9cca5824f70dc9dd" + diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-rust-auditable/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-rust-auditable/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..a35897003b98f757f2165572f752eeebc8da4895 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-rust-auditable/Dockerfile @@ -0,0 +1,2 @@ +# An image containing the example hello-auditable binary from https://github.com/Shnatsel/rust-audit/tree/master/hello-auditable +FROM docker.io/tofay/hello-rust-auditable:latest diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-sqlite-rpmdb/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-sqlite-rpmdb/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..938b431d518a9cb427fb6a3651fa222e235c2432 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-sqlite-rpmdb/Dockerfile @@ -0,0 +1 @@ +FROM fedora:35@sha256:36af84ba69e21c9ef86a0424a090674c433b2b80c2462e57503886f1d823abe8 diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-vertical-package-dups/Dockerfile b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-vertical-package-dups/Dockerfile new file mode 100644 index 0000000000000000000000000000000000000000..ebe48155d3fa5d3ea2dfe5a7bde03e80eeb28e57 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/image-vertical-package-dups/Dockerfile @@ -0,0 +1,6 @@ +FROM centos:7.9.2009 +# modifying the RPM DB multiple times will result in duplicate packages when using all-layers (if there was no de-dup logic) +# curl is tricky, it already exists in the image and is being upgraded +RUN yum install -y wget curl +RUN yum install -y vsftpd +RUN yum install -y httpd \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/index.d.ts b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/index.d.ts new file mode 100644 index 0000000000000000000000000000000000000000..dc15b553fbdf172a12ee0ff0b5fbb4afd14ae865 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/index.d.ts @@ -0,0 +1,7 @@ +/** + * Collapse whitespace to a single space. + * + * @param {string} value + * @returns {string} + */ +export function collapseWhiteSpace(value: string): string; diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/index.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/index.js new file mode 100644 index 0000000000000000000000000000000000000000..baa70d8b2c925a67b559fcfd7854a89531a2712e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/index.js @@ -0,0 +1,9 @@ +/** + * Collapse whitespace to a single space. + * + * @param {string} value + * @returns {string} + */ +export function collapseWhiteSpace(value) { + return String(value).replace(/\s+/g, ' ') +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/license b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/license new file mode 100644 index 0000000000000000000000000000000000000000..32e7a3d93ca5a2b8cce57405841a44e78f3fbb55 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/license @@ -0,0 +1,22 @@ +(The MIT License) + +Copyright (c) 2015 Titus Wormer + +Permission is hereby granted, free of charge, to any person obtaining +a copy of this software and associated documentation files (the +'Software'), to deal in the Software without restriction, including +without limitation the rights to use, copy, modify, merge, publish, +distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to +the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY +CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/package-lock.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/package-lock.json new file mode 100644 index 0000000000000000000000000000000000000000..b3c33eeb7ba70188e8928a08ef43c19f97df5928 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/package-lock.json @@ -0,0 +1,8360 @@ +{ + "name": "collapse-white-space", + "version": "2.0.0", + "lockfileVersion": 1, + "requires": true, + "dependencies": { + "@babel/code-frame": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.14.5.tgz", + "integrity": "sha512-9pzDqyc6OLDaqe+zbACgFkb6fKMNG6CObKpnYXChRsvYGyEdc7CA2BaqeOM+vOtCS5ndmJicPJhKAwYRI6UfFw==", + "dev": true, + "requires": { + "@babel/highlight": "^7.14.5" + } + }, + "@babel/compat-data": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.15.0.tgz", + "integrity": "sha512-0NqAC1IJE0S0+lL1SWFMxMkz1pKCNCjI4tr2Zx4LJSXxCLAdr6KyArnY+sno5m3yH9g737ygOyPABDsnXkpxiA==", + "dev": true + }, + "@babel/core": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.15.0.tgz", + "integrity": "sha512-tXtmTminrze5HEUPn/a0JtOzzfp0nk+UEXQ/tqIJo3WDGypl/2OFQEMll/zSFU8f/lfmfLXvTaORHF3cfXIQMw==", + "dev": true, + "requires": { + "@babel/code-frame": "^7.14.5", + "@babel/generator": "^7.15.0", + "@babel/helper-compilation-targets": "^7.15.0", + "@babel/helper-module-transforms": "^7.15.0", + "@babel/helpers": "^7.14.8", + "@babel/parser": "^7.15.0", + "@babel/template": "^7.14.5", + "@babel/traverse": "^7.15.0", + "@babel/types": "^7.15.0", + "convert-source-map": "^1.7.0", + "debug": "^4.1.0", + "gensync": "^1.0.0-beta.2", + "json5": "^2.1.2", + "semver": "^6.3.0", + "source-map": "^0.5.0" + }, + "dependencies": { + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", + "dev": true + } + } + }, + "@babel/eslint-parser": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/eslint-parser/-/eslint-parser-7.15.0.tgz", + "integrity": "sha512-+gSPtjSBxOZz4Uh8Ggqu7HbfpB8cT1LwW0DnVVLZEJvzXauiD0Di3zszcBkRmfGGrLdYeHUwcflG7i3tr9kQlw==", + "dev": true, + "requires": { + "eslint-scope": "^5.1.1", + "eslint-visitor-keys": "^2.1.0", + "semver": "^6.3.0" + } + }, + "@babel/generator": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.15.0.tgz", + "integrity": "sha512-eKl4XdMrbpYvuB505KTta4AV9g+wWzmVBW69tX0H2NwKVKd2YJbKgyK6M8j/rgLbmHOYJn6rUklV677nOyJrEQ==", + "dev": true, + "requires": { + "@babel/types": "^7.15.0", + "jsesc": "^2.5.1", + "source-map": "^0.5.0" + }, + "dependencies": { + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", + "dev": true + } + } + }, + "@babel/helper-compilation-targets": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.15.0.tgz", + "integrity": "sha512-h+/9t0ncd4jfZ8wsdAsoIxSa61qhBYlycXiHWqJaQBCXAhDCMbPRSMTGnZIkkmt1u4ag+UQmuqcILwqKzZ4N2A==", + "dev": true, + "requires": { + "@babel/compat-data": "^7.15.0", + "@babel/helper-validator-option": "^7.14.5", + "browserslist": "^4.16.6", + "semver": "^6.3.0" + } + }, + "@babel/helper-function-name": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.14.5.tgz", + "integrity": "sha512-Gjna0AsXWfFvrAuX+VKcN/aNNWonizBj39yGwUzVDVTlMYJMK2Wp6xdpy72mfArFq5uK+NOuexfzZlzI1z9+AQ==", + "dev": true, + "requires": { + "@babel/helper-get-function-arity": "^7.14.5", + "@babel/template": "^7.14.5", + "@babel/types": "^7.14.5" + } + }, + "@babel/helper-get-function-arity": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/helper-get-function-arity/-/helper-get-function-arity-7.14.5.tgz", + "integrity": "sha512-I1Db4Shst5lewOM4V+ZKJzQ0JGGaZ6VY1jYvMghRjqs6DWgxLCIyFt30GlnKkfUeFLpJt2vzbMVEXVSXlIFYUg==", + "dev": true, + "requires": { + "@babel/types": "^7.14.5" + } + }, + "@babel/helper-hoist-variables": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/helper-hoist-variables/-/helper-hoist-variables-7.14.5.tgz", + "integrity": "sha512-R1PXiz31Uc0Vxy4OEOm07x0oSjKAdPPCh3tPivn/Eo8cvz6gveAeuyUUPB21Hoiif0uoPQSSdhIPS3352nvdyQ==", + "dev": true, + "requires": { + "@babel/types": "^7.14.5" + } + }, + "@babel/helper-member-expression-to-functions": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.15.0.tgz", + "integrity": "sha512-Jq8H8U2kYiafuj2xMTPQwkTBnEEdGKpT35lJEQsRRjnG0LW3neucsaMWLgKcwu3OHKNeYugfw+Z20BXBSEs2Lg==", + "dev": true, + "requires": { + "@babel/types": "^7.15.0" + } + }, + "@babel/helper-module-imports": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.14.5.tgz", + "integrity": "sha512-SwrNHu5QWS84XlHwGYPDtCxcA0hrSlL2yhWYLgeOc0w7ccOl2qv4s/nARI0aYZW+bSwAL5CukeXA47B/1NKcnQ==", + "dev": true, + "requires": { + "@babel/types": "^7.14.5" + } + }, + "@babel/helper-module-transforms": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.15.0.tgz", + "integrity": "sha512-RkGiW5Rer7fpXv9m1B3iHIFDZdItnO2/BLfWVW/9q7+KqQSDY5kUfQEbzdXM1MVhJGcugKV7kRrNVzNxmk7NBg==", + "dev": true, + "requires": { + "@babel/helper-module-imports": "^7.14.5", + "@babel/helper-replace-supers": "^7.15.0", + "@babel/helper-simple-access": "^7.14.8", + "@babel/helper-split-export-declaration": "^7.14.5", + "@babel/helper-validator-identifier": "^7.14.9", + "@babel/template": "^7.14.5", + "@babel/traverse": "^7.15.0", + "@babel/types": "^7.15.0" + } + }, + "@babel/helper-optimise-call-expression": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/helper-optimise-call-expression/-/helper-optimise-call-expression-7.14.5.tgz", + "integrity": "sha512-IqiLIrODUOdnPU9/F8ib1Fx2ohlgDhxnIDU7OEVi+kAbEZcyiF7BLU8W6PfvPi9LzztjS7kcbzbmL7oG8kD6VA==", + "dev": true, + "requires": { + "@babel/types": "^7.14.5" + } + }, + "@babel/helper-replace-supers": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.15.0.tgz", + "integrity": "sha512-6O+eWrhx+HEra/uJnifCwhwMd6Bp5+ZfZeJwbqUTuqkhIT6YcRhiZCOOFChRypOIe0cV46kFrRBlm+t5vHCEaA==", + "dev": true, + "requires": { + "@babel/helper-member-expression-to-functions": "^7.15.0", + "@babel/helper-optimise-call-expression": "^7.14.5", + "@babel/traverse": "^7.15.0", + "@babel/types": "^7.15.0" + } + }, + "@babel/helper-simple-access": { + "version": "7.14.8", + "resolved": "https://registry.npmjs.org/@babel/helper-simple-access/-/helper-simple-access-7.14.8.tgz", + "integrity": "sha512-TrFN4RHh9gnWEU+s7JloIho2T76GPwRHhdzOWLqTrMnlas8T9O7ec+oEDNsRXndOmru9ymH9DFrEOxpzPoSbdg==", + "dev": true, + "requires": { + "@babel/types": "^7.14.8" + } + }, + "@babel/helper-split-export-declaration": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.14.5.tgz", + "integrity": "sha512-hprxVPu6e5Kdp2puZUmvOGjaLv9TCe58E/Fl6hRq4YiVQxIcNvuq6uTM2r1mT/oPskuS9CgR+I94sqAYv0NGKA==", + "dev": true, + "requires": { + "@babel/types": "^7.14.5" + } + }, + "@babel/helper-validator-identifier": { + "version": "7.14.9", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.14.9.tgz", + "integrity": "sha512-pQYxPY0UP6IHISRitNe8bsijHex4TWZXi2HwKVsjPiltzlhse2znVcm9Ace510VT1kxIHjGJCZZQBX2gJDbo0g==", + "dev": true + }, + "@babel/helper-validator-option": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.14.5.tgz", + "integrity": "sha512-OX8D5eeX4XwcroVW45NMvoYaIuFI+GQpA2a8Gi+X/U/cDUIRsV37qQfF905F0htTRCREQIB4KqPeaveRJUl3Ow==", + "dev": true + }, + "@babel/helpers": { + "version": "7.15.3", + "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.15.3.tgz", + "integrity": "sha512-HwJiz52XaS96lX+28Tnbu31VeFSQJGOeKHJeaEPQlTl7PnlhFElWPj8tUXtqFIzeN86XxXoBr+WFAyK2PPVz6g==", + "dev": true, + "requires": { + "@babel/template": "^7.14.5", + "@babel/traverse": "^7.15.0", + "@babel/types": "^7.15.0" + } + }, + "@babel/highlight": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.14.5.tgz", + "integrity": "sha512-qf9u2WFWVV0MppaL877j2dBtQIDgmidgjGk5VIMw3OadXvYaXn66U1BFlH2t4+t3i+8PhedppRv+i40ABzd+gg==", + "dev": true, + "requires": { + "@babel/helper-validator-identifier": "^7.14.5", + "chalk": "^2.0.0", + "js-tokens": "^4.0.0" + }, + "dependencies": { + "ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, + "requires": { + "color-convert": "^1.9.0" + } + }, + "chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, + "requires": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + } + }, + "color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, + "requires": { + "color-name": "1.1.3" + } + }, + "color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", + "dev": true + }, + "has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true + }, + "supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "requires": { + "has-flag": "^3.0.0" + } + } + } + }, + "@babel/parser": { + "version": "7.15.3", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.15.3.tgz", + "integrity": "sha512-O0L6v/HvqbdJawj0iBEfVQMc3/6WP+AeOsovsIgBFyJaG+W2w7eqvZB7puddATmWuARlm1SX7DwxJ/JJUnDpEA==", + "dev": true + }, + "@babel/template": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.14.5.tgz", + "integrity": "sha512-6Z3Po85sfxRGachLULUhOmvAaOo7xCvqGQtxINai2mEGPFm6pQ4z5QInFnUrRpfoSV60BnjyF5F3c+15fxFV1g==", + "dev": true, + "requires": { + "@babel/code-frame": "^7.14.5", + "@babel/parser": "^7.14.5", + "@babel/types": "^7.14.5" + } + }, + "@babel/traverse": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.15.0.tgz", + "integrity": "sha512-392d8BN0C9eVxVWd8H6x9WfipgVH5IaIoLp23334Sc1vbKKWINnvwRpb4us0xtPaCumlwbTtIYNA0Dv/32sVFw==", + "dev": true, + "requires": { + "@babel/code-frame": "^7.14.5", + "@babel/generator": "^7.15.0", + "@babel/helper-function-name": "^7.14.5", + "@babel/helper-hoist-variables": "^7.14.5", + "@babel/helper-split-export-declaration": "^7.14.5", + "@babel/parser": "^7.15.0", + "@babel/types": "^7.15.0", + "debug": "^4.1.0", + "globals": "^11.1.0" + }, + "dependencies": { + "globals": { + "version": "11.12.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", + "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==", + "dev": true + } + } + }, + "@babel/types": { + "version": "7.15.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.15.0.tgz", + "integrity": "sha512-OBvfqnllOIdX4ojTHpwZbpvz4j3EWyjkZEdmjH0/cgsd6QOdSgU8rLSk6ard/pcW7rlmjdVSX/AWOaORR1uNOQ==", + "dev": true, + "requires": { + "@babel/helper-validator-identifier": "^7.14.9", + "to-fast-properties": "^2.0.0" + } + }, + "@bcoe/v8-coverage": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz", + "integrity": "sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw==", + "dev": true + }, + "@eslint/eslintrc": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-0.4.3.tgz", + "integrity": "sha512-J6KFFz5QCYUJq3pf0mjEcCJVERbzv71PUIDczuh9JkwGEzced6CO5ADLHB1rbf/+oPBtoPfMYNOpGDzCANlbXw==", + "dev": true, + "requires": { + "ajv": "^6.12.4", + "debug": "^4.1.1", + "espree": "^7.3.0", + "globals": "^13.9.0", + "ignore": "^4.0.6", + "import-fresh": "^3.2.1", + "js-yaml": "^3.13.1", + "minimatch": "^3.0.4", + "strip-json-comments": "^3.1.1" + }, + "dependencies": { + "ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", + "dev": true + } + } + }, + "@humanwhocodes/config-array": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.5.0.tgz", + "integrity": "sha512-FagtKFz74XrTl7y6HCzQpwDfXP0yhxe9lHLD1UZxjvZIcbyRz8zTFF/yYNfSfzU414eDwZ1SrO0Qvtyf+wFMQg==", + "dev": true, + "requires": { + "@humanwhocodes/object-schema": "^1.2.0", + "debug": "^4.1.1", + "minimatch": "^3.0.4" + } + }, + "@humanwhocodes/object-schema": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-1.2.0.tgz", + "integrity": "sha512-wdppn25U8z/2yiaT6YGquE6X8sSv7hNMWSXYSSU1jGv/yd6XqjXgTDJ8KP4NgjTXfJ3GbRjeeb8RTV7a/VpM+w==", + "dev": true + }, + "@istanbuljs/schema": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/@istanbuljs/schema/-/schema-0.1.3.tgz", + "integrity": "sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==", + "dev": true + }, + "@mrmlnc/readdir-enhanced": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/@mrmlnc/readdir-enhanced/-/readdir-enhanced-2.2.1.tgz", + "integrity": "sha512-bPHp6Ji8b41szTOcaP63VlnbbO5Ny6dwAATtY6JTjh5N2OLrb5Qk/Th5cRkRQhkWCt+EJsYrNB0MiL+Gpn6e3g==", + "dev": true, + "requires": { + "call-me-maybe": "^1.0.1", + "glob-to-regexp": "^0.3.0" + } + }, + "@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", + "dev": true, + "requires": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + } + }, + "@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", + "dev": true + }, + "@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", + "dev": true, + "requires": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + } + }, + "@sindresorhus/is": { + "version": "0.14.0", + "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.14.0.tgz", + "integrity": "sha512-9NET910DNaIPngYnLLPeg+Ogzqsi9uM4mSboU5y6p8S5DzMTVEsJZrawi+BoDNUVBa2DhJqQYUFvMDfgU062LQ==", + "dev": true + }, + "@szmarczak/http-timer": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-1.1.2.tgz", + "integrity": "sha512-XIB2XbzHTN6ieIjfIMV9hlVcfPU26s2vafYWQcZHWXHOxiaRZYEDKEwdl129Zyg50+foYV2jCgtrqSA6qNuNSA==", + "dev": true, + "requires": { + "defer-to-connect": "^1.0.1" + } + }, + "@types/eslint": { + "version": "7.28.0", + "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-7.28.0.tgz", + "integrity": "sha512-07XlgzX0YJUn4iG1ocY4IX9DzKSmMGUs6ESKlxWhZRaa0fatIWaHWUVapcuGa8r5HFnTqzj+4OCjd5f7EZ/i/A==", + "dev": true, + "requires": { + "@types/estree": "*", + "@types/json-schema": "*" + } + }, + "@types/estree": { + "version": "0.0.50", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.50.tgz", + "integrity": "sha512-C6N5s2ZFtuZRj54k2/zyRhNDjJwwcViAM3Nbm8zjBpbqAdZ00mr0CFxvSKeO8Y/e03WVFLpQMdHYVfUd6SB+Hw==", + "dev": true + }, + "@types/glob": { + "version": "7.1.4", + "resolved": "https://registry.npmjs.org/@types/glob/-/glob-7.1.4.tgz", + "integrity": "sha512-w+LsMxKyYQm347Otw+IfBXOv9UWVjpHpCDdbBMt8Kz/xbvCYNjP+0qPh91Km3iKfSRLBB0P7fAMf0KHrPu+MyA==", + "dev": true, + "requires": { + "@types/minimatch": "*", + "@types/node": "*" + } + }, + "@types/istanbul-lib-coverage": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/@types/istanbul-lib-coverage/-/istanbul-lib-coverage-2.0.3.tgz", + "integrity": "sha512-sz7iLqvVUg1gIedBOvlkxPlc8/uVzyS5OwGz1cKjXzkl3FpL3al0crU8YGU1WoHkxn0Wxbw5tyi6hvzJKNzFsw==", + "dev": true + }, + "@types/json-schema": { + "version": "7.0.9", + "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.9.tgz", + "integrity": "sha512-qcUXuemtEu+E5wZSJHNxUXeCZhAfXKQ41D+duX+VYPde7xyEVZci+/oXKJL13tnRs9lR2pr4fod59GT6/X1/yQ==", + "dev": true + }, + "@types/mdast": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-3.0.8.tgz", + "integrity": "sha512-HdUXWDNtDenuVJFrV2xBCLEMiw1Vn7FMuJxqJC5oBvC2adA3pgtp6CPCIMQdz3pmWxGuJjT+hOp6FnOXy6dXoQ==", + "dev": true, + "requires": { + "@types/unist": "*" + } + }, + "@types/minimatch": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-3.0.5.tgz", + "integrity": "sha512-Klz949h02Gz2uZCMGwDUSDS1YBlTdDDgbWHi+81l29tQALUtvz4rAYi5uoVhE5Lagoq6DeqAUlbrHvW/mXDgdQ==", + "dev": true + }, + "@types/minimist": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/@types/minimist/-/minimist-1.2.2.tgz", + "integrity": "sha512-jhuKLIRrhvCPLqwPcx6INqmKeiA5EWrsCOPhrlFSrbrmU4ZMPjj5Ul/oLCMDO98XRUIwVm78xICz4EPCektzeQ==", + "dev": true + }, + "@types/node": { + "version": "16.6.2", + "resolved": "https://registry.npmjs.org/@types/node/-/node-16.6.2.tgz", + "integrity": "sha512-LSw8TZt12ZudbpHc6EkIyDM3nHVWKYrAvGy6EAJfNfjusbwnThqjqxUKKRwuV3iWYeW/LYMzNgaq3MaLffQ2xA==", + "dev": true + }, + "@types/normalize-package-data": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/@types/normalize-package-data/-/normalize-package-data-2.4.1.tgz", + "integrity": "sha512-Gj7cI7z+98M282Tqmp2K5EIsoouUEzbBJhQQzDE3jSIRk6r9gsz0oUokqIUR4u1R3dMHo0pDHM7sNOHyhulypw==", + "dev": true + }, + "@types/parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/@types/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha512-//oorEZjL6sbPcKUaCdIGlIUeH26mgzimjBB77G6XRgnDl/L5wOnpyBGRe/Mmf5CVW3PwEBE1NjiMZ/ssFh4wA==", + "dev": true + }, + "@types/tape": { + "version": "4.13.2", + "resolved": "https://registry.npmjs.org/@types/tape/-/tape-4.13.2.tgz", + "integrity": "sha512-V1ez/RtYRGN9cNYApw5xf27DpMkTB0033X6a2i3KUmKhSojBfbWN0i3EgZxboUG96WJLHLdOyZ01aiZwVW5aSA==", + "dev": true, + "requires": { + "@types/node": "*" + } + }, + "@types/unist": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.6.tgz", + "integrity": "sha512-PBjIUxZHOuj0R15/xuwJYjFi+KZdNFrehocChv4g5hu6aFroHue8m0lBP0POdK2nKzbw0cgV1mws8+V/JAcEkQ==", + "dev": true + }, + "@typescript-eslint/eslint-plugin": { + "version": "4.29.2", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-4.29.2.tgz", + "integrity": "sha512-x4EMgn4BTfVd9+Z+r+6rmWxoAzBaapt4QFqE+d8L8sUtYZYLDTK6VG/y/SMMWA5t1/BVU5Kf+20rX4PtWzUYZg==", + "dev": true, + "requires": { + "@typescript-eslint/experimental-utils": "4.29.2", + "@typescript-eslint/scope-manager": "4.29.2", + "debug": "^4.3.1", + "functional-red-black-tree": "^1.0.1", + "regexpp": "^3.1.0", + "semver": "^7.3.5", + "tsutils": "^3.21.0" + }, + "dependencies": { + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + } + } + }, + "@typescript-eslint/experimental-utils": { + "version": "4.29.2", + "resolved": "https://registry.npmjs.org/@typescript-eslint/experimental-utils/-/experimental-utils-4.29.2.tgz", + "integrity": "sha512-P6mn4pqObhftBBPAv4GQtEK7Yos1fz/MlpT7+YjH9fTxZcALbiiPKuSIfYP/j13CeOjfq8/fr9Thr2glM9ub7A==", + "dev": true, + "requires": { + "@types/json-schema": "^7.0.7", + "@typescript-eslint/scope-manager": "4.29.2", + "@typescript-eslint/types": "4.29.2", + "@typescript-eslint/typescript-estree": "4.29.2", + "eslint-scope": "^5.1.1", + "eslint-utils": "^3.0.0" + } + }, + "@typescript-eslint/parser": { + "version": "4.29.2", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-4.29.2.tgz", + "integrity": "sha512-WQ6BPf+lNuwteUuyk1jD/aHKqMQ9jrdCn7Gxt9vvBnzbpj7aWEf+aZsJ1zvTjx5zFxGCt000lsbD9tQPEL8u6g==", + "dev": true, + "requires": { + "@typescript-eslint/scope-manager": "4.29.2", + "@typescript-eslint/types": "4.29.2", + "@typescript-eslint/typescript-estree": "4.29.2", + "debug": "^4.3.1" + } + }, + "@typescript-eslint/scope-manager": { + "version": "4.29.2", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-4.29.2.tgz", + "integrity": "sha512-mfHmvlQxmfkU8D55CkZO2sQOueTxLqGvzV+mG6S/6fIunDiD2ouwsAoiYCZYDDK73QCibYjIZmGhpvKwAB5BOA==", + "dev": true, + "requires": { + "@typescript-eslint/types": "4.29.2", + "@typescript-eslint/visitor-keys": "4.29.2" + } + }, + "@typescript-eslint/types": { + "version": "4.29.2", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-4.29.2.tgz", + "integrity": "sha512-K6ApnEXId+WTGxqnda8z4LhNMa/pZmbTFkDxEBLQAbhLZL50DjeY0VIDCml/0Y3FlcbqXZrABqrcKxq+n0LwzQ==", + "dev": true + }, + "@typescript-eslint/typescript-estree": { + "version": "4.29.2", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-4.29.2.tgz", + "integrity": "sha512-TJ0/hEnYxapYn9SGn3dCnETO0r+MjaxtlWZ2xU+EvytF0g4CqTpZL48SqSNn2hXsPolnewF30pdzR9a5Lj3DNg==", + "dev": true, + "requires": { + "@typescript-eslint/types": "4.29.2", + "@typescript-eslint/visitor-keys": "4.29.2", + "debug": "^4.3.1", + "globby": "^11.0.3", + "is-glob": "^4.0.1", + "semver": "^7.3.5", + "tsutils": "^3.21.0" + }, + "dependencies": { + "globby": { + "version": "11.0.4", + "resolved": "https://registry.npmjs.org/globby/-/globby-11.0.4.tgz", + "integrity": "sha512-9O4MVG9ioZJ08ffbcyVYyLOJLk5JQ688pJ4eMGLpdWLHq/Wr1D9BlriLQyL0E+jbkuePVZXYFj47QM/v093wHg==", + "dev": true, + "requires": { + "array-union": "^2.1.0", + "dir-glob": "^3.0.1", + "fast-glob": "^3.1.1", + "ignore": "^5.1.4", + "merge2": "^1.3.0", + "slash": "^3.0.0" + } + }, + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + } + } + }, + "@typescript-eslint/visitor-keys": { + "version": "4.29.2", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-4.29.2.tgz", + "integrity": "sha512-bDgJLQ86oWHJoZ1ai4TZdgXzJxsea3Ee9u9wsTAvjChdj2WLcVsgWYAPeY7RQMn16tKrlQaBnpKv7KBfs4EQag==", + "dev": true, + "requires": { + "@typescript-eslint/types": "4.29.2", + "eslint-visitor-keys": "^2.0.0" + } + }, + "acorn": { + "version": "7.4.1", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.4.1.tgz", + "integrity": "sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A==", + "dev": true + }, + "acorn-jsx": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", + "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", + "dev": true + }, + "ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + } + }, + "ansi-align": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-align/-/ansi-align-3.0.0.tgz", + "integrity": "sha512-ZpClVKqXN3RGBmKibdfWzqCY4lnjEuoNzU5T0oEFpfd/z5qJHVarukridD4juLO2FXMiwUQxr9WqQtaYa8XRYw==", + "dev": true, + "requires": { + "string-width": "^3.0.0" + }, + "dependencies": { + "ansi-regex": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.1.0.tgz", + "integrity": "sha512-1apePfXM1UOSqw0o9IiFAovVz9M5S1Dg+4TrDwfMewQ6p/rmMueb7tWZjQ1rx4Loy1ArBggoqGpfqqdI4rondg==", + "dev": true + }, + "emoji-regex": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-7.0.3.tgz", + "integrity": "sha512-CwBLREIQ7LvYFB0WyRvwhq5N5qPhc6PMjD6bYggFlI5YyDgl+0vxq5VHbMOFqLg7hfWzmu8T5Z1QofhmTIhItA==", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "string-width": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-3.1.0.tgz", + "integrity": "sha512-vafcv6KjVZKSgz06oM/H6GDBrAtz8vdhQakGjFIvNrHA6y3HCF1CInLy+QLq8dTJPQ1b+KDUqDFctkdRW44e1w==", + "dev": true, + "requires": { + "emoji-regex": "^7.0.1", + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^5.1.0" + } + }, + "strip-ansi": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.2.0.tgz", + "integrity": "sha512-DuRs1gKbBqsMKIZlrffwlug8MHkcnpjs5VPmL1PAh+mA30U0DTotfDZ0d2UUsXpPmPmMMJ6W773MaA3J+lbiWA==", + "dev": true, + "requires": { + "ansi-regex": "^4.1.0" + } + } + } + }, + "ansi-colors": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/ansi-colors/-/ansi-colors-4.1.1.tgz", + "integrity": "sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA==", + "dev": true + }, + "ansi-escapes": { + "version": "4.3.2", + "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-4.3.2.tgz", + "integrity": "sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ==", + "dev": true, + "requires": { + "type-fest": "^0.21.3" + }, + "dependencies": { + "type-fest": { + "version": "0.21.3", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.21.3.tgz", + "integrity": "sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w==", + "dev": true + } + } + }, + "ansi-regex": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.0.tgz", + "integrity": "sha512-bY6fj56OUQ0hU1KjFNDQuJFezqKdrAyFdIevADiqrWHwSlbmBNMHp5ak2f40Pm8JTFyM2mqxkG6ngkHO11f/lg==", + "dev": true + }, + "ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "requires": { + "color-convert": "^2.0.1" + } + }, + "anymatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.2.tgz", + "integrity": "sha512-P43ePfOAIupkguHUycrc4qJ9kz8ZiuOUijaETwX7THt0Y/GNK7v0aa8rY816xWjZ7rJdA5XdMcpVFTKMq+RvWg==", + "dev": true, + "requires": { + "normalize-path": "^3.0.0", + "picomatch": "^2.0.4" + } + }, + "argparse": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", + "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "dev": true, + "requires": { + "sprintf-js": "~1.0.2" + } + }, + "arr-diff": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz", + "integrity": "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=", + "dev": true + }, + "arr-flatten": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", + "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==", + "dev": true + }, + "arr-union": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/arr-union/-/arr-union-3.1.0.tgz", + "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=", + "dev": true + }, + "array-find": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/array-find/-/array-find-1.0.0.tgz", + "integrity": "sha1-bI4obRHtdoMn+OYuzuhzU8o+eLg=", + "dev": true + }, + "array-includes": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.3.tgz", + "integrity": "sha512-gcem1KlBU7c9rB+Rq8/3PPKsK2kjqeEBa3bD5kkQo4nYlOHQCJqIJFqBXDEfwaRuYTT4E+FxA9xez7Gf/e3Q7A==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3", + "es-abstract": "^1.18.0-next.2", + "get-intrinsic": "^1.1.1", + "is-string": "^1.0.5" + } + }, + "array-iterate": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/array-iterate/-/array-iterate-1.1.4.tgz", + "integrity": "sha512-sNRaPGh9nnmdC8Zf+pT3UqP8rnWj5Hf9wiFGsX3wUQ2yVSIhO2ShFwCoceIPpB41QF6i2OEmrHmCo36xronCVA==", + "dev": true + }, + "array-union": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", + "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", + "dev": true + }, + "array-uniq": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", + "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=", + "dev": true + }, + "array-unique": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", + "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=", + "dev": true + }, + "array.prototype.flat": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.2.4.tgz", + "integrity": "sha512-4470Xi3GAPAjZqFcljX2xzckv1qeKPizoNkiS0+O4IoPR2ZNpcjE0pkhdihlDouK+x6QOast26B4Q/O9DJnwSg==", + "dev": true, + "requires": { + "call-bind": "^1.0.0", + "define-properties": "^1.1.3", + "es-abstract": "^1.18.0-next.1" + } + }, + "arrify": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-2.0.1.tgz", + "integrity": "sha512-3duEwti880xqi4eAMN8AyR4a0ByT90zoYdLlevfrvU43vb0YZwZVfxOgxWrLXXXpyugL0hNZc9G6BiB5B3nUug==", + "dev": true + }, + "assign-symbols": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assign-symbols/-/assign-symbols-1.0.0.tgz", + "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=", + "dev": true + }, + "astral-regex": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/astral-regex/-/astral-regex-2.0.0.tgz", + "integrity": "sha512-Z7tMw1ytTXt5jqMcOP+OQteU1VuNK9Y02uuJtKQ1Sv69jXQKKg5cibLwGJow8yzZP+eAc18EmLGPal0bp36rvQ==", + "dev": true + }, + "at-least-node": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz", + "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==", + "dev": true + }, + "atob": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.2.tgz", + "integrity": "sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg==", + "dev": true + }, + "available-typed-arrays": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.4.tgz", + "integrity": "sha512-SA5mXJWrId1TaQjfxUYghbqQ/hYioKmLJvPJyDuYRtXXenFNMjj4hSSt1Cf1xsuXSXrtxrVC5Ot4eU6cOtBDdA==", + "dev": true + }, + "bail": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/bail/-/bail-1.0.5.tgz", + "integrity": "sha512-xFbRxM1tahm08yHBP16MMjVUAvDaBMD38zsM9EMAUN61omwLmKlOpB/Zku5QkjZ8TZ4vn53pj+t518cH0S03RQ==", + "dev": true + }, + "balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "base": { + "version": "0.11.2", + "resolved": "https://registry.npmjs.org/base/-/base-0.11.2.tgz", + "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", + "dev": true, + "requires": { + "cache-base": "^1.0.1", + "class-utils": "^0.3.5", + "component-emitter": "^1.2.1", + "define-property": "^1.0.0", + "isobject": "^3.0.1", + "mixin-deep": "^1.2.0", + "pascalcase": "^0.1.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, + "binary-extensions": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz", + "integrity": "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==", + "dev": true + }, + "boxen": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/boxen/-/boxen-5.0.1.tgz", + "integrity": "sha512-49VBlw+PrWEF51aCmy7QIteYPIFZxSpvqBdP/2itCPPlJ49kj9zg/XPRFrdkne2W+CfwXUls8exMvu1RysZpKA==", + "dev": true, + "requires": { + "ansi-align": "^3.0.0", + "camelcase": "^6.2.0", + "chalk": "^4.1.0", + "cli-boxes": "^2.2.1", + "string-width": "^4.2.0", + "type-fest": "^0.20.2", + "widest-line": "^3.1.0", + "wrap-ansi": "^7.0.0" + }, + "dependencies": { + "camelcase": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.2.0.tgz", + "integrity": "sha512-c7wVvbw3f37nuobQNtgsgG9POC9qMbNuMQmTCqZv23b6MIz0fcYpBiOlv9gEN/hdLdnZTDQhg6e9Dq5M1vKvfg==", + "dev": true + }, + "chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + } + } + }, + "brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "braces": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", + "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", + "dev": true, + "requires": { + "fill-range": "^7.0.1" + } + }, + "browserslist": { + "version": "4.16.8", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.8.tgz", + "integrity": "sha512-sc2m9ohR/49sWEbPj14ZSSZqp+kbi16aLao42Hmn3Z8FpjuMaq2xCA2l4zl9ITfyzvnvyE0hcg62YkIGKxgaNQ==", + "dev": true, + "requires": { + "caniuse-lite": "^1.0.30001251", + "colorette": "^1.3.0", + "electron-to-chromium": "^1.3.811", + "escalade": "^3.1.1", + "node-releases": "^1.1.75" + } + }, + "buf-compare": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/buf-compare/-/buf-compare-1.0.1.tgz", + "integrity": "sha1-/vKNqLgROgoNtEMLC2Rntpcws0o=", + "dev": true + }, + "buffer-from": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", + "dev": true + }, + "c8": { + "version": "7.8.0", + "resolved": "https://registry.npmjs.org/c8/-/c8-7.8.0.tgz", + "integrity": "sha512-x2Bx+IIEd608B1LmjiNQ/kizRPkCWo5XzuV57J9afPjAHSnYXALwbCSOkQ7cSaNXBNblfqcvdycj+klmL+j6yA==", + "dev": true, + "requires": { + "@bcoe/v8-coverage": "^0.2.3", + "@istanbuljs/schema": "^0.1.2", + "find-up": "^5.0.0", + "foreground-child": "^2.0.0", + "istanbul-lib-coverage": "^3.0.0", + "istanbul-lib-report": "^3.0.0", + "istanbul-reports": "^3.0.2", + "rimraf": "^3.0.0", + "test-exclude": "^6.0.0", + "v8-to-istanbul": "^8.0.0", + "yargs": "^16.2.0", + "yargs-parser": "^20.2.7" + } + }, + "cache-base": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", + "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", + "dev": true, + "requires": { + "collection-visit": "^1.0.0", + "component-emitter": "^1.2.1", + "get-value": "^2.0.6", + "has-value": "^1.0.0", + "isobject": "^3.0.1", + "set-value": "^2.0.0", + "to-object-path": "^0.3.0", + "union-value": "^1.0.0", + "unset-value": "^1.0.0" + } + }, + "cacheable-request": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-6.1.0.tgz", + "integrity": "sha512-Oj3cAGPCqOZX7Rz64Uny2GYAZNliQSqfbePrgAQ1wKAihYmCUnraBtJtKcGR4xz7wF+LoJC+ssFZvv5BgF9Igg==", + "dev": true, + "requires": { + "clone-response": "^1.0.2", + "get-stream": "^5.1.0", + "http-cache-semantics": "^4.0.0", + "keyv": "^3.0.0", + "lowercase-keys": "^2.0.0", + "normalize-url": "^4.1.0", + "responselike": "^1.0.2" + }, + "dependencies": { + "get-stream": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-5.2.0.tgz", + "integrity": "sha512-nBF+F1rAZVCu/p7rjzgA+Yb4lfYXrpl7a6VmJrU8wF9I1CKvP/QwPNZHnOlwbTkY6dvtFIzFMSyQXbLoTQPRpA==", + "dev": true, + "requires": { + "pump": "^3.0.0" + } + }, + "lowercase-keys": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-2.0.0.tgz", + "integrity": "sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==", + "dev": true + } + } + }, + "call-bind": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", + "integrity": "sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==", + "dev": true, + "requires": { + "function-bind": "^1.1.1", + "get-intrinsic": "^1.0.2" + } + }, + "call-me-maybe": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/call-me-maybe/-/call-me-maybe-1.0.1.tgz", + "integrity": "sha1-JtII6onje1y95gJQoV8DHBak1ms=", + "dev": true + }, + "callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "dev": true + }, + "camelcase": { + "version": "5.3.1", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", + "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==", + "dev": true + }, + "camelcase-keys": { + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/camelcase-keys/-/camelcase-keys-6.2.2.tgz", + "integrity": "sha512-YrwaA0vEKazPBkn0ipTiMpSajYDSe+KjQfrjhcBMxJt/znbvlHd8Pw/Vamaz5EB4Wfhs3SUR3Z9mwRu/P3s3Yg==", + "dev": true, + "requires": { + "camelcase": "^5.3.1", + "map-obj": "^4.0.0", + "quick-lru": "^4.0.1" + } + }, + "caniuse-lite": { + "version": "1.0.30001251", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001251.tgz", + "integrity": "sha512-HOe1r+9VkU4TFmnU70z+r7OLmtR+/chB1rdcJUeQlAinjEeb0cKL20tlAtOagNZhbrtLnCvV19B4FmF1rgzl6A==", + "dev": true + }, + "ccount": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/ccount/-/ccount-1.1.0.tgz", + "integrity": "sha512-vlNK021QdI7PNeiUh/lKkC/mNHHfV0m/Ad5JoI0TYtlBnJAslM/JIkm/tGC88bkLIwO6OQ5uV6ztS6kVAtCDlg==", + "dev": true + }, + "chalk": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-3.0.0.tgz", + "integrity": "sha512-4D3B6Wf41KOYRFdszmDqMCGq5VV/uMAB273JILmO+3jAlh8X4qDtdtgCR3fxtbLEMzSx22QdhnDcJvu2u1fVwg==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + }, + "character-entities": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-1.2.4.tgz", + "integrity": "sha512-iBMyeEHxfVnIakwOuDXpVkc54HijNgCyQB2w0VfGQThle6NXn50zU6V/u+LDhxHcDUPojn6Kpga3PTAD8W1bQw==", + "dev": true + }, + "character-entities-legacy": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-1.1.4.tgz", + "integrity": "sha512-3Xnr+7ZFS1uxeiUDvV02wQ+QDbc55o97tIV5zHScSPJpcLm/r0DFPcoY3tYRp+VZukxuMeKgXYmsXQHO05zQeA==", + "dev": true + }, + "character-reference-invalid": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-1.1.4.tgz", + "integrity": "sha512-mKKUkUbhPpQlCOfIuZkvSEgktjPFIsZKRRbC6KWVEMvlzblj3i3asQv5ODsrwt0N3pHAEvjP8KTQPHkp0+6jOg==", + "dev": true + }, + "chokidar": { + "version": "3.5.2", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.2.tgz", + "integrity": "sha512-ekGhOnNVPgT77r4K/U3GDhu+FQ2S8TnK/s2KbIGXi0SZWuwkZ2QNyfWdZW+TVfn84DpEP7rLeCt2UI6bJ8GwbQ==", + "dev": true, + "requires": { + "anymatch": "~3.1.2", + "braces": "~3.0.2", + "fsevents": "~2.3.2", + "glob-parent": "~5.1.2", + "is-binary-path": "~2.1.0", + "is-glob": "~4.0.1", + "normalize-path": "~3.0.0", + "readdirp": "~3.6.0" + } + }, + "ci-info": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", + "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==", + "dev": true + }, + "class-utils": { + "version": "0.3.6", + "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz", + "integrity": "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==", + "dev": true, + "requires": { + "arr-union": "^3.1.0", + "define-property": "^0.2.5", + "isobject": "^3.0.0", + "static-extend": "^0.1.1" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + } + } + }, + "clean-regexp": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/clean-regexp/-/clean-regexp-1.0.0.tgz", + "integrity": "sha1-jffHquUf02h06PjQW5GAvBGj/tc=", + "dev": true, + "requires": { + "escape-string-regexp": "^1.0.5" + } + }, + "cli-boxes": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-2.2.1.tgz", + "integrity": "sha512-y4coMcylgSCdVinjiDBuR8PCC2bLjyGTwEmPb9NHR/QaNU6EUOXcTY/s6VjGMD6ENSEaeQYHCY0GNGS5jfMwPw==", + "dev": true + }, + "cliui": { + "version": "7.0.4", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-7.0.4.tgz", + "integrity": "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==", + "dev": true, + "requires": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.0", + "wrap-ansi": "^7.0.0" + } + }, + "clone-response": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", + "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", + "dev": true, + "requires": { + "mimic-response": "^1.0.0" + } + }, + "co": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/co/-/co-3.1.0.tgz", + "integrity": "sha1-TqVOpaCJOBUxheFSEMaNkJK8G3g=", + "dev": true + }, + "collapse-white-space": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/collapse-white-space/-/collapse-white-space-1.0.6.tgz", + "integrity": "sha512-jEovNnrhMuqyCcjfEJA56v0Xq8SkIoPKDyaHahwo3POf4qcSXqMYuwNcOTzp74vTsR9Tn08z4MxWqAhcekogkQ==", + "dev": true + }, + "collection-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz", + "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", + "dev": true, + "requires": { + "map-visit": "^1.0.0", + "object-visit": "^1.0.0" + } + }, + "color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "requires": { + "color-name": "~1.1.4" + } + }, + "color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, + "colorette": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/colorette/-/colorette-1.3.0.tgz", + "integrity": "sha512-ecORCqbSFP7Wm8Y6lyqMJjexBQqXSF7SSeaTyGGphogUjBlFP9m9o08wy86HL2uB7fMTxtOUzLMk7ogKcxMg1w==", + "dev": true + }, + "commondir": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", + "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=", + "dev": true + }, + "component-emitter": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.3.0.tgz", + "integrity": "sha512-Rd3se6QB+sO1TwqZjscQrurpEPIfO0/yYnSin6Q/rD3mOutHvUrCAhJub3r90uNb+SESBuE0QYoB90YdfatsRg==", + "dev": true + }, + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", + "dev": true + }, + "concat-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-2.0.0.tgz", + "integrity": "sha512-MWufYdFw53ccGjCA+Ol7XJYpAlW6/prSMzuPOTRnJGcGzuhLn4Scrz7qf6o8bROZ514ltazcIFJZevcfbo0x7A==", + "dev": true, + "requires": { + "buffer-from": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.0.2", + "typedarray": "^0.0.6" + } + }, + "configstore": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-5.0.1.tgz", + "integrity": "sha512-aMKprgk5YhBNyH25hj8wGt2+D52Sw1DRRIzqBwLp2Ya9mFmY8KPvvtvmna8SxVR9JMZ4kzMD68N22vlaRpkeFA==", + "dev": true, + "requires": { + "dot-prop": "^5.2.0", + "graceful-fs": "^4.1.2", + "make-dir": "^3.0.0", + "unique-string": "^2.0.0", + "write-file-atomic": "^3.0.0", + "xdg-basedir": "^4.0.0" + } + }, + "confusing-browser-globals": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/confusing-browser-globals/-/confusing-browser-globals-1.0.10.tgz", + "integrity": "sha512-gNld/3lySHwuhaVluJUKLePYirM3QNCKzVxqAdhJII9/WXKVX5PURzMVJspS1jTslSqjeuG4KMVTSouit5YPHA==", + "dev": true + }, + "convert-source-map": { + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.8.0.tgz", + "integrity": "sha512-+OQdjP49zViI/6i7nIJpA8rAl4sV/JdPfU9nZs3VqOwGIgizICvuN2ru6fMd+4llL0tar18UYJXfZ/TWtmhUjA==", + "dev": true, + "requires": { + "safe-buffer": "~5.1.1" + } + }, + "copy-descriptor": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", + "integrity": "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=", + "dev": true + }, + "core-assert": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/core-assert/-/core-assert-0.2.1.tgz", + "integrity": "sha1-+F4s+b/tKPdzzIs/pcW2m9wC/j8=", + "dev": true, + "requires": { + "buf-compare": "^1.0.0", + "is-error": "^2.2.0" + } + }, + "cosmiconfig": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.0.0.tgz", + "integrity": "sha512-pondGvTuVYDk++upghXJabWzL6Kxu6f26ljFw64Swq9v6sQPUL3EUlVDV56diOjpCayKihL6hVe8exIACU4XcA==", + "dev": true, + "requires": { + "@types/parse-json": "^4.0.0", + "import-fresh": "^3.2.1", + "parse-json": "^5.0.0", + "path-type": "^4.0.0", + "yaml": "^1.10.0" + } + }, + "cross-spawn": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", + "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", + "dev": true, + "requires": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + } + }, + "crypto-random-string": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-2.0.0.tgz", + "integrity": "sha512-v1plID3y9r/lPhviJ1wrXpLeyUIGAZ2SHNYTEapm7/8A9nLPoyvVp3RK/EPFqn5kEznyWgYZNsRtYYIWbuG8KA==", + "dev": true + }, + "debug": { + "version": "4.3.2", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.2.tgz", + "integrity": "sha512-mOp8wKcvj7XxC78zLgw/ZA+6TSgkoE2C/ienthhRD298T7UNwAg9diBpLRxC0mOezLl4B0xV7M0cCO6P/O0Xhw==", + "dev": true, + "requires": { + "ms": "2.1.2" + } + }, + "decamelize": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=", + "dev": true + }, + "decamelize-keys": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.0.tgz", + "integrity": "sha1-0XGoeTMlKAfrPLYdwcFEXQeN8tk=", + "dev": true, + "requires": { + "decamelize": "^1.1.0", + "map-obj": "^1.0.0" + }, + "dependencies": { + "map-obj": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-1.0.1.tgz", + "integrity": "sha1-2TPOuSBdgr3PSIb2dCvcK03qFG0=", + "dev": true + } + } + }, + "decode-uri-component": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", + "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=", + "dev": true + }, + "decompress-response": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", + "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", + "dev": true, + "requires": { + "mimic-response": "^1.0.0" + } + }, + "deep-equal": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/deep-equal/-/deep-equal-2.0.5.tgz", + "integrity": "sha512-nPiRgmbAtm1a3JsnLCf6/SLfXcjyN5v8L1TXzdCmHrXJ4hx+gW/w1YCcn7z8gJtSiDArZCgYtbao3QqLm/N1Sw==", + "dev": true, + "requires": { + "call-bind": "^1.0.0", + "es-get-iterator": "^1.1.1", + "get-intrinsic": "^1.0.1", + "is-arguments": "^1.0.4", + "is-date-object": "^1.0.2", + "is-regex": "^1.1.1", + "isarray": "^2.0.5", + "object-is": "^1.1.4", + "object-keys": "^1.1.1", + "object.assign": "^4.1.2", + "regexp.prototype.flags": "^1.3.0", + "side-channel": "^1.0.3", + "which-boxed-primitive": "^1.0.1", + "which-collection": "^1.0.1", + "which-typed-array": "^1.1.2" + } + }, + "deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true + }, + "deep-is": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", + "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", + "dev": true + }, + "deep-strict-equal": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/deep-strict-equal/-/deep-strict-equal-0.2.0.tgz", + "integrity": "sha1-SgeBR6irV/ag1PVUckPNIvROtOQ=", + "dev": true, + "requires": { + "core-assert": "^0.2.0" + } + }, + "defer-to-connect": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-1.1.3.tgz", + "integrity": "sha512-0ISdNousHvZT2EiFlZeZAHBUvSxmKswVCEf8hW7KWgG4a8MVEu/3Vb6uWYozkjylyCxe0JBIiRB1jV45S70WVQ==", + "dev": true + }, + "define-properties": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.3.tgz", + "integrity": "sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ==", + "dev": true, + "requires": { + "object-keys": "^1.0.12" + } + }, + "define-property": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", + "integrity": "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==", + "dev": true, + "requires": { + "is-descriptor": "^1.0.2", + "isobject": "^3.0.1" + }, + "dependencies": { + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, + "defined": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/defined/-/defined-1.0.0.tgz", + "integrity": "sha1-yY2bzvdWdBiOEQlpFRGZ45sfppM=", + "dev": true + }, + "dir-glob": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", + "integrity": "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==", + "dev": true, + "requires": { + "path-type": "^4.0.0" + } + }, + "doctrine": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", + "dev": true, + "requires": { + "esutils": "^2.0.2" + } + }, + "dot-prop": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.3.0.tgz", + "integrity": "sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==", + "dev": true, + "requires": { + "is-obj": "^2.0.0" + } + }, + "dotignore": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/dotignore/-/dotignore-0.1.2.tgz", + "integrity": "sha512-UGGGWfSauusaVJC+8fgV+NVvBXkCTmVv7sk6nojDZZvuOUNGUy0Zk4UpHQD6EDjS0jpBwcACvH4eofvyzBcRDw==", + "dev": true, + "requires": { + "minimatch": "^3.0.4" + } + }, + "duplexer3": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", + "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=", + "dev": true + }, + "electron-to-chromium": { + "version": "1.3.813", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.813.tgz", + "integrity": "sha512-YcSRImHt6JZZ2sSuQ4Bzajtk98igQ0iKkksqlzZLzbh4p0OIyJRSvUbsgqfcR8txdfsoYCc4ym306t4p2kP/aw==", + "dev": true + }, + "emoji-regex": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", + "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", + "dev": true + }, + "end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "dev": true, + "requires": { + "once": "^1.4.0" + } + }, + "enhance-visitors": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/enhance-visitors/-/enhance-visitors-1.0.0.tgz", + "integrity": "sha1-qpRdBdpGVnKh69OP7i7T2oUY6Vo=", + "dev": true, + "requires": { + "lodash": "^4.13.1" + } + }, + "enhanced-resolve": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-0.9.1.tgz", + "integrity": "sha1-TW5omzcl+GCQknzMhs2fFjW4ni4=", + "dev": true, + "requires": { + "graceful-fs": "^4.1.2", + "memory-fs": "^0.2.0", + "tapable": "^0.1.8" + } + }, + "enquirer": { + "version": "2.3.6", + "resolved": "https://registry.npmjs.org/enquirer/-/enquirer-2.3.6.tgz", + "integrity": "sha512-yjNnPr315/FjS4zIsUxYguYUPP2e1NK4d7E7ZOLiyYCcbFBiTMyID+2wvm2w6+pZ/odMA7cRkjhsPbltwBOrLg==", + "dev": true, + "requires": { + "ansi-colors": "^4.1.1" + } + }, + "env-editor": { + "version": "0.4.2", + "resolved": "https://registry.npmjs.org/env-editor/-/env-editor-0.4.2.tgz", + "integrity": "sha512-ObFo8v4rQJAE59M69QzwloxPZtd33TpYEIjtKD1rrFDcM1Gd7IkDxEBU+HriziN6HSHQnBJi8Dmy+JWkav5HKA==", + "dev": true + }, + "error-ex": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", + "dev": true, + "requires": { + "is-arrayish": "^0.2.1" + } + }, + "es-abstract": { + "version": "1.18.5", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.18.5.tgz", + "integrity": "sha512-DDggyJLoS91CkJjgauM5c0yZMjiD1uK3KcaCeAmffGwZ+ODWzOkPN4QwRbsK5DOFf06fywmyLci3ZD8jLGhVYA==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "es-to-primitive": "^1.2.1", + "function-bind": "^1.1.1", + "get-intrinsic": "^1.1.1", + "has": "^1.0.3", + "has-symbols": "^1.0.2", + "internal-slot": "^1.0.3", + "is-callable": "^1.2.3", + "is-negative-zero": "^2.0.1", + "is-regex": "^1.1.3", + "is-string": "^1.0.6", + "object-inspect": "^1.11.0", + "object-keys": "^1.1.1", + "object.assign": "^4.1.2", + "string.prototype.trimend": "^1.0.4", + "string.prototype.trimstart": "^1.0.4", + "unbox-primitive": "^1.0.1" + } + }, + "es-get-iterator": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/es-get-iterator/-/es-get-iterator-1.1.2.tgz", + "integrity": "sha512-+DTO8GYwbMCwbywjimwZMHp8AuYXOS2JZFWoi2AlPOS3ebnII9w/NLpNZtA7A0YLaVDw+O7KFCeoIV7OPvM7hQ==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.0", + "has-symbols": "^1.0.1", + "is-arguments": "^1.1.0", + "is-map": "^2.0.2", + "is-set": "^2.0.2", + "is-string": "^1.0.5", + "isarray": "^2.0.5" + } + }, + "es-to-primitive": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.1.tgz", + "integrity": "sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA==", + "dev": true, + "requires": { + "is-callable": "^1.1.4", + "is-date-object": "^1.0.1", + "is-symbol": "^1.0.2" + } + }, + "escalade": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", + "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "dev": true + }, + "escape-goat": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-2.1.1.tgz", + "integrity": "sha512-8/uIhbG12Csjy2JEW7D9pHbreaVaS/OpN3ycnyvElTdwM5n6GY6W6e2IPemfvGZeUMqZ9A/3GqIZMgKnBhAw/Q==", + "dev": true + }, + "escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", + "dev": true + }, + "eslint": { + "version": "7.32.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-7.32.0.tgz", + "integrity": "sha512-VHZ8gX+EDfz+97jGcgyGCyRia/dPOd6Xh9yPv8Bl1+SoaIwD+a/vlrOmGRUyOYu7MwUhc7CxqeaDZU13S4+EpA==", + "dev": true, + "requires": { + "@babel/code-frame": "7.12.11", + "@eslint/eslintrc": "^0.4.3", + "@humanwhocodes/config-array": "^0.5.0", + "ajv": "^6.10.0", + "chalk": "^4.0.0", + "cross-spawn": "^7.0.2", + "debug": "^4.0.1", + "doctrine": "^3.0.0", + "enquirer": "^2.3.5", + "escape-string-regexp": "^4.0.0", + "eslint-scope": "^5.1.1", + "eslint-utils": "^2.1.0", + "eslint-visitor-keys": "^2.0.0", + "espree": "^7.3.1", + "esquery": "^1.4.0", + "esutils": "^2.0.2", + "fast-deep-equal": "^3.1.3", + "file-entry-cache": "^6.0.1", + "functional-red-black-tree": "^1.0.1", + "glob-parent": "^5.1.2", + "globals": "^13.6.0", + "ignore": "^4.0.6", + "import-fresh": "^3.0.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "js-yaml": "^3.13.1", + "json-stable-stringify-without-jsonify": "^1.0.1", + "levn": "^0.4.1", + "lodash.merge": "^4.6.2", + "minimatch": "^3.0.4", + "natural-compare": "^1.4.0", + "optionator": "^0.9.1", + "progress": "^2.0.0", + "regexpp": "^3.1.0", + "semver": "^7.2.1", + "strip-ansi": "^6.0.0", + "strip-json-comments": "^3.1.0", + "table": "^6.0.9", + "text-table": "^0.2.0", + "v8-compile-cache": "^2.0.3" + }, + "dependencies": { + "@babel/code-frame": { + "version": "7.12.11", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.12.11.tgz", + "integrity": "sha512-Zt1yodBx1UcyiePMSkWnU4hPqhwq7hGi2nFL1LeA3EUl+q2LQx16MISgJ0+z7dnmgvP9QtIleuETGOiOH1RcIw==", + "dev": true, + "requires": { + "@babel/highlight": "^7.10.4" + } + }, + "chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + }, + "escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "dev": true + }, + "eslint-utils": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-2.1.0.tgz", + "integrity": "sha512-w94dQYoauyvlDc43XnGB8lU3Zt713vNChgt4EWwhXAP2XkBvndfxF0AgIqKOOasjPIPzj9JqgwkwbCYD0/V3Zg==", + "dev": true, + "requires": { + "eslint-visitor-keys": "^1.1.0" + }, + "dependencies": { + "eslint-visitor-keys": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", + "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==", + "dev": true + } + } + }, + "ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", + "dev": true + }, + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + } + } + }, + "eslint-config-prettier": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-7.2.0.tgz", + "integrity": "sha512-rV4Qu0C3nfJKPOAhFujFxB7RMP+URFyQqqOZW9DMRD7ZDTFyjaIlETU3xzHELt++4ugC0+Jm084HQYkkJe+Ivg==", + "dev": true + }, + "eslint-config-xo": { + "version": "0.35.0", + "resolved": "https://registry.npmjs.org/eslint-config-xo/-/eslint-config-xo-0.35.0.tgz", + "integrity": "sha512-+WyZTLWUJlvExFrBU/Ldw8AB/S0d3x+26JQdBWbcqig2ZaWh0zinYcHok+ET4IoPaEcRRf3FE9kjItNVjBwnAg==", + "dev": true, + "requires": { + "confusing-browser-globals": "1.0.10" + } + }, + "eslint-config-xo-typescript": { + "version": "0.38.0", + "resolved": "https://registry.npmjs.org/eslint-config-xo-typescript/-/eslint-config-xo-typescript-0.38.0.tgz", + "integrity": "sha512-f5z0gN1r9X84PK1qav6T6YT1zW6KcAqtsMPtmqoKBLt4ACRr6tbAddtFwqkluAEH9JvHjWxuB8vu4KJFcjuzdQ==", + "dev": true + }, + "eslint-formatter-pretty": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/eslint-formatter-pretty/-/eslint-formatter-pretty-4.1.0.tgz", + "integrity": "sha512-IsUTtGxF1hrH6lMWiSl1WbGaiP01eT6kzywdY1U+zLc0MP+nwEnUiS9UI8IaOTUhTeQJLlCEWIbXINBH4YJbBQ==", + "dev": true, + "requires": { + "@types/eslint": "^7.2.13", + "ansi-escapes": "^4.2.1", + "chalk": "^4.1.0", + "eslint-rule-docs": "^1.1.5", + "log-symbols": "^4.0.0", + "plur": "^4.0.0", + "string-width": "^4.2.0", + "supports-hyperlinks": "^2.0.0" + }, + "dependencies": { + "chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + } + } + }, + "eslint-import-resolver-node": { + "version": "0.3.6", + "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.6.tgz", + "integrity": "sha512-0En0w03NRVMn9Uiyn8YRPDKvWjxCWkslUEhGNTdGx15RvPJYQ+lbOlqrlNI2vEAs4pDYK4f/HN2TbDmk5TP0iw==", + "dev": true, + "requires": { + "debug": "^3.2.7", + "resolve": "^1.20.0" + }, + "dependencies": { + "debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "requires": { + "ms": "^2.1.1" + } + }, + "resolve": { + "version": "1.20.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.20.0.tgz", + "integrity": "sha512-wENBPt4ySzg4ybFQW2TT1zMQucPK95HSh/nq2CFTZVOGut2+pQvSsgtda4d26YrYcr067wjbmzOG8byDPBX63A==", + "dev": true, + "requires": { + "is-core-module": "^2.2.0", + "path-parse": "^1.0.6" + } + } + } + }, + "eslint-import-resolver-webpack": { + "version": "0.13.1", + "resolved": "https://registry.npmjs.org/eslint-import-resolver-webpack/-/eslint-import-resolver-webpack-0.13.1.tgz", + "integrity": "sha512-O/8mG6AHmaKYSMb4lWxiXPpaARxOJ4rMQEHJ8vTgjS1MXooJA3KPgBPPAdOPoV17v5ML5120qod5FBLM+DtgEw==", + "dev": true, + "requires": { + "array-find": "^1.0.0", + "debug": "^3.2.7", + "enhanced-resolve": "^0.9.1", + "find-root": "^1.1.0", + "has": "^1.0.3", + "interpret": "^1.4.0", + "is-core-module": "^2.4.0", + "is-regex": "^1.1.3", + "lodash": "^4.17.21", + "resolve": "^1.20.0", + "semver": "^5.7.1" + }, + "dependencies": { + "debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "requires": { + "ms": "^2.1.1" + } + }, + "resolve": { + "version": "1.20.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.20.0.tgz", + "integrity": "sha512-wENBPt4ySzg4ybFQW2TT1zMQucPK95HSh/nq2CFTZVOGut2+pQvSsgtda4d26YrYcr067wjbmzOG8byDPBX63A==", + "dev": true, + "requires": { + "is-core-module": "^2.2.0", + "path-parse": "^1.0.6" + } + }, + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true + } + } + }, + "eslint-module-utils": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.6.2.tgz", + "integrity": "sha512-QG8pcgThYOuqxupd06oYTZoNOGaUdTY1PqK+oS6ElF6vs4pBdk/aYxFVQQXzcrAqp9m7cl7lb2ubazX+g16k2Q==", + "dev": true, + "requires": { + "debug": "^3.2.7", + "pkg-dir": "^2.0.0" + }, + "dependencies": { + "debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "requires": { + "ms": "^2.1.1" + } + }, + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "locate-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", + "dev": true, + "requires": { + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + } + }, + "p-limit": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, + "requires": { + "p-try": "^1.0.0" + } + }, + "p-locate": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "dev": true, + "requires": { + "p-limit": "^1.1.0" + } + }, + "p-try": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", + "dev": true + }, + "path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true + }, + "pkg-dir": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-2.0.0.tgz", + "integrity": "sha1-9tXREJ4Z1j7fQo4L1X4Sd3YVM0s=", + "dev": true, + "requires": { + "find-up": "^2.1.0" + } + } + } + }, + "eslint-plugin-ava": { + "version": "11.0.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-ava/-/eslint-plugin-ava-11.0.0.tgz", + "integrity": "sha512-UMGedfl/gIKx1tzjGtAsTSJgowyAEZU2VWmpoWXYcuuV4B2H4Cu90yuMgMPEVt1mQlIZ21L7YM2CSpHUFJo/LQ==", + "dev": true, + "requires": { + "deep-strict-equal": "^0.2.0", + "enhance-visitors": "^1.0.0", + "eslint-utils": "^2.1.0", + "espree": "^7.2.0", + "espurify": "^2.0.1", + "import-modules": "^2.0.0", + "micro-spelling-correcter": "^1.1.1", + "pkg-dir": "^4.2.0", + "resolve-from": "^5.0.0" + }, + "dependencies": { + "eslint-utils": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-2.1.0.tgz", + "integrity": "sha512-w94dQYoauyvlDc43XnGB8lU3Zt713vNChgt4EWwhXAP2XkBvndfxF0AgIqKOOasjPIPzj9JqgwkwbCYD0/V3Zg==", + "dev": true, + "requires": { + "eslint-visitor-keys": "^1.1.0" + } + }, + "eslint-visitor-keys": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", + "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==", + "dev": true + } + } + }, + "eslint-plugin-es": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-es/-/eslint-plugin-es-3.0.1.tgz", + "integrity": "sha512-GUmAsJaN4Fc7Gbtl8uOBlayo2DqhwWvEzykMHSCZHU3XdJ+NSzzZcVhXh3VxX5icqQ+oQdIEawXX8xkR3mIFmQ==", + "dev": true, + "requires": { + "eslint-utils": "^2.0.0", + "regexpp": "^3.0.0" + }, + "dependencies": { + "eslint-utils": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-2.1.0.tgz", + "integrity": "sha512-w94dQYoauyvlDc43XnGB8lU3Zt713vNChgt4EWwhXAP2XkBvndfxF0AgIqKOOasjPIPzj9JqgwkwbCYD0/V3Zg==", + "dev": true, + "requires": { + "eslint-visitor-keys": "^1.1.0" + } + }, + "eslint-visitor-keys": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", + "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==", + "dev": true + } + } + }, + "eslint-plugin-eslint-comments": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-eslint-comments/-/eslint-plugin-eslint-comments-3.2.0.tgz", + "integrity": "sha512-0jkOl0hfojIHHmEHgmNdqv4fmh7300NdpA9FFpF7zaoLvB/QeXOGNLIo86oAveJFrfB1p05kC8hpEMHM8DwWVQ==", + "dev": true, + "requires": { + "escape-string-regexp": "^1.0.5", + "ignore": "^5.0.5" + } + }, + "eslint-plugin-import": { + "version": "2.24.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.24.1.tgz", + "integrity": "sha512-KSFWhNxPH8OGJwpRJJs+Z7I0a13E2iFQZJIvSnCu6KUs4qmgAm3xN9GYBCSoiGWmwA7gERZPXqYQjcoCROnYhQ==", + "dev": true, + "requires": { + "array-includes": "^3.1.3", + "array.prototype.flat": "^1.2.4", + "debug": "^2.6.9", + "doctrine": "^2.1.0", + "eslint-import-resolver-node": "^0.3.6", + "eslint-module-utils": "^2.6.2", + "find-up": "^2.0.0", + "has": "^1.0.3", + "is-core-module": "^2.6.0", + "minimatch": "^3.0.4", + "object.values": "^1.1.4", + "pkg-up": "^2.0.0", + "read-pkg-up": "^3.0.0", + "resolve": "^1.20.0", + "tsconfig-paths": "^3.10.1" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, + "doctrine": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", + "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", + "dev": true, + "requires": { + "esutils": "^2.0.2" + } + }, + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "locate-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", + "dev": true, + "requires": { + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", + "dev": true + }, + "p-limit": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, + "requires": { + "p-try": "^1.0.0" + } + }, + "p-locate": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "dev": true, + "requires": { + "p-limit": "^1.1.0" + } + }, + "p-try": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", + "dev": true + }, + "path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true + }, + "resolve": { + "version": "1.20.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.20.0.tgz", + "integrity": "sha512-wENBPt4ySzg4ybFQW2TT1zMQucPK95HSh/nq2CFTZVOGut2+pQvSsgtda4d26YrYcr067wjbmzOG8byDPBX63A==", + "dev": true, + "requires": { + "is-core-module": "^2.2.0", + "path-parse": "^1.0.6" + } + } + } + }, + "eslint-plugin-no-use-extend-native": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-no-use-extend-native/-/eslint-plugin-no-use-extend-native-0.5.0.tgz", + "integrity": "sha512-dBNjs8hor8rJgeXLH4HTut5eD3RGWf9JUsadIfuL7UosVQ/dnvOKwxEcRrXrFxrMZ8llUVWT+hOimxJABsAUzQ==", + "dev": true, + "requires": { + "is-get-set-prop": "^1.0.0", + "is-js-type": "^2.0.0", + "is-obj-prop": "^1.0.0", + "is-proto-prop": "^2.0.0" + } + }, + "eslint-plugin-node": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-node/-/eslint-plugin-node-11.1.0.tgz", + "integrity": "sha512-oUwtPJ1W0SKD0Tr+wqu92c5xuCeQqB3hSCHasn/ZgjFdA9iDGNkNf2Zi9ztY7X+hNuMib23LNGRm6+uN+KLE3g==", + "dev": true, + "requires": { + "eslint-plugin-es": "^3.0.0", + "eslint-utils": "^2.0.0", + "ignore": "^5.1.1", + "minimatch": "^3.0.4", + "resolve": "^1.10.1", + "semver": "^6.1.0" + }, + "dependencies": { + "eslint-utils": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-2.1.0.tgz", + "integrity": "sha512-w94dQYoauyvlDc43XnGB8lU3Zt713vNChgt4EWwhXAP2XkBvndfxF0AgIqKOOasjPIPzj9JqgwkwbCYD0/V3Zg==", + "dev": true, + "requires": { + "eslint-visitor-keys": "^1.1.0" + } + }, + "eslint-visitor-keys": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", + "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==", + "dev": true + }, + "resolve": { + "version": "1.20.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.20.0.tgz", + "integrity": "sha512-wENBPt4ySzg4ybFQW2TT1zMQucPK95HSh/nq2CFTZVOGut2+pQvSsgtda4d26YrYcr067wjbmzOG8byDPBX63A==", + "dev": true, + "requires": { + "is-core-module": "^2.2.0", + "path-parse": "^1.0.6" + } + } + } + }, + "eslint-plugin-prettier": { + "version": "3.4.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-3.4.0.tgz", + "integrity": "sha512-UDK6rJT6INSfcOo545jiaOwB701uAIt2/dR7WnFQoGCVl1/EMqdANBmwUaqqQ45aXprsTGzSa39LI1PyuRBxxw==", + "dev": true, + "requires": { + "prettier-linter-helpers": "^1.0.0" + } + }, + "eslint-plugin-promise": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-promise/-/eslint-plugin-promise-4.3.1.tgz", + "integrity": "sha512-bY2sGqyptzFBDLh/GMbAxfdJC+b0f23ME63FOE4+Jao0oZ3E1LEwFtWJX/1pGMJLiTtrSSern2CRM/g+dfc0eQ==", + "dev": true + }, + "eslint-plugin-unicorn": { + "version": "28.0.2", + "resolved": "https://registry.npmjs.org/eslint-plugin-unicorn/-/eslint-plugin-unicorn-28.0.2.tgz", + "integrity": "sha512-k4AoFP7n8/oq6lBXkdc9Flid6vw2B8j7aXFCxgzJCyKvmaKrCUFb1TFPhG9eSJQFZowqmymMPRtl8oo9NKLUbw==", + "dev": true, + "requires": { + "ci-info": "^2.0.0", + "clean-regexp": "^1.0.0", + "eslint-template-visitor": "^2.2.2", + "eslint-utils": "^2.1.0", + "eslint-visitor-keys": "^2.0.0", + "import-modules": "^2.1.0", + "lodash": "^4.17.20", + "pluralize": "^8.0.0", + "read-pkg-up": "^7.0.1", + "regexp-tree": "^0.1.22", + "reserved-words": "^0.1.2", + "safe-regex": "^2.1.1", + "semver": "^7.3.4" + }, + "dependencies": { + "eslint-utils": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-2.1.0.tgz", + "integrity": "sha512-w94dQYoauyvlDc43XnGB8lU3Zt713vNChgt4EWwhXAP2XkBvndfxF0AgIqKOOasjPIPzj9JqgwkwbCYD0/V3Zg==", + "dev": true, + "requires": { + "eslint-visitor-keys": "^1.1.0" + }, + "dependencies": { + "eslint-visitor-keys": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", + "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==", + "dev": true + } + } + }, + "find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "dev": true, + "requires": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + } + }, + "locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "dev": true, + "requires": { + "p-locate": "^4.1.0" + } + }, + "p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "dev": true, + "requires": { + "p-try": "^2.0.0" + } + }, + "p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "dev": true, + "requires": { + "p-limit": "^2.2.0" + } + }, + "read-pkg": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-5.2.0.tgz", + "integrity": "sha512-Ug69mNOpfvKDAc2Q8DRpMjjzdtrnv9HcSMX+4VsZxD1aZ6ZzrIE7rlzXBtWTyhULSMKg076AW6WR5iZpD0JiOg==", + "dev": true, + "requires": { + "@types/normalize-package-data": "^2.4.0", + "normalize-package-data": "^2.5.0", + "parse-json": "^5.0.0", + "type-fest": "^0.6.0" + }, + "dependencies": { + "type-fest": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.6.0.tgz", + "integrity": "sha512-q+MB8nYR1KDLrgr4G5yemftpMC7/QLqVndBmEEdqzmNj5dcFOO4Oo8qlwZE3ULT3+Zim1F8Kq4cBnikNhlCMlg==", + "dev": true + } + } + }, + "read-pkg-up": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-7.0.1.tgz", + "integrity": "sha512-zK0TB7Xd6JpCLmlLmufqykGE+/TlOePD6qKClNW7hHDKFh/J7/7gCWGR7joEQEW1bKq3a3yUZSObOoWLFQ4ohg==", + "dev": true, + "requires": { + "find-up": "^4.1.0", + "read-pkg": "^5.2.0", + "type-fest": "^0.8.1" + } + }, + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + }, + "type-fest": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.8.1.tgz", + "integrity": "sha512-4dbzIzqvjtgiM5rw1k5rEHtBANKmdudhGyBEajN01fEyhaAIhsoKNy6y7+IN93IfpFtwY9iqi7kD+xwKhQsNJA==", + "dev": true + } + } + }, + "eslint-rule-docs": { + "version": "1.1.231", + "resolved": "https://registry.npmjs.org/eslint-rule-docs/-/eslint-rule-docs-1.1.231.tgz", + "integrity": "sha512-egHz9A1WG7b8CS0x1P6P/Rj5FqZOjray/VjpJa14tMZalfRKvpE2ONJ3plCM7+PcinmU4tcmbPLv0VtwzSdLVA==", + "dev": true + }, + "eslint-scope": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", + "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", + "dev": true, + "requires": { + "esrecurse": "^4.3.0", + "estraverse": "^4.1.1" + } + }, + "eslint-template-visitor": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/eslint-template-visitor/-/eslint-template-visitor-2.3.2.tgz", + "integrity": "sha512-3ydhqFpuV7x1M9EK52BPNj6V0Kwu0KKkcIAfpUhwHbR8ocRln/oUHgfxQupY8O1h4Qv/POHDumb/BwwNfxbtnA==", + "dev": true, + "requires": { + "@babel/core": "^7.12.16", + "@babel/eslint-parser": "^7.12.16", + "eslint-visitor-keys": "^2.0.0", + "esquery": "^1.3.1", + "multimap": "^1.1.0" + } + }, + "eslint-utils": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-3.0.0.tgz", + "integrity": "sha512-uuQC43IGctw68pJA1RgbQS8/NP7rch6Cwd4j3ZBtgo4/8Flj4eGE7ZYSZRN3iq5pVUv6GPdW5Z1RFleo84uLDA==", + "dev": true, + "requires": { + "eslint-visitor-keys": "^2.0.0" + } + }, + "eslint-visitor-keys": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-2.1.0.tgz", + "integrity": "sha512-0rSmRBzXgDzIsD6mGdJgevzgezI534Cer5L/vyMX0kHzT/jiB43jRhd9YUlMGYLQy2zprNmoT8qasCGtY+QaKw==", + "dev": true + }, + "espree": { + "version": "7.3.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-7.3.1.tgz", + "integrity": "sha512-v3JCNCE64umkFpmkFGqzVKsOT0tN1Zr+ueqLZfpV1Ob8e+CEgPWa+OxCoGH3tnhimMKIaBm4m/vaRpJ/krRz2g==", + "dev": true, + "requires": { + "acorn": "^7.4.0", + "acorn-jsx": "^5.3.1", + "eslint-visitor-keys": "^1.3.0" + }, + "dependencies": { + "eslint-visitor-keys": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", + "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==", + "dev": true + } + } + }, + "esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", + "dev": true + }, + "espurify": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/espurify/-/espurify-2.1.1.tgz", + "integrity": "sha512-zttWvnkhcDyGOhSH4vO2qCBILpdCMv/MX8lp4cqgRkQoDRGK2oZxi2GfWhlP2dIXmk7BaKeOTuzbHhyC68o8XQ==", + "dev": true + }, + "esquery": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.4.0.tgz", + "integrity": "sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w==", + "dev": true, + "requires": { + "estraverse": "^5.1.0" + }, + "dependencies": { + "estraverse": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.2.0.tgz", + "integrity": "sha512-BxbNGGNm0RyRYvUdHpIwv9IWzeM9XClbOxwoATuFdOE7ZE6wHL+HQ5T8hoPM+zHvmKzzsEqhgy0GrQ5X13afiQ==", + "dev": true + } + } + }, + "esrecurse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", + "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, + "requires": { + "estraverse": "^5.2.0" + }, + "dependencies": { + "estraverse": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.2.0.tgz", + "integrity": "sha512-BxbNGGNm0RyRYvUdHpIwv9IWzeM9XClbOxwoATuFdOE7ZE6wHL+HQ5T8hoPM+zHvmKzzsEqhgy0GrQ5X13afiQ==", + "dev": true + } + } + }, + "estraverse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", + "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", + "dev": true + }, + "esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "dev": true + }, + "execa": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", + "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", + "dev": true, + "requires": { + "cross-spawn": "^7.0.3", + "get-stream": "^6.0.0", + "human-signals": "^2.1.0", + "is-stream": "^2.0.0", + "merge-stream": "^2.0.0", + "npm-run-path": "^4.0.1", + "onetime": "^5.1.2", + "signal-exit": "^3.0.3", + "strip-final-newline": "^2.0.0" + } + }, + "expand-brackets": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", + "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", + "dev": true, + "requires": { + "debug": "^2.3.3", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "posix-character-classes": "^0.1.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", + "dev": true + } + } + }, + "extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "dev": true + }, + "extend-shallow": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz", + "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", + "dev": true, + "requires": { + "assign-symbols": "^1.0.0", + "is-extendable": "^1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "dev": true, + "requires": { + "is-plain-object": "^2.0.4" + } + } + } + }, + "extglob": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz", + "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==", + "dev": true, + "requires": { + "array-unique": "^0.3.2", + "define-property": "^1.0.0", + "expand-brackets": "^2.1.4", + "extend-shallow": "^2.0.1", + "fragment-cache": "^0.2.1", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, + "fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "dev": true + }, + "fast-diff": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.2.0.tgz", + "integrity": "sha512-xJuoT5+L99XlZ8twedaRf6Ax2TgQVxvgZOYoPKqZufmJib0tL2tegPBOZb1pVNgIhlqDlA0eO0c3wBvQcmzx4w==", + "dev": true + }, + "fast-glob": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.7.tgz", + "integrity": "sha512-rYGMRwip6lUMvYD3BTScMwT1HtAs2d71SMv66Vrxs0IekGZEjhM0pcMfjQPnknBt2zeCwQMEupiN02ZP4DiT1Q==", + "dev": true, + "requires": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.4" + } + }, + "fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "dev": true + }, + "fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", + "dev": true + }, + "fastq": { + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.12.0.tgz", + "integrity": "sha512-VNX0QkHK3RsXVKr9KrlUv/FoTa0NdbYoHHl7uXHv2rzyHSlxjdNAKug2twd9luJxpcyNeAgf5iPPMutJO67Dfg==", + "dev": true, + "requires": { + "reusify": "^1.0.4" + } + }, + "fault": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/fault/-/fault-1.0.4.tgz", + "integrity": "sha512-CJ0HCB5tL5fYTEA7ToAq5+kTwd++Borf1/bifxd9iT70QcXr4MRrO3Llf8Ifs70q+SJcGHFtnIE/Nw6giCtECA==", + "dev": true, + "requires": { + "format": "^0.2.0" + } + }, + "figgy-pudding": { + "version": "3.5.2", + "resolved": "https://registry.npmjs.org/figgy-pudding/-/figgy-pudding-3.5.2.tgz", + "integrity": "sha512-0btnI/H8f2pavGMN8w40mlSKOfTK2SVJmBfBeVIj3kNw0swwgzyRq0d5TJVOwodFmtvpPeWPN/MCcfuWF0Ezbw==", + "dev": true + }, + "figures": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", + "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", + "dev": true, + "requires": { + "escape-string-regexp": "^1.0.5" + } + }, + "file-entry-cache": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-6.0.1.tgz", + "integrity": "sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==", + "dev": true, + "requires": { + "flat-cache": "^3.0.4" + } + }, + "fill-range": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", + "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", + "dev": true, + "requires": { + "to-regex-range": "^5.0.1" + } + }, + "find-cache-dir": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/find-cache-dir/-/find-cache-dir-3.3.1.tgz", + "integrity": "sha512-t2GDMt3oGC/v+BMwzmllWDuJF/xcDtE5j/fCGbqDD7OLuJkj0cfh1YSA5VKPvwMeLFLNDBkwOKZ2X85jGLVftQ==", + "dev": true, + "requires": { + "commondir": "^1.0.1", + "make-dir": "^3.0.2", + "pkg-dir": "^4.1.0" + } + }, + "find-root": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/find-root/-/find-root-1.1.0.tgz", + "integrity": "sha512-NKfW6bec6GfKc0SGx1e07QZY9PE99u0Bft/0rzSD5k3sO/vwkVUpDUKVm5Gpp5Ue3YfShPFTX2070tDs5kB9Ng==", + "dev": true + }, + "find-up": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", + "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", + "dev": true, + "requires": { + "locate-path": "^6.0.0", + "path-exists": "^4.0.0" + } + }, + "flat-cache": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.0.4.tgz", + "integrity": "sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==", + "dev": true, + "requires": { + "flatted": "^3.1.0", + "rimraf": "^3.0.2" + } + }, + "flatted": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.2.2.tgz", + "integrity": "sha512-JaTY/wtrcSyvXJl4IMFHPKyFur1sE9AUqc0QnhOaJ0CxHtAoIV8pYDzeEfAaNEtGkOfq4gr3LBFmdXW5mOQFnA==", + "dev": true + }, + "for-each": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", + "dev": true, + "requires": { + "is-callable": "^1.1.3" + } + }, + "for-in": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", + "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=", + "dev": true + }, + "foreach": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/foreach/-/foreach-2.0.5.tgz", + "integrity": "sha1-C+4AUBiusmDQo6865ljdATbsG5k=", + "dev": true + }, + "foreground-child": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-2.0.0.tgz", + "integrity": "sha512-dCIq9FpEcyQyXKCkyzmlPTFNgrCzPudOe+mhvJU5zAtlBnGVy2yKxtfsxK2tQBThwq225jcvBjpw1Gr40uzZCA==", + "dev": true, + "requires": { + "cross-spawn": "^7.0.0", + "signal-exit": "^3.0.2" + } + }, + "format": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/format/-/format-0.2.2.tgz", + "integrity": "sha1-1hcBB+nv3E7TDJ3DkBbflCtctYs=", + "dev": true + }, + "fragment-cache": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", + "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", + "dev": true, + "requires": { + "map-cache": "^0.2.2" + } + }, + "fs-extra": { + "version": "9.1.0", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz", + "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==", + "dev": true, + "requires": { + "at-least-node": "^1.0.0", + "graceful-fs": "^4.2.0", + "jsonfile": "^6.0.1", + "universalify": "^2.0.0" + } + }, + "fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", + "dev": true + }, + "fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "dev": true, + "optional": true + }, + "function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "functional-red-black-tree": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz", + "integrity": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", + "dev": true + }, + "gensync": { + "version": "1.0.0-beta.2", + "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", + "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", + "dev": true + }, + "get-caller-file": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", + "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==", + "dev": true + }, + "get-intrinsic": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.1.tgz", + "integrity": "sha512-kWZrnVM42QCiEA2Ig1bG8zjoIMOgxWwYCEeNdwY6Tv/cOSeGpcoX4pXHfKUxNKVoArnrEr2e9srnAxxGIraS9Q==", + "dev": true, + "requires": { + "function-bind": "^1.1.1", + "has": "^1.0.3", + "has-symbols": "^1.0.1" + } + }, + "get-package-type": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/get-package-type/-/get-package-type-0.1.0.tgz", + "integrity": "sha512-pjzuKtY64GYfWizNAJ0fr9VqttZkNiK2iS430LtIHzjBEr6bX8Am2zm4sW4Ro5wjWW5cAlRL1qAMTcXbjNAO2Q==", + "dev": true + }, + "get-set-props": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/get-set-props/-/get-set-props-0.1.0.tgz", + "integrity": "sha1-mYR1wXhEVobQsyJG2l3428++jqM=", + "dev": true + }, + "get-stdin": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-8.0.0.tgz", + "integrity": "sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg==", + "dev": true + }, + "get-stream": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-6.0.1.tgz", + "integrity": "sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==", + "dev": true + }, + "get-value": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", + "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=", + "dev": true + }, + "github-slugger": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/github-slugger/-/github-slugger-1.3.0.tgz", + "integrity": "sha512-gwJScWVNhFYSRDvURk/8yhcFBee6aFjye2a7Lhb2bUyRulpIoek9p0I9Kt7PT67d/nUlZbFu8L9RLiA0woQN8Q==", + "dev": true, + "requires": { + "emoji-regex": ">=6.0.0 <=6.1.1" + }, + "dependencies": { + "emoji-regex": { + "version": "6.1.1", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-6.1.1.tgz", + "integrity": "sha1-xs0OwbBkLio8Z6ETfvxeeW2k+I4=", + "dev": true + } + } + }, + "glob": { + "version": "7.1.7", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.7.tgz", + "integrity": "sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ==", + "dev": true, + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "requires": { + "is-glob": "^4.0.1" + } + }, + "glob-to-regexp": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.3.0.tgz", + "integrity": "sha1-jFoUlNIGbFcMw7/kSWF1rMTVAqs=", + "dev": true + }, + "global-dirs": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-3.0.0.tgz", + "integrity": "sha512-v8ho2DS5RiCjftj1nD9NmnfaOzTdud7RRnVd9kFNOjqZbISlx5DQ+OrTkywgd0dIt7oFCvKetZSHoHcP3sDdiA==", + "dev": true, + "requires": { + "ini": "2.0.0" + }, + "dependencies": { + "ini": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ini/-/ini-2.0.0.tgz", + "integrity": "sha512-7PnF4oN3CvZF23ADhA5wRaYEQpJ8qygSkbtTXWBeXWXmEVRXK+1ITciHWwHhsjv1TmW0MgacIv6hEi5pX5NQdA==", + "dev": true + } + } + }, + "globals": { + "version": "13.11.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.11.0.tgz", + "integrity": "sha512-08/xrJ7wQjK9kkkRoI3OFUBbLx4f+6x3SGwcPvQ0QH6goFDrOU2oyAWrmh3dJezu65buo+HBMzAMQy6rovVC3g==", + "dev": true, + "requires": { + "type-fest": "^0.20.2" + } + }, + "globby": { + "version": "9.2.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-9.2.0.tgz", + "integrity": "sha512-ollPHROa5mcxDEkwg6bPt3QbEf4pDQSNtd6JPL1YvOvAo/7/0VAm9TccUeoTmarjPw4pfUthSCqcyfNB1I3ZSg==", + "dev": true, + "requires": { + "@types/glob": "^7.1.1", + "array-union": "^1.0.2", + "dir-glob": "^2.2.2", + "fast-glob": "^2.2.6", + "glob": "^7.1.3", + "ignore": "^4.0.3", + "pify": "^4.0.1", + "slash": "^2.0.0" + }, + "dependencies": { + "@nodelib/fs.stat": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-1.1.3.tgz", + "integrity": "sha512-shAmDyaQC4H92APFoIaVDHCx5bStIocgvbwQyxPRrbUY20V1EYTbSDchWbuwlMG3V17cprZhA6+78JfB+3DTPw==", + "dev": true + }, + "array-union": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", + "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", + "dev": true, + "requires": { + "array-uniq": "^1.0.1" + } + }, + "braces": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz", + "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", + "dev": true, + "requires": { + "arr-flatten": "^1.1.0", + "array-unique": "^0.3.2", + "extend-shallow": "^2.0.1", + "fill-range": "^4.0.0", + "isobject": "^3.0.1", + "repeat-element": "^1.1.2", + "snapdragon": "^0.8.1", + "snapdragon-node": "^2.0.1", + "split-string": "^3.0.2", + "to-regex": "^3.0.1" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, + "dir-glob": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-2.2.2.tgz", + "integrity": "sha512-f9LBi5QWzIW3I6e//uxZoLBlUt9kcp66qo0sSCxL6YZKc75R1c4MFCoe/LaZiBGmgujvQdxc5Bn3QhfyvK5Hsw==", + "dev": true, + "requires": { + "path-type": "^3.0.0" + } + }, + "fast-glob": { + "version": "2.2.7", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-2.2.7.tgz", + "integrity": "sha512-g1KuQwHOZAmOZMuBtHdxDtju+T2RT8jgCC9aANsbpdiDDTSnjgfuVsIBNKbUeJI3oKMRExcfNDtJl4OhbffMsw==", + "dev": true, + "requires": { + "@mrmlnc/readdir-enhanced": "^2.2.1", + "@nodelib/fs.stat": "^1.1.2", + "glob-parent": "^3.1.0", + "is-glob": "^4.0.0", + "merge2": "^1.2.3", + "micromatch": "^3.1.10" + } + }, + "fill-range": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", + "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", + "dev": true, + "requires": { + "extend-shallow": "^2.0.1", + "is-number": "^3.0.0", + "repeat-string": "^1.6.1", + "to-regex-range": "^2.1.0" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, + "glob-parent": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", + "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", + "dev": true, + "requires": { + "is-glob": "^3.1.0", + "path-dirname": "^1.0.0" + }, + "dependencies": { + "is-glob": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", + "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", + "dev": true, + "requires": { + "is-extglob": "^2.1.0" + } + } + } + }, + "ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", + "dev": true + }, + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true + }, + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "micromatch": { + "version": "3.1.10", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", + "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==", + "dev": true, + "requires": { + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "braces": "^2.3.1", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "extglob": "^2.0.4", + "fragment-cache": "^0.2.1", + "kind-of": "^6.0.2", + "nanomatch": "^1.2.9", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.2" + } + }, + "path-type": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", + "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", + "dev": true, + "requires": { + "pify": "^3.0.0" + }, + "dependencies": { + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true + } + } + }, + "pify": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz", + "integrity": "sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==", + "dev": true + }, + "slash": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-2.0.0.tgz", + "integrity": "sha512-ZYKh3Wh2z1PpEXWr0MpSBZ0V6mZHAQfYevttO11c51CaWjGTaadiKZ+wVt1PbMlDV5qhMFslpZCemhwOK7C89A==", + "dev": true + }, + "to-regex-range": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz", + "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", + "dev": true, + "requires": { + "is-number": "^3.0.0", + "repeat-string": "^1.6.1" + } + } + } + }, + "got": { + "version": "9.6.0", + "resolved": "https://registry.npmjs.org/got/-/got-9.6.0.tgz", + "integrity": "sha512-R7eWptXuGYxwijs0eV+v3o6+XH1IqVK8dJOEecQfTmkncw9AV4dcw/Dhxi8MdlqPthxxpZyizMzyg8RTmEsG+Q==", + "dev": true, + "requires": { + "@sindresorhus/is": "^0.14.0", + "@szmarczak/http-timer": "^1.1.2", + "cacheable-request": "^6.0.0", + "decompress-response": "^3.3.0", + "duplexer3": "^0.1.4", + "get-stream": "^4.1.0", + "lowercase-keys": "^1.0.1", + "mimic-response": "^1.0.1", + "p-cancelable": "^1.0.0", + "to-readable-stream": "^1.0.0", + "url-parse-lax": "^3.0.0" + }, + "dependencies": { + "get-stream": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz", + "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==", + "dev": true, + "requires": { + "pump": "^3.0.0" + } + } + } + }, + "graceful-fs": { + "version": "4.2.8", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.8.tgz", + "integrity": "sha512-qkIilPUYcNhJpd33n0GBXTB1MMPp14TxEsEs0pTrsSVucApsYzW5V+Q8Qxhik6KU3evy+qkAAowTByymK0avdg==", + "dev": true + }, + "hard-rejection": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/hard-rejection/-/hard-rejection-2.1.0.tgz", + "integrity": "sha512-VIZB+ibDhx7ObhAe7OVtoEbuP4h/MuOTHJ+J8h/eBXotJYl0fBgR72xDFCKgIh22OJZIOVNxBMWuhAr10r8HdA==", + "dev": true + }, + "has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "requires": { + "function-bind": "^1.1.1" + } + }, + "has-bigints": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.1.tgz", + "integrity": "sha512-LSBS2LjbNBTf6287JEbEzvJgftkF5qFkmCo9hDRpAzKhUOlJ+hx8dd4USs00SgsUNwc4617J9ki5YtEClM2ffA==", + "dev": true + }, + "has-dynamic-import": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/has-dynamic-import/-/has-dynamic-import-2.0.0.tgz", + "integrity": "sha512-GYPi/aZmACJVrVfEhP1rNUFmtCuK+SQ96mn8Bs7mXiGZRAJiI4VjaMmjj4uuvW8qaF085uWJvyJk9UNYUIYn0A==", + "dev": true, + "requires": { + "call-bind": "^1.0.2" + } + }, + "has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true + }, + "has-symbols": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.2.tgz", + "integrity": "sha512-chXa79rL/UC2KlX17jo3vRGz0azaWEx5tGqZg5pO3NUyEJVB17dMruQlzCCOfUvElghKcm5194+BCRvi2Rv/Gw==", + "dev": true + }, + "has-tostringtag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.0.tgz", + "integrity": "sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==", + "dev": true, + "requires": { + "has-symbols": "^1.0.2" + } + }, + "has-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", + "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", + "dev": true, + "requires": { + "get-value": "^2.0.6", + "has-values": "^1.0.0", + "isobject": "^3.0.0" + } + }, + "has-values": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz", + "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", + "dev": true, + "requires": { + "is-number": "^3.0.0", + "kind-of": "^4.0.0" + }, + "dependencies": { + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true + }, + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "kind-of": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", + "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "has-yarn": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/has-yarn/-/has-yarn-2.1.0.tgz", + "integrity": "sha512-UqBRqi4ju7T+TqGNdqAO0PaSVGsDGJUBQvk9eUWNGRY1CFGDzYhLWoM7JQEemnlvVcv/YEmc2wNW8BC24EnUsw==", + "dev": true + }, + "hosted-git-info": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-3.0.8.tgz", + "integrity": "sha512-aXpmwoOhRBrw6X3j0h5RloK4x1OzsxMPyxqIHyNfSe2pypkVTZFpEiRoSipPEPlMrh0HW/XsjkJ5WgnCirpNUw==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + }, + "html-escaper": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/html-escaper/-/html-escaper-2.0.2.tgz", + "integrity": "sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==", + "dev": true + }, + "http-cache-semantics": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.0.tgz", + "integrity": "sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==", + "dev": true + }, + "human-signals": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-2.1.0.tgz", + "integrity": "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==", + "dev": true + }, + "ignore": { + "version": "5.1.8", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.1.8.tgz", + "integrity": "sha512-BMpfD7PpiETpBl/A6S498BaIJ6Y/ABT93ETbby2fP00v4EbvPBXWEoaR1UBPKs3iR53pJY7EtZk5KACI57i1Uw==", + "dev": true + }, + "import-fresh": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", + "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==", + "dev": true, + "requires": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + }, + "dependencies": { + "resolve-from": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", + "dev": true + } + } + }, + "import-lazy": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", + "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", + "dev": true + }, + "import-modules": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/import-modules/-/import-modules-2.1.0.tgz", + "integrity": "sha512-8HEWcnkbGpovH9yInoisxaSoIg9Brbul+Ju3Kqe2UsYDUBJD/iQjSgEj0zPcTDPKfPp2fs5xlv1i+JSye/m1/A==", + "dev": true + }, + "imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", + "dev": true + }, + "indent-string": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-4.0.0.tgz", + "integrity": "sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==", + "dev": true + }, + "inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", + "dev": true, + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "ini": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", + "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", + "dev": true + }, + "internal-slot": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.3.tgz", + "integrity": "sha512-O0DB1JC/sPyZl7cIo78n5dR7eUSwwpYPiXRhTzNxZVAMUuB8vlnRFyLxdrVToks6XPLVnFfbzaVd5WLjhgg+vA==", + "dev": true, + "requires": { + "get-intrinsic": "^1.1.0", + "has": "^1.0.3", + "side-channel": "^1.0.4" + } + }, + "interpret": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.4.0.tgz", + "integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==", + "dev": true + }, + "irregular-plurals": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/irregular-plurals/-/irregular-plurals-3.3.0.tgz", + "integrity": "sha512-MVBLKUTangM3EfRPFROhmWQQKRDsrgI83J8GS3jXy+OwYqiR2/aoWndYQ5416jLE3uaGgLH7ncme3X9y09gZ3g==", + "dev": true + }, + "is-absolute": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-absolute/-/is-absolute-1.0.0.tgz", + "integrity": "sha512-dOWoqflvcydARa360Gvv18DZ/gRuHKi2NU/wU5X1ZFzdYfH29nkiNZsF3mp4OJ3H4yo9Mx8A/uAGNzpzPN3yBA==", + "dev": true, + "requires": { + "is-relative": "^1.0.0", + "is-windows": "^1.0.1" + } + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true + }, + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "is-alphabetical": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-1.0.4.tgz", + "integrity": "sha512-DwzsA04LQ10FHTZuL0/grVDk4rFoVH1pjAToYwBrHSxcrBIGQuXrQMtD5U1b0U2XVgKZCTLLP8u2Qxqhy3l2Vg==", + "dev": true + }, + "is-alphanumerical": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-1.0.4.tgz", + "integrity": "sha512-UzoZUr+XfVz3t3v4KyGEniVL9BDRoQtY7tOyrRybkVNjDFWyo1yhXNGrrBTQxp3ib9BLAWs7k2YKBQsFRkZG9A==", + "dev": true, + "requires": { + "is-alphabetical": "^1.0.0", + "is-decimal": "^1.0.0" + } + }, + "is-arguments": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/is-arguments/-/is-arguments-1.1.1.tgz", + "integrity": "sha512-8Q7EARjzEnKpt/PCD7e1cgUS0a6X8u5tdSiMqXhojOdoV9TsMsiO+9VLC5vAmO8N7/GmXn7yjR8qnA6bVAEzfA==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + } + }, + "is-arrayish": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", + "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=", + "dev": true + }, + "is-bigint": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.0.4.tgz", + "integrity": "sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==", + "dev": true, + "requires": { + "has-bigints": "^1.0.1" + } + }, + "is-binary-path": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", + "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", + "dev": true, + "requires": { + "binary-extensions": "^2.0.0" + } + }, + "is-boolean-object": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.1.2.tgz", + "integrity": "sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + } + }, + "is-buffer": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.5.tgz", + "integrity": "sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ==", + "dev": true + }, + "is-callable": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.4.tgz", + "integrity": "sha512-nsuwtxZfMX67Oryl9LCQ+upnC0Z0BgpwntpS89m1H/TLF0zNfzfLMV/9Wa/6MZsj0acpEjAO0KF1xT6ZdLl95w==", + "dev": true + }, + "is-ci": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-2.0.0.tgz", + "integrity": "sha512-YfJT7rkpQB0updsdHLGWrvhBJfcfzNNawYDNIyQXJz0IViGf75O8EBPKSdvw2rF+LGCsX4FZ8tcr3b19LcZq4w==", + "dev": true, + "requires": { + "ci-info": "^2.0.0" + } + }, + "is-core-module": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.6.0.tgz", + "integrity": "sha512-wShG8vs60jKfPWpF2KZRaAtvt3a20OAn7+IJ6hLPECpSABLcKtFKTTI4ZtH5QcBruBHlq+WsdHWyz0BCZW7svQ==", + "dev": true, + "requires": { + "has": "^1.0.3" + } + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true + }, + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "is-date-object": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.5.tgz", + "integrity": "sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==", + "dev": true, + "requires": { + "has-tostringtag": "^1.0.0" + } + }, + "is-decimal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-1.0.4.tgz", + "integrity": "sha512-RGdriMmQQvZ2aqaQq3awNA6dCGtKpiDFcOzrTWrDAT2MiWrKQVPmxLGHl7Y2nNu6led0kEyoX0enY0qXYsv9zw==", + "dev": true + }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^0.1.6", + "is-data-descriptor": "^0.1.4", + "kind-of": "^5.0.0" + }, + "dependencies": { + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } + } + }, + "is-docker": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-2.2.1.tgz", + "integrity": "sha512-F+i2BKsFrH66iaUFc0woD8sLy8getkwTwtOBjvs56Cx4CgJDeKQeqfz8wAYiSb8JOprWhHH5p77PbmYCvvUuXQ==", + "dev": true + }, + "is-empty": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/is-empty/-/is-empty-1.2.0.tgz", + "integrity": "sha1-3pu1snhzigWgsJpX4ftNSjQan2s=", + "dev": true + }, + "is-error": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/is-error/-/is-error-2.2.2.tgz", + "integrity": "sha512-IOQqts/aHWbiisY5DuPJQ0gcbvaLFCa7fBa9xoLfxBZvQ+ZI/Zh9xoI7Gk+G64N0FdK4AbibytHht2tWgpJWLg==", + "dev": true + }, + "is-extendable": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", + "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=", + "dev": true + }, + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", + "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", + "dev": true + }, + "is-get-set-prop": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-get-set-prop/-/is-get-set-prop-1.0.0.tgz", + "integrity": "sha1-JzGHfk14pqae3M5rudaLB3nnYxI=", + "dev": true, + "requires": { + "get-set-props": "^0.1.0", + "lowercase-keys": "^1.0.0" + } + }, + "is-glob": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz", + "integrity": "sha512-5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg==", + "dev": true, + "requires": { + "is-extglob": "^2.1.1" + } + }, + "is-hexadecimal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-1.0.4.tgz", + "integrity": "sha512-gyPJuv83bHMpocVYoqof5VDiZveEoGoFL8m3BXNb2VW8Xs+rz9kqO8LOQ5DH6EsuvilT1ApazU0pyl+ytbPtlw==", + "dev": true + }, + "is-installed-globally": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.4.0.tgz", + "integrity": "sha512-iwGqO3J21aaSkC7jWnHP/difazwS7SFeIqxv6wEtLU8Y5KlzFTjyqcSIT0d8s4+dDhKytsk9PJZ2BkS5eZwQRQ==", + "dev": true, + "requires": { + "global-dirs": "^3.0.0", + "is-path-inside": "^3.0.2" + } + }, + "is-js-type": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-js-type/-/is-js-type-2.0.0.tgz", + "integrity": "sha1-c2FwBtZZtOtHKbunR9KHgt8PfiI=", + "dev": true, + "requires": { + "js-types": "^1.0.0" + } + }, + "is-map": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/is-map/-/is-map-2.0.2.tgz", + "integrity": "sha512-cOZFQQozTha1f4MxLFzlgKYPTyj26picdZTx82hbc/Xf4K/tZOOXSCkMvU4pKioRXGDLJRn0GM7Upe7kR721yg==", + "dev": true + }, + "is-negated-glob": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-negated-glob/-/is-negated-glob-1.0.0.tgz", + "integrity": "sha1-aRC8pdqMleeEtXUbl2z1oQ/uNtI=", + "dev": true + }, + "is-negative-zero": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.1.tgz", + "integrity": "sha512-2z6JzQvZRa9A2Y7xC6dQQm4FSTSTNWjKIYYTt4246eMTJmIo0Q+ZyOsU66X8lxK1AbB92dFeglPLrhwpeRKO6w==", + "dev": true + }, + "is-npm": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-5.0.0.tgz", + "integrity": "sha512-WW/rQLOazUq+ST/bCAVBp/2oMERWLsR7OrKyt052dNDk4DHcDE0/7QSXITlmi+VBcV13DfIbysG3tZJm5RfdBA==", + "dev": true + }, + "is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", + "dev": true + }, + "is-number-object": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.6.tgz", + "integrity": "sha512-bEVOqiRcvo3zO1+G2lVMy+gkkEm9Yh7cDMRusKKu5ZJKPUYSJwICTKZrNKHA2EbSP0Tu0+6B/emsYNHZyn6K8g==", + "dev": true, + "requires": { + "has-tostringtag": "^1.0.0" + } + }, + "is-obj": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz", + "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==", + "dev": true + }, + "is-obj-prop": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-obj-prop/-/is-obj-prop-1.0.0.tgz", + "integrity": "sha1-s03nnEULjXxzqyzfZ9yHWtuF+A4=", + "dev": true, + "requires": { + "lowercase-keys": "^1.0.0", + "obj-props": "^1.0.0" + } + }, + "is-path-inside": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-3.0.3.tgz", + "integrity": "sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==", + "dev": true + }, + "is-plain-obj": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", + "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", + "dev": true + }, + "is-plain-object": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", + "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", + "dev": true, + "requires": { + "isobject": "^3.0.1" + } + }, + "is-proto-prop": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-proto-prop/-/is-proto-prop-2.0.0.tgz", + "integrity": "sha512-jl3NbQ/fGLv5Jhan4uX+Ge9ohnemqyblWVVCpAvtTQzNFvV2xhJq+esnkIbYQ9F1nITXoLfDDQLp7LBw/zzncg==", + "dev": true, + "requires": { + "lowercase-keys": "^1.0.0", + "proto-props": "^2.0.0" + } + }, + "is-regex": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.1.4.tgz", + "integrity": "sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + } + }, + "is-relative": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-relative/-/is-relative-1.0.0.tgz", + "integrity": "sha512-Kw/ReK0iqwKeu0MITLFuj0jbPAmEiOsIwyIXvvbfa6QfmN9pkD1M+8pdk7Rl/dTKbH34/XBFMbgD4iMJhLQbGA==", + "dev": true, + "requires": { + "is-unc-path": "^1.0.0" + } + }, + "is-set": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/is-set/-/is-set-2.0.2.tgz", + "integrity": "sha512-+2cnTEZeY5z/iXGbLhPrOAaK/Mau5k5eXq9j14CpRTftq0pAJu2MwVRSZhyZWBzx3o6X795Lz6Bpb6R0GKf37g==", + "dev": true + }, + "is-stream": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", + "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", + "dev": true + }, + "is-string": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.0.7.tgz", + "integrity": "sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==", + "dev": true, + "requires": { + "has-tostringtag": "^1.0.0" + } + }, + "is-symbol": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.4.tgz", + "integrity": "sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg==", + "dev": true, + "requires": { + "has-symbols": "^1.0.2" + } + }, + "is-typed-array": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.7.tgz", + "integrity": "sha512-VxlpTBGknhQ3o7YiVjIhdLU6+oD8dPz/79vvvH4F+S/c8608UCVa9fgDpa1kZgFoUST2DCgacc70UszKgzKuvA==", + "dev": true, + "requires": { + "available-typed-arrays": "^1.0.4", + "call-bind": "^1.0.2", + "es-abstract": "^1.18.5", + "foreach": "^2.0.5", + "has-tostringtag": "^1.0.0" + } + }, + "is-typedarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", + "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", + "dev": true + }, + "is-unc-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-unc-path/-/is-unc-path-1.0.0.tgz", + "integrity": "sha512-mrGpVd0fs7WWLfVsStvgF6iEJnbjDFZh9/emhRDcGWTduTfNHd9CHeUwH3gYIjdbwo4On6hunkztwOaAw0yllQ==", + "dev": true, + "requires": { + "unc-path-regex": "^0.1.2" + } + }, + "is-unicode-supported": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz", + "integrity": "sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw==", + "dev": true + }, + "is-weakmap": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-weakmap/-/is-weakmap-2.0.1.tgz", + "integrity": "sha512-NSBR4kH5oVj1Uwvv970ruUkCV7O1mzgVFO4/rev2cLRda9Tm9HrL70ZPut4rOHgY0FNrUu9BCbXA2sdQ+x0chA==", + "dev": true + }, + "is-weakset": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-weakset/-/is-weakset-2.0.1.tgz", + "integrity": "sha512-pi4vhbhVHGLxohUw7PhGsueT4vRGFoXhP7+RGN0jKIv9+8PWYCQTqtADngrxOm2g46hoH0+g8uZZBzMrvVGDmw==", + "dev": true + }, + "is-windows": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", + "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==", + "dev": true + }, + "is-wsl": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-2.2.0.tgz", + "integrity": "sha512-fKzAra0rGJUUBwGBgNkHZuToZcn+TtXHpeCgmkMJMMYx1sQDYaCSyjJBSCa2nH1DGm7s3n1oBnohoVTBaN7Lww==", + "dev": true, + "requires": { + "is-docker": "^2.0.0" + } + }, + "is-yarn-global": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/is-yarn-global/-/is-yarn-global-0.3.0.tgz", + "integrity": "sha512-VjSeb/lHmkoyd8ryPVIKvOCn4D1koMqY+vqyjjUfc3xyKtP4dYOxM44sZrnqQSzSds3xyOrUTLTC9LVCVgLngw==", + "dev": true + }, + "isarray": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", + "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", + "dev": true + }, + "isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", + "dev": true + }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + }, + "istanbul-lib-coverage": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/istanbul-lib-coverage/-/istanbul-lib-coverage-3.0.0.tgz", + "integrity": "sha512-UiUIqxMgRDET6eR+o5HbfRYP1l0hqkWOs7vNxC/mggutCMUIhWMm8gAHb8tHlyfD3/l6rlgNA5cKdDzEAf6hEg==", + "dev": true + }, + "istanbul-lib-report": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/istanbul-lib-report/-/istanbul-lib-report-3.0.0.tgz", + "integrity": "sha512-wcdi+uAKzfiGT2abPpKZ0hSU1rGQjUQnLvtY5MpQ7QCTahD3VODhcu4wcfY1YtkGaDD5yuydOLINXsfbus9ROw==", + "dev": true, + "requires": { + "istanbul-lib-coverage": "^3.0.0", + "make-dir": "^3.0.0", + "supports-color": "^7.1.0" + } + }, + "istanbul-reports": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.0.2.tgz", + "integrity": "sha512-9tZvz7AiR3PEDNGiV9vIouQ/EAcqMXFmkcA1CDFTwOB98OZVDL0PH9glHotf5Ugp6GCOTypfzGWI/OqjWNCRUw==", + "dev": true, + "requires": { + "html-escaper": "^2.0.0", + "istanbul-lib-report": "^3.0.0" + } + }, + "js-tokens": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true + }, + "js-types": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/js-types/-/js-types-1.0.0.tgz", + "integrity": "sha1-0kLmSU7Vcq08koCfyL7X92h8vwM=", + "dev": true + }, + "js-yaml": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz", + "integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==", + "dev": true, + "requires": { + "argparse": "^1.0.7", + "esprima": "^4.0.0" + } + }, + "jsesc": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz", + "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==", + "dev": true + }, + "json-buffer": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", + "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=", + "dev": true + }, + "json-parse-better-errors": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz", + "integrity": "sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==", + "dev": true + }, + "json-parse-even-better-errors": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", + "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", + "dev": true + }, + "json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "json-stable-stringify-without-jsonify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", + "integrity": "sha1-nbe1lJatPzz+8wp1FC0tkwrXJlE=", + "dev": true + }, + "json5": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.0.tgz", + "integrity": "sha512-f+8cldu7X/y7RAJurMEJmdoKXGB/X550w2Nr3tTbezL6RwEE/iMcm+tZnXeoZtKuOq6ft8+CqzEkrIgx1fPoQA==", + "dev": true, + "requires": { + "minimist": "^1.2.5" + } + }, + "jsonfile": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz", + "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==", + "dev": true, + "requires": { + "graceful-fs": "^4.1.6", + "universalify": "^2.0.0" + } + }, + "keyv": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.1.0.tgz", + "integrity": "sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==", + "dev": true, + "requires": { + "json-buffer": "3.0.0" + } + }, + "kind-of": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz", + "integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==", + "dev": true + }, + "latest-version": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-5.1.0.tgz", + "integrity": "sha512-weT+r0kTkRQdCdYCNtkMwWXQTMEswKrFBkm4ckQOMVhhqhIMI1UT2hMj+1iigIhgSZm5gTmrRXBNoGUgaTY1xA==", + "dev": true, + "requires": { + "package-json": "^6.3.0" + } + }, + "levenshtein-edit-distance": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/levenshtein-edit-distance/-/levenshtein-edit-distance-1.0.0.tgz", + "integrity": "sha1-iVuvR4zOi1waDSfkXXwdl4pmHkk=", + "dev": true + }, + "levn": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", + "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", + "dev": true, + "requires": { + "prelude-ls": "^1.2.1", + "type-check": "~0.4.0" + } + }, + "libnpmconfig": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/libnpmconfig/-/libnpmconfig-1.2.1.tgz", + "integrity": "sha512-9esX8rTQAHqarx6qeZqmGQKBNZR5OIbl/Ayr0qQDy3oXja2iFVQQI81R6GZ2a02bSNZ9p3YOGX1O6HHCb1X7kA==", + "dev": true, + "requires": { + "figgy-pudding": "^3.5.1", + "find-up": "^3.0.0", + "ini": "^1.3.5" + }, + "dependencies": { + "find-up": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-3.0.0.tgz", + "integrity": "sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==", + "dev": true, + "requires": { + "locate-path": "^3.0.0" + } + }, + "locate-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-3.0.0.tgz", + "integrity": "sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==", + "dev": true, + "requires": { + "p-locate": "^3.0.0", + "path-exists": "^3.0.0" + } + }, + "p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "dev": true, + "requires": { + "p-try": "^2.0.0" + } + }, + "p-locate": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-3.0.0.tgz", + "integrity": "sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==", + "dev": true, + "requires": { + "p-limit": "^2.0.0" + } + }, + "path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true + } + } + }, + "line-column-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/line-column-path/-/line-column-path-2.0.0.tgz", + "integrity": "sha512-nz3A+vi4bElhwd62E9+Qk/f9BDYLSzD/4Hy1rir0I4GnMxSTezSymzANyph5N1PgRZ3sSbA+yR5hOuXxc71a0Q==", + "dev": true, + "requires": { + "type-fest": "^0.4.1" + }, + "dependencies": { + "type-fest": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.4.1.tgz", + "integrity": "sha512-IwzA/LSfD2vC1/YDYMv/zHP4rDF1usCwllsDpbolT3D4fUepIO7f9K70jjmUewU/LmGUKJcwcVtDCpnKk4BPMw==", + "dev": true + } + } + }, + "lines-and-columns": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.1.6.tgz", + "integrity": "sha1-HADHQ7QzzQpOgHWPe2SldEDZ/wA=", + "dev": true + }, + "load-json-file": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", + "integrity": "sha1-L19Fq5HjMhYjT9U62rZo607AmTs=", + "dev": true, + "requires": { + "graceful-fs": "^4.1.2", + "parse-json": "^4.0.0", + "pify": "^3.0.0", + "strip-bom": "^3.0.0" + }, + "dependencies": { + "parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", + "dev": true, + "requires": { + "error-ex": "^1.3.1", + "json-parse-better-errors": "^1.0.1" + } + } + } + }, + "load-plugin": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/load-plugin/-/load-plugin-3.0.0.tgz", + "integrity": "sha512-od7eKCCZ62ITvFf8nHHrIiYmgOHb4xVNDRDqxBWSaao5FZyyZVX8OmRCbwjDGPrSrgIulwPNyBsWCGnhiDC0oQ==", + "dev": true, + "requires": { + "libnpmconfig": "^1.0.0", + "resolve-from": "^5.0.0" + } + }, + "locate-path": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", + "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==", + "dev": true, + "requires": { + "p-locate": "^5.0.0" + } + }, + "lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", + "dev": true + }, + "lodash.clonedeep": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/lodash.clonedeep/-/lodash.clonedeep-4.5.0.tgz", + "integrity": "sha1-4j8/nE+Pvd6HJSnBBxhXoIblzO8=", + "dev": true + }, + "lodash.merge": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", + "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", + "dev": true + }, + "lodash.truncate": { + "version": "4.4.2", + "resolved": "https://registry.npmjs.org/lodash.truncate/-/lodash.truncate-4.4.2.tgz", + "integrity": "sha1-WjUNoLERO4N+z//VgSy+WNbq4ZM=", + "dev": true + }, + "log-symbols": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-4.1.0.tgz", + "integrity": "sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg==", + "dev": true, + "requires": { + "chalk": "^4.1.0", + "is-unicode-supported": "^0.1.0" + }, + "dependencies": { + "chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + } + } + }, + "longest-streak": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-2.0.4.tgz", + "integrity": "sha512-vM6rUVCVUJJt33bnmHiZEvr7wPT78ztX7rojL+LW51bHtLh6HTjx84LA5W4+oa6aKEJA7jJu5LR6vQRBpA5DVg==", + "dev": true + }, + "lowercase-keys": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", + "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==", + "dev": true + }, + "lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "requires": { + "yallist": "^4.0.0" + } + }, + "make-dir": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz", + "integrity": "sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw==", + "dev": true, + "requires": { + "semver": "^6.0.0" + } + }, + "map-cache": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", + "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", + "dev": true + }, + "map-obj": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-4.2.1.tgz", + "integrity": "sha512-+WA2/1sPmDj1dlvvJmB5G6JKfY9dpn7EVBUL06+y6PoljPkh+6V1QihwxNkbcGxCRjt2b0F9K0taiCuo7MbdFQ==", + "dev": true + }, + "map-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", + "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", + "dev": true, + "requires": { + "object-visit": "^1.0.0" + } + }, + "markdown-extensions": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/markdown-extensions/-/markdown-extensions-1.1.1.tgz", + "integrity": "sha512-WWC0ZuMzCyDHYCasEGs4IPvLyTGftYwh6wIEOULOF0HXcqZlhwRzrK0w2VUlxWA98xnvb/jszw4ZSkJ6ADpM6Q==", + "dev": true + }, + "markdown-table": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/markdown-table/-/markdown-table-2.0.0.tgz", + "integrity": "sha512-Ezda85ToJUBhM6WGaG6veasyym+Tbs3cMAw/ZhOPqXiYsr0jgocBV3j3nx+4lk47plLlIqjwuTm/ywVI+zjJ/A==", + "dev": true, + "requires": { + "repeat-string": "^1.0.0" + } + }, + "match-casing": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/match-casing/-/match-casing-1.0.3.tgz", + "integrity": "sha512-oMyC3vUVCFbGu+M2Zxl212LPJThcaw7QxB5lFuJPQCgV/dsGBP0yZeCoLmX6CiBkoBcVbAKDJZrBpJVu0XcLMw==", + "dev": true + }, + "mdast-comment-marker": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/mdast-comment-marker/-/mdast-comment-marker-1.1.2.tgz", + "integrity": "sha512-vTFXtmbbF3rgnTh3Zl3irso4LtvwUq/jaDvT2D1JqTGAwaipcS7RpTxzi6KjoRqI9n2yuAhzLDAC8xVTF3XYVQ==", + "dev": true + }, + "mdast-util-find-and-replace": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/mdast-util-find-and-replace/-/mdast-util-find-and-replace-1.1.1.tgz", + "integrity": "sha512-9cKl33Y21lyckGzpSmEQnIDjEfeeWelN5s1kUW1LwdB0Fkuq2u+4GdqcGEygYxJE8GVqCl0741bYXHgamfWAZA==", + "dev": true, + "requires": { + "escape-string-regexp": "^4.0.0", + "unist-util-is": "^4.0.0", + "unist-util-visit-parents": "^3.0.0" + }, + "dependencies": { + "escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "dev": true + } + } + }, + "mdast-util-from-markdown": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-0.8.5.tgz", + "integrity": "sha512-2hkTXtYYnr+NubD/g6KGBS/0mFmBcifAsI0yIWRiRo0PjVs6SSOSOdtzbp6kSGnShDN6G5aWZpKQ2lWRy27mWQ==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.0", + "mdast-util-to-string": "^2.0.0", + "micromark": "~2.11.0", + "parse-entities": "^2.0.0", + "unist-util-stringify-position": "^2.0.0" + } + }, + "mdast-util-gfm": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/mdast-util-gfm/-/mdast-util-gfm-0.1.2.tgz", + "integrity": "sha512-NNkhDx/qYcuOWB7xHUGWZYVXvjPFFd6afg6/e2g+SV4r9q5XUcCbV4Wfa3DLYIiD+xAEZc6K4MGaE/m0KDcPwQ==", + "dev": true, + "requires": { + "mdast-util-gfm-autolink-literal": "^0.1.0", + "mdast-util-gfm-strikethrough": "^0.2.0", + "mdast-util-gfm-table": "^0.1.0", + "mdast-util-gfm-task-list-item": "^0.1.0", + "mdast-util-to-markdown": "^0.6.1" + } + }, + "mdast-util-gfm-autolink-literal": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-autolink-literal/-/mdast-util-gfm-autolink-literal-0.1.3.tgz", + "integrity": "sha512-GjmLjWrXg1wqMIO9+ZsRik/s7PLwTaeCHVB7vRxUwLntZc8mzmTsLVr6HW1yLokcnhfURsn5zmSVdi3/xWWu1A==", + "dev": true, + "requires": { + "ccount": "^1.0.0", + "mdast-util-find-and-replace": "^1.1.0", + "micromark": "^2.11.3" + } + }, + "mdast-util-gfm-strikethrough": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-strikethrough/-/mdast-util-gfm-strikethrough-0.2.3.tgz", + "integrity": "sha512-5OQLXpt6qdbttcDG/UxYY7Yjj3e8P7X16LzvpX8pIQPYJ/C2Z1qFGMmcw+1PZMUM3Z8wt8NRfYTvCni93mgsgA==", + "dev": true, + "requires": { + "mdast-util-to-markdown": "^0.6.0" + } + }, + "mdast-util-gfm-table": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-table/-/mdast-util-gfm-table-0.1.6.tgz", + "integrity": "sha512-j4yDxQ66AJSBwGkbpFEp9uG/LS1tZV3P33fN1gkyRB2LoRL+RR3f76m0HPHaby6F4Z5xr9Fv1URmATlRRUIpRQ==", + "dev": true, + "requires": { + "markdown-table": "^2.0.0", + "mdast-util-to-markdown": "~0.6.0" + } + }, + "mdast-util-gfm-task-list-item": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-task-list-item/-/mdast-util-gfm-task-list-item-0.1.6.tgz", + "integrity": "sha512-/d51FFIfPsSmCIRNp7E6pozM9z1GYPIkSy1urQ8s/o4TC22BZ7DqfHFWiqBD23bc7J3vV1Fc9O4QIHBlfuit8A==", + "dev": true, + "requires": { + "mdast-util-to-markdown": "~0.6.0" + } + }, + "mdast-util-heading-style": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/mdast-util-heading-style/-/mdast-util-heading-style-1.0.6.tgz", + "integrity": "sha512-8ZuuegRqS0KESgjAGW8zTx4tJ3VNIiIaGFNEzFpRSAQBavVc7AvOo9I4g3crcZBfYisHs4seYh0rAVimO6HyOw==", + "dev": true + }, + "mdast-util-to-markdown": { + "version": "0.6.5", + "resolved": "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-0.6.5.tgz", + "integrity": "sha512-XeV9sDE7ZlOQvs45C9UKMtfTcctcaj/pGwH8YLbMHoMOXNNCn2LsqVQOqrF1+/NU8lKDAqozme9SCXWyo9oAcQ==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "longest-streak": "^2.0.0", + "mdast-util-to-string": "^2.0.0", + "parse-entities": "^2.0.0", + "repeat-string": "^1.0.0", + "zwitch": "^1.0.0" + } + }, + "mdast-util-to-nlcst": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/mdast-util-to-nlcst/-/mdast-util-to-nlcst-4.0.1.tgz", + "integrity": "sha512-Y4ffygj85MTt70STKnEquw6k73jYWJBaYcb4ITAKgSNokZF7fH8rEHZ1GsRY/JaxqUevMaEnsDmkVv5Z9uVRdg==", + "dev": true, + "requires": { + "nlcst-to-string": "^2.0.0", + "repeat-string": "^1.0.0", + "unist-util-position": "^3.0.0", + "vfile-location": "^3.1.0" + } + }, + "mdast-util-to-string": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-2.0.0.tgz", + "integrity": "sha512-AW4DRS3QbBayY/jJmD8437V1Gombjf8RSOUCMFBuo5iHi58AGEgVCKQ+ezHkZZDpAQS75hcBMpLqjpJTjtUL7w==", + "dev": true + }, + "mdast-util-toc": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-toc/-/mdast-util-toc-5.1.0.tgz", + "integrity": "sha512-csimbRIVkiqc+PpFeKDGQ/Ck2N4f9FYH3zzBMMJzcxoKL8m+cM0n94xXm0I9eaxHnKdY9n145SGTdyJC7i273g==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.3", + "@types/unist": "^2.0.3", + "extend": "^3.0.2", + "github-slugger": "^1.2.1", + "mdast-util-to-string": "^2.0.0", + "unist-util-is": "^4.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "memory-fs": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/memory-fs/-/memory-fs-0.2.0.tgz", + "integrity": "sha1-8rslNovBIeORwlIN6Slpyu4KApA=", + "dev": true + }, + "meow": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/meow/-/meow-9.0.0.tgz", + "integrity": "sha512-+obSblOQmRhcyBt62furQqRAQpNyWXo8BuQ5bN7dG8wmwQ+vwHKp/rCFD4CrTP8CsDQD1sjoZ94K417XEUk8IQ==", + "dev": true, + "requires": { + "@types/minimist": "^1.2.0", + "camelcase-keys": "^6.2.2", + "decamelize": "^1.2.0", + "decamelize-keys": "^1.1.0", + "hard-rejection": "^2.1.0", + "minimist-options": "4.1.0", + "normalize-package-data": "^3.0.0", + "read-pkg-up": "^7.0.1", + "redent": "^3.0.0", + "trim-newlines": "^3.0.0", + "type-fest": "^0.18.0", + "yargs-parser": "^20.2.3" + }, + "dependencies": { + "find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "dev": true, + "requires": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + } + }, + "hosted-git-info": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.0.2.tgz", + "integrity": "sha512-c9OGXbZ3guC/xOlCg1Ci/VgWlwsqDv1yMQL1CWqXDL0hDjXuNcq0zuR4xqPSuasI3kqFDhqSyTjREz5gzq0fXg==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + }, + "locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "dev": true, + "requires": { + "p-locate": "^4.1.0" + } + }, + "normalize-package-data": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-3.0.3.tgz", + "integrity": "sha512-p2W1sgqij3zMMyRC067Dg16bfzVH+w7hyegmpIvZ4JNjqtGOVAIvLmjBx3yP7YTe9vKJgkoNOPjwQGogDoMXFA==", + "dev": true, + "requires": { + "hosted-git-info": "^4.0.1", + "is-core-module": "^2.5.0", + "semver": "^7.3.4", + "validate-npm-package-license": "^3.0.1" + } + }, + "p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "dev": true, + "requires": { + "p-try": "^2.0.0" + } + }, + "p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "dev": true, + "requires": { + "p-limit": "^2.2.0" + } + }, + "read-pkg": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-5.2.0.tgz", + "integrity": "sha512-Ug69mNOpfvKDAc2Q8DRpMjjzdtrnv9HcSMX+4VsZxD1aZ6ZzrIE7rlzXBtWTyhULSMKg076AW6WR5iZpD0JiOg==", + "dev": true, + "requires": { + "@types/normalize-package-data": "^2.4.0", + "normalize-package-data": "^2.5.0", + "parse-json": "^5.0.0", + "type-fest": "^0.6.0" + }, + "dependencies": { + "hosted-git-info": { + "version": "2.8.9", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.8.9.tgz", + "integrity": "sha512-mxIDAb9Lsm6DoOJ7xH+5+X4y1LU/4Hi50L9C5sIswK3JzULS4bwk1FvjdBgvYR4bzT4tuUQiC15FE2f5HbLvYw==", + "dev": true + }, + "normalize-package-data": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", + "dev": true, + "requires": { + "hosted-git-info": "^2.1.4", + "resolve": "^1.10.0", + "semver": "2 || 3 || 4 || 5", + "validate-npm-package-license": "^3.0.1" + } + }, + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true + }, + "type-fest": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.6.0.tgz", + "integrity": "sha512-q+MB8nYR1KDLrgr4G5yemftpMC7/QLqVndBmEEdqzmNj5dcFOO4Oo8qlwZE3ULT3+Zim1F8Kq4cBnikNhlCMlg==", + "dev": true + } + } + }, + "read-pkg-up": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-7.0.1.tgz", + "integrity": "sha512-zK0TB7Xd6JpCLmlLmufqykGE+/TlOePD6qKClNW7hHDKFh/J7/7gCWGR7joEQEW1bKq3a3yUZSObOoWLFQ4ohg==", + "dev": true, + "requires": { + "find-up": "^4.1.0", + "read-pkg": "^5.2.0", + "type-fest": "^0.8.1" + }, + "dependencies": { + "type-fest": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.8.1.tgz", + "integrity": "sha512-4dbzIzqvjtgiM5rw1k5rEHtBANKmdudhGyBEajN01fEyhaAIhsoKNy6y7+IN93IfpFtwY9iqi7kD+xwKhQsNJA==", + "dev": true + } + } + }, + "resolve": { + "version": "1.20.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.20.0.tgz", + "integrity": "sha512-wENBPt4ySzg4ybFQW2TT1zMQucPK95HSh/nq2CFTZVOGut2+pQvSsgtda4d26YrYcr067wjbmzOG8byDPBX63A==", + "dev": true, + "requires": { + "is-core-module": "^2.2.0", + "path-parse": "^1.0.6" + } + }, + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + }, + "type-fest": { + "version": "0.18.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.18.1.tgz", + "integrity": "sha512-OIAYXk8+ISY+qTOwkHtKqzAuxchoMiD9Udx+FSGQDuiRR+PJKJHc2NJAXlbhkGwTt/4/nKZxELY1w3ReWOL8mw==", + "dev": true + } + } + }, + "merge-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", + "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", + "dev": true + }, + "merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true + }, + "micro-spelling-correcter": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/micro-spelling-correcter/-/micro-spelling-correcter-1.1.1.tgz", + "integrity": "sha512-lkJ3Rj/mtjlRcHk6YyCbvZhyWTOzdBvTHsxMmZSk5jxN1YyVSQ+JETAom55mdzfcyDrY/49Z7UCW760BK30crg==", + "dev": true + }, + "micromark": { + "version": "2.11.4", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-2.11.4.tgz", + "integrity": "sha512-+WoovN/ppKolQOFIAajxi7Lu9kInbPxFuTBVEavFcL8eAfVstoc5MocPmqBeAdBOJV00uaVjegzH4+MA0DN/uA==", + "dev": true, + "requires": { + "debug": "^4.0.0", + "parse-entities": "^2.0.0" + } + }, + "micromark-extension-gfm": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm/-/micromark-extension-gfm-0.3.3.tgz", + "integrity": "sha512-oVN4zv5/tAIA+l3GbMi7lWeYpJ14oQyJ3uEim20ktYFAcfX1x3LNlFGGlmrZHt7u9YlKExmyJdDGaTt6cMSR/A==", + "dev": true, + "requires": { + "micromark": "~2.11.0", + "micromark-extension-gfm-autolink-literal": "~0.5.0", + "micromark-extension-gfm-strikethrough": "~0.6.5", + "micromark-extension-gfm-table": "~0.4.0", + "micromark-extension-gfm-tagfilter": "~0.3.0", + "micromark-extension-gfm-task-list-item": "~0.3.0" + } + }, + "micromark-extension-gfm-autolink-literal": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-autolink-literal/-/micromark-extension-gfm-autolink-literal-0.5.7.tgz", + "integrity": "sha512-ePiDGH0/lhcngCe8FtH4ARFoxKTUelMp4L7Gg2pujYD5CSMb9PbblnyL+AAMud/SNMyusbS2XDSiPIRcQoNFAw==", + "dev": true, + "requires": { + "micromark": "~2.11.3" + } + }, + "micromark-extension-gfm-strikethrough": { + "version": "0.6.5", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-strikethrough/-/micromark-extension-gfm-strikethrough-0.6.5.tgz", + "integrity": "sha512-PpOKlgokpQRwUesRwWEp+fHjGGkZEejj83k9gU5iXCbDG+XBA92BqnRKYJdfqfkrRcZRgGuPuXb7DaK/DmxOhw==", + "dev": true, + "requires": { + "micromark": "~2.11.0" + } + }, + "micromark-extension-gfm-table": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-table/-/micromark-extension-gfm-table-0.4.3.tgz", + "integrity": "sha512-hVGvESPq0fk6ALWtomcwmgLvH8ZSVpcPjzi0AjPclB9FsVRgMtGZkUcpE0zgjOCFAznKepF4z3hX8z6e3HODdA==", + "dev": true, + "requires": { + "micromark": "~2.11.0" + } + }, + "micromark-extension-gfm-tagfilter": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-tagfilter/-/micromark-extension-gfm-tagfilter-0.3.0.tgz", + "integrity": "sha512-9GU0xBatryXifL//FJH+tAZ6i240xQuFrSL7mYi8f4oZSbc+NvXjkrHemeYP0+L4ZUT+Ptz3b95zhUZnMtoi/Q==", + "dev": true + }, + "micromark-extension-gfm-task-list-item": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-task-list-item/-/micromark-extension-gfm-task-list-item-0.3.3.tgz", + "integrity": "sha512-0zvM5iSLKrc/NQl84pZSjGo66aTGd57C1idmlWmE87lkMcXrTxg1uXa/nXomxJytoje9trP0NDLvw4bZ/Z/XCQ==", + "dev": true, + "requires": { + "micromark": "~2.11.0" + } + }, + "micromatch": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.4.tgz", + "integrity": "sha512-pRmzw/XUcwXGpD9aI9q/0XOwLNygjETJ8y0ao0wdqprrzDa4YnxLcz7fQRZr8voh8V10kGhABbNcHVk5wHgWwg==", + "dev": true, + "requires": { + "braces": "^3.0.1", + "picomatch": "^2.2.3" + } + }, + "mimic-fn": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz", + "integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==", + "dev": true + }, + "mimic-response": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==", + "dev": true + }, + "min-indent": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/min-indent/-/min-indent-1.0.1.tgz", + "integrity": "sha512-I9jwMn07Sy/IwOj3zVkVik2JTvgpaykDZEigL6Rx6N9LbMywwUSMtxET+7lVoDLLd3O3IXwJwvuuns8UB/HeAg==", + "dev": true + }, + "minimatch": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", + "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", + "dev": true, + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, + "minimist-options": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/minimist-options/-/minimist-options-4.1.0.tgz", + "integrity": "sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==", + "dev": true, + "requires": { + "arrify": "^1.0.1", + "is-plain-obj": "^1.1.0", + "kind-of": "^6.0.3" + }, + "dependencies": { + "arrify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", + "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", + "dev": true + }, + "is-plain-obj": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", + "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=", + "dev": true + } + } + }, + "mixin-deep": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.2.tgz", + "integrity": "sha512-WRoDn//mXBiJ1H40rqa3vH0toePwSsGb45iInWlTySa+Uu4k3tYUSxa2v1KqAiLtvlrSzaExqS1gtk96A9zvEA==", + "dev": true, + "requires": { + "for-in": "^1.0.2", + "is-extendable": "^1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "dev": true, + "requires": { + "is-plain-object": "^2.0.4" + } + } + } + }, + "ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", + "dev": true + }, + "multimap": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/multimap/-/multimap-1.1.0.tgz", + "integrity": "sha512-0ZIR9PasPxGXmRsEF8jsDzndzHDj7tIav+JUmvIFB/WHswliFnquxECT/De7GR4yg99ky/NlRKJT82G1y271bw==", + "dev": true + }, + "nanomatch": { + "version": "1.2.13", + "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz", + "integrity": "sha512-fpoe2T0RbHwBTBUOftAfBPaDEi06ufaUai0mE6Yn1kacc3SnTErfb/h+X94VXzI64rKFHYImXSvdwGGCmwOqCA==", + "dev": true, + "requires": { + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "fragment-cache": "^0.2.1", + "is-windows": "^1.0.2", + "kind-of": "^6.0.2", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + } + }, + "natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", + "dev": true + }, + "nlcst-is-literal": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/nlcst-is-literal/-/nlcst-is-literal-1.2.2.tgz", + "integrity": "sha512-R+1OJEmRl3ZOp9d8PbiRxGpnvmpi3jU+lzSqCJoLeogdEh0FYDRH1aC223qUbaKffxNTJkEfeDOeQfziw749yA==", + "dev": true, + "requires": { + "nlcst-to-string": "^2.0.0" + } + }, + "nlcst-normalize": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/nlcst-normalize/-/nlcst-normalize-2.1.5.tgz", + "integrity": "sha512-xSqTKv8IHIy3n/orD7wj81BZljLfbrTot0Pv64MYUnQUXfDbi1xDSpJR4qEmbFWyFoHsmivcOdgrK+o7ky3mcw==", + "dev": true, + "requires": { + "nlcst-to-string": "^2.0.0" + } + }, + "nlcst-search": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/nlcst-search/-/nlcst-search-2.0.0.tgz", + "integrity": "sha512-+3xdctMFTcG+76vKAa0wObNg1EYq7IIQlZcL+HxSFXkHO1DgSPRjsPJrmelVIvMg7rk+wmBcdPEoScv/CTT1Zw==", + "dev": true, + "requires": { + "nlcst-is-literal": "^1.0.0", + "nlcst-normalize": "^2.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "nlcst-to-string": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/nlcst-to-string/-/nlcst-to-string-2.0.4.tgz", + "integrity": "sha512-3x3jwTd6UPG7vi5k4GEzvxJ5rDA7hVUIRNHPblKuMVP9Z3xmlsd9cgLcpAMkc5uPOBna82EeshROFhsPkbnTZg==", + "dev": true + }, + "node-releases": { + "version": "1.1.75", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.75.tgz", + "integrity": "sha512-Qe5OUajvqrqDSy6wrWFmMwfJ0jVgwiw4T3KqmbTcZ62qW0gQkheXYhcFM1+lOVcGUoRxcEcfyvFMAnDgaF1VWw==", + "dev": true + }, + "normalize-package-data": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", + "dev": true, + "requires": { + "hosted-git-info": "^2.1.4", + "resolve": "^1.10.0", + "semver": "2 || 3 || 4 || 5", + "validate-npm-package-license": "^3.0.1" + }, + "dependencies": { + "hosted-git-info": { + "version": "2.8.9", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.8.9.tgz", + "integrity": "sha512-mxIDAb9Lsm6DoOJ7xH+5+X4y1LU/4Hi50L9C5sIswK3JzULS4bwk1FvjdBgvYR4bzT4tuUQiC15FE2f5HbLvYw==", + "dev": true + }, + "resolve": { + "version": "1.20.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.20.0.tgz", + "integrity": "sha512-wENBPt4ySzg4ybFQW2TT1zMQucPK95HSh/nq2CFTZVOGut2+pQvSsgtda4d26YrYcr067wjbmzOG8byDPBX63A==", + "dev": true, + "requires": { + "is-core-module": "^2.2.0", + "path-parse": "^1.0.6" + } + }, + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true + } + } + }, + "normalize-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "dev": true + }, + "normalize-url": { + "version": "4.5.1", + "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-4.5.1.tgz", + "integrity": "sha512-9UZCFRHQdNrfTpGg8+1INIg93B6zE0aXMVFkw1WFwvO4SlZywU6aLg5Of0Ap/PgcbSw4LNxvMWXMeugwMCX0AA==", + "dev": true + }, + "npm-run-path": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz", + "integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==", + "dev": true, + "requires": { + "path-key": "^3.0.0" + } + }, + "number-to-words": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/number-to-words/-/number-to-words-1.2.4.tgz", + "integrity": "sha512-/fYevVkXRcyBiZDg6yzZbm0RuaD6i0qRfn8yr+6D0KgBMOndFPxuW10qCHpzs50nN8qKuv78k8MuotZhcVX6Pw==", + "dev": true + }, + "obj-props": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/obj-props/-/obj-props-1.3.0.tgz", + "integrity": "sha512-k2Xkjx5wn6eC3537SWAXHzB6lkI81kS+icMKMkh4nG3w7shWG6MaWOBrNvhWVOszrtL5uxdfymQQfPUxwY+2eg==", + "dev": true + }, + "object-copy": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz", + "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", + "dev": true, + "requires": { + "copy-descriptor": "^0.1.0", + "define-property": "^0.2.5", + "kind-of": "^3.0.3" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true + }, + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "object-inspect": { + "version": "1.11.0", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.11.0.tgz", + "integrity": "sha512-jp7ikS6Sd3GxQfZJPyH3cjcbJF6GZPClgdV+EFygjFLQ5FmW/dRUnTd9PQ9k0JhoNDabWFbpF1yCdSWCC6gexg==", + "dev": true + }, + "object-is": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/object-is/-/object-is-1.1.5.tgz", + "integrity": "sha512-3cyDsyHgtmi7I7DfSSI2LDp6SK2lwvtbg0p0R1e0RvTqF5ceGx+K2dfSjm1bKDMVCFEDAQvy+o8c6a7VujOddw==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3" + } + }, + "object-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", + "dev": true + }, + "object-visit": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", + "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", + "dev": true, + "requires": { + "isobject": "^3.0.0" + } + }, + "object.assign": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.2.tgz", + "integrity": "sha512-ixT2L5THXsApyiUPYKmW+2EHpXXe5Ii3M+f4e+aJFAHao5amFRW6J0OO6c/LU8Be47utCx2GL89hxGB6XSmKuQ==", + "dev": true, + "requires": { + "call-bind": "^1.0.0", + "define-properties": "^1.1.3", + "has-symbols": "^1.0.1", + "object-keys": "^1.1.1" + } + }, + "object.pick": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", + "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", + "dev": true, + "requires": { + "isobject": "^3.0.1" + } + }, + "object.values": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.1.4.tgz", + "integrity": "sha512-TnGo7j4XSnKQoK3MfvkzqKCi0nVe/D9I9IjwTNYdb/fxYHpjrluHVOgw0AF6jrRFGMPHdfuidR09tIDiIvnaSg==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3", + "es-abstract": "^1.18.2" + } + }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dev": true, + "requires": { + "wrappy": "1" + } + }, + "onetime": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", + "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", + "dev": true, + "requires": { + "mimic-fn": "^2.1.0" + } + }, + "open": { + "version": "7.4.2", + "resolved": "https://registry.npmjs.org/open/-/open-7.4.2.tgz", + "integrity": "sha512-MVHddDVweXZF3awtlAS+6pgKLlm/JgxZ90+/NBurBoQctVOOB/zDdVjcyPzQ+0laDGbsWgrRkflI65sQeOgT9Q==", + "dev": true, + "requires": { + "is-docker": "^2.0.0", + "is-wsl": "^2.1.1" + } + }, + "open-editor": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/open-editor/-/open-editor-3.0.0.tgz", + "integrity": "sha512-00Nqoa7k8F4AK1oSFMIIhYku+essXiCljR2L2kV+bl5j90ANgbQgzEeTdZu23LsikDoz+KfhyRHpGLAwpQhugA==", + "dev": true, + "requires": { + "env-editor": "^0.4.1", + "execa": "^5.0.0", + "line-column-path": "^2.0.0", + "open": "^7.3.0" + } + }, + "optionator": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.1.tgz", + "integrity": "sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==", + "dev": true, + "requires": { + "deep-is": "^0.1.3", + "fast-levenshtein": "^2.0.6", + "levn": "^0.4.1", + "prelude-ls": "^1.2.1", + "type-check": "^0.4.0", + "word-wrap": "^1.2.3" + } + }, + "p-cancelable": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-1.1.0.tgz", + "integrity": "sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==", + "dev": true + }, + "p-limit": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", + "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", + "dev": true, + "requires": { + "yocto-queue": "^0.1.0" + } + }, + "p-locate": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz", + "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==", + "dev": true, + "requires": { + "p-limit": "^3.0.2" + } + }, + "p-reduce": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/p-reduce/-/p-reduce-2.1.0.tgz", + "integrity": "sha512-2USApvnsutq8uoxZBGbbWM0JIYLiEMJ9RlaN7fAzVNb9OZN0SHjjTTfIcb667XynS5Y1VhwDJVDa72TnPzAYWw==", + "dev": true + }, + "p-try": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", + "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==", + "dev": true + }, + "package-json": { + "version": "6.5.0", + "resolved": "https://registry.npmjs.org/package-json/-/package-json-6.5.0.tgz", + "integrity": "sha512-k3bdm2n25tkyxcjSKzB5x8kfVxlMdgsbPr0GkZcwHsLpba6cBjqCt1KlcChKEvxHIcTB1FVMuwoijZ26xex5MQ==", + "dev": true, + "requires": { + "got": "^9.6.0", + "registry-auth-token": "^4.0.0", + "registry-url": "^5.0.0", + "semver": "^6.2.0" + } + }, + "parent-module": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", + "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", + "dev": true, + "requires": { + "callsites": "^3.0.0" + } + }, + "parse-english": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/parse-english/-/parse-english-4.2.0.tgz", + "integrity": "sha512-jw5N6wZUZViIw3VLG/FUSeL3vDhfw5Q2g4E3nYC69Mm5ANbh9ZWd+eligQbeUoyObZM8neynTn3l14e09pjEWg==", + "dev": true, + "requires": { + "nlcst-to-string": "^2.0.0", + "parse-latin": "^4.0.0", + "unist-util-modify-children": "^2.0.0", + "unist-util-visit-children": "^1.0.0" + } + }, + "parse-entities": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-2.0.0.tgz", + "integrity": "sha512-kkywGpCcRYhqQIchaWqZ875wzpS/bMKhz5HnN3p7wveJTkTtyAB/AlnS0f8DFSqYW1T82t6yEAkEcB+A1I3MbQ==", + "dev": true, + "requires": { + "character-entities": "^1.0.0", + "character-entities-legacy": "^1.0.0", + "character-reference-invalid": "^1.0.0", + "is-alphanumerical": "^1.0.0", + "is-decimal": "^1.0.0", + "is-hexadecimal": "^1.0.0" + } + }, + "parse-json": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz", + "integrity": "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==", + "dev": true, + "requires": { + "@babel/code-frame": "^7.0.0", + "error-ex": "^1.3.1", + "json-parse-even-better-errors": "^2.3.0", + "lines-and-columns": "^1.1.6" + } + }, + "parse-latin": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/parse-latin/-/parse-latin-4.3.0.tgz", + "integrity": "sha512-TYKL+K98dcAWoCw/Ac1yrPviU8Trk+/gmjQVaoWEFDZmVD4KRg6c/80xKqNNFQObo2mTONgF8trzAf2UTwKafw==", + "dev": true, + "requires": { + "nlcst-to-string": "^2.0.0", + "unist-util-modify-children": "^2.0.0", + "unist-util-visit-children": "^1.0.0" + } + }, + "pascalcase": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", + "integrity": "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=", + "dev": true + }, + "path-dirname": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", + "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=", + "dev": true + }, + "path-exists": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", + "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", + "dev": true + }, + "path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", + "dev": true + }, + "path-key": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", + "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", + "dev": true + }, + "path-parse": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", + "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", + "dev": true + }, + "path-type": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", + "integrity": "sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==", + "dev": true + }, + "picomatch": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.0.tgz", + "integrity": "sha512-lY1Q/PiJGC2zOv/z391WOTD+Z02bCgsFfvxoXXf6h7kv9o+WmsmzYqrAwY63sNgOxE4xEdq0WyUnXfKeBrSvYw==", + "dev": true + }, + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true + }, + "pkg-dir": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-4.2.0.tgz", + "integrity": "sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==", + "dev": true, + "requires": { + "find-up": "^4.0.0" + }, + "dependencies": { + "find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "dev": true, + "requires": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + } + }, + "locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "dev": true, + "requires": { + "p-locate": "^4.1.0" + } + }, + "p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "dev": true, + "requires": { + "p-try": "^2.0.0" + } + }, + "p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "dev": true, + "requires": { + "p-limit": "^2.2.0" + } + } + } + }, + "pkg-up": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/pkg-up/-/pkg-up-2.0.0.tgz", + "integrity": "sha1-yBmscoBZpGHKscOImivjxJoATX8=", + "dev": true, + "requires": { + "find-up": "^2.1.0" + }, + "dependencies": { + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "locate-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", + "dev": true, + "requires": { + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + } + }, + "p-limit": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, + "requires": { + "p-try": "^1.0.0" + } + }, + "p-locate": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "dev": true, + "requires": { + "p-limit": "^1.1.0" + } + }, + "p-try": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", + "dev": true + }, + "path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true + } + } + }, + "plur": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/plur/-/plur-4.0.0.tgz", + "integrity": "sha512-4UGewrYgqDFw9vV6zNV+ADmPAUAfJPKtGvb/VdpQAx25X5f3xXdGdyOEVFwkl8Hl/tl7+xbeHqSEM+D5/TirUg==", + "dev": true, + "requires": { + "irregular-plurals": "^3.2.0" + } + }, + "pluralize": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/pluralize/-/pluralize-8.0.0.tgz", + "integrity": "sha512-Nc3IT5yHzflTfbjgqWcCPpo7DaKy4FnpB0l/zCAW0Tc7jxAiuqSxHasntB3D7887LSrA93kDJ9IXovxJYxyLCA==", + "dev": true + }, + "posix-character-classes": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", + "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=", + "dev": true + }, + "prelude-ls": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", + "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", + "dev": true + }, + "prepend-http": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", + "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=", + "dev": true + }, + "prettier": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.3.2.tgz", + "integrity": "sha512-lnJzDfJ66zkMy58OL5/NY5zp70S7Nz6KqcKkXYzn2tMVrNxvbqaBpg7H3qHaLxCJ5lNMsGuM8+ohS7cZrthdLQ==", + "dev": true + }, + "prettier-linter-helpers": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/prettier-linter-helpers/-/prettier-linter-helpers-1.0.0.tgz", + "integrity": "sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w==", + "dev": true, + "requires": { + "fast-diff": "^1.1.2" + } + }, + "progress": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", + "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==", + "dev": true + }, + "propose": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/propose/-/propose-0.0.5.tgz", + "integrity": "sha1-SKBl2ex9TIZn9AULFcSi2F28pWs=", + "dev": true, + "requires": { + "levenshtein-edit-distance": "^1.0.0" + } + }, + "proto-props": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/proto-props/-/proto-props-2.0.0.tgz", + "integrity": "sha512-2yma2tog9VaRZY2mn3Wq51uiSW4NcPYT1cQdBagwyrznrilKSZwIZ0UG3ZPL/mx+axEns0hE35T5ufOYZXEnBQ==", + "dev": true + }, + "pump": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "dev": true, + "requires": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "punycode": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true + }, + "pupa": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/pupa/-/pupa-2.1.1.tgz", + "integrity": "sha512-l1jNAspIBSFqbT+y+5FosojNpVpF94nlI+wDUpqP9enwOTfHx9f0gh5nB96vl+6yTpsJsypeNrwfzPrKuHB41A==", + "dev": true, + "requires": { + "escape-goat": "^2.0.0" + } + }, + "queue-microtask": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", + "dev": true + }, + "quick-lru": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-4.0.1.tgz", + "integrity": "sha512-ARhCpm70fzdcvNQfPoy49IaanKkTlRWF2JMzqhcJbhSFRZv7nPTvZJdcY7301IPmvW+/p0RgIWnQDLJxifsQ7g==", + "dev": true + }, + "quotation": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/quotation/-/quotation-1.1.3.tgz", + "integrity": "sha512-45gUgmX/RtQOQV1kwM06boP49OYXcKCPrYwdmAvs5YqkpiobhNKKwo524JM6Ma0ko3oN9tXNcWs9+ABq3Ry7YA==", + "dev": true + }, + "rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "dev": true, + "requires": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "dependencies": { + "strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", + "dev": true + } + } + }, + "read-pkg": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", + "integrity": "sha1-nLxoaXj+5l0WwA4rGcI3/Pbjg4k=", + "dev": true, + "requires": { + "load-json-file": "^4.0.0", + "normalize-package-data": "^2.3.2", + "path-type": "^3.0.0" + }, + "dependencies": { + "path-type": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", + "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", + "dev": true, + "requires": { + "pify": "^3.0.0" + } + } + } + }, + "read-pkg-up": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", + "integrity": "sha1-PtSWaF26D4/hGNBpHcUfSh/5bwc=", + "dev": true, + "requires": { + "find-up": "^2.0.0", + "read-pkg": "^3.0.0" + }, + "dependencies": { + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "locate-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", + "dev": true, + "requires": { + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + } + }, + "p-limit": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, + "requires": { + "p-try": "^1.0.0" + } + }, + "p-locate": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "dev": true, + "requires": { + "p-limit": "^1.1.0" + } + }, + "p-try": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", + "dev": true + }, + "path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true + } + } + }, + "readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "dev": true, + "requires": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + } + }, + "readdirp": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", + "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", + "dev": true, + "requires": { + "picomatch": "^2.2.1" + } + }, + "redent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/redent/-/redent-3.0.0.tgz", + "integrity": "sha512-6tDA8g98We0zd0GvVeMT9arEOnTw9qM03L9cJXaCjrip1OO764RDBLBfrB4cwzNGDj5OA5ioymC9GkizgWJDUg==", + "dev": true, + "requires": { + "indent-string": "^4.0.0", + "strip-indent": "^3.0.0" + } + }, + "regex-not": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz", + "integrity": "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==", + "dev": true, + "requires": { + "extend-shallow": "^3.0.2", + "safe-regex": "^1.1.0" + }, + "dependencies": { + "safe-regex": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz", + "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", + "dev": true, + "requires": { + "ret": "~0.1.10" + } + } + } + }, + "regexp-tree": { + "version": "0.1.23", + "resolved": "https://registry.npmjs.org/regexp-tree/-/regexp-tree-0.1.23.tgz", + "integrity": "sha512-+7HWfb4Bvu8Rs2eQTUIpX9I/PlQkYOuTNbRpKLJlQpSgwSkzFYh+pUj0gtvglnOZLKB6YgnIgRuJ2/IlpL48qw==", + "dev": true + }, + "regexp.prototype.flags": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.3.1.tgz", + "integrity": "sha512-JiBdRBq91WlY7uRJ0ds7R+dU02i6LKi8r3BuQhNXn+kmeLN+EfHhfjqMRis1zJxnlu88hq/4dx0P2OP3APRTOA==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3" + } + }, + "regexpp": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.2.0.tgz", + "integrity": "sha512-pq2bWo9mVD43nbts2wGv17XLiNLya+GklZ8kaDLV2Z08gDCsGpnKn9BFMepvWuHCbyVvY7J5o5+BVvoQbmlJLg==", + "dev": true + }, + "registry-auth-token": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-4.2.1.tgz", + "integrity": "sha512-6gkSb4U6aWJB4SF2ZvLb76yCBjcvufXBqvvEx1HbmKPkutswjW1xNVRY0+daljIYRbogN7O0etYSlbiaEQyMyw==", + "dev": true, + "requires": { + "rc": "^1.2.8" + } + }, + "registry-url": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-5.1.0.tgz", + "integrity": "sha512-8acYXXTI0AkQv6RAOjE3vOaIXZkT9wo4LOFbBKYQEEnnMNBpKqdUrI6S4NT0KPIo/WVvJ5tE/X5LF/TQUf0ekw==", + "dev": true, + "requires": { + "rc": "^1.2.8" + } + }, + "remark": { + "version": "13.0.0", + "resolved": "https://registry.npmjs.org/remark/-/remark-13.0.0.tgz", + "integrity": "sha512-HDz1+IKGtOyWN+QgBiAT0kn+2s6ovOxHyPAFGKVE81VSzJ+mq7RwHFledEvB5F1p4iJvOah/LOKdFuzvRnNLCA==", + "dev": true, + "requires": { + "remark-parse": "^9.0.0", + "remark-stringify": "^9.0.0", + "unified": "^9.1.0" + } + }, + "remark-cli": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/remark-cli/-/remark-cli-9.0.0.tgz", + "integrity": "sha512-y6kCXdwZoMoh0Wo4Och1tDW50PmMc86gW6GpF08v9d+xUCEJE2wwXdQ+TnTaUamRnfFdU+fE+eNf2PJ53cyq8g==", + "dev": true, + "requires": { + "markdown-extensions": "^1.1.0", + "remark": "^13.0.0", + "unified-args": "^8.0.0" + } + }, + "remark-comment-config": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/remark-comment-config/-/remark-comment-config-6.0.0.tgz", + "integrity": "sha512-hpv4RS6AASn+ah+j9k+3+RsQmtAfRbt2evXCEoW/9W93CJ7PLkxCgeoNnkssGjQ6mLNV6vS5vNflSVIJALn29Q==", + "dev": true, + "requires": { + "mdast-comment-marker": "^1.0.1" + } + }, + "remark-gfm": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/remark-gfm/-/remark-gfm-1.0.0.tgz", + "integrity": "sha512-KfexHJCiqvrdBZVbQ6RopMZGwaXz6wFJEfByIuEwGf0arvITHjiKKZ1dpXujjH9KZdm1//XJQwgfnJ3lmXaDPA==", + "dev": true, + "requires": { + "mdast-util-gfm": "^0.1.0", + "micromark-extension-gfm": "^0.3.0" + } + }, + "remark-github": { + "version": "10.1.0", + "resolved": "https://registry.npmjs.org/remark-github/-/remark-github-10.1.0.tgz", + "integrity": "sha512-q0BTFb41N6/uXQVkxRwLRTFRfLFPYP+8li26Js5XC0GKritCSaxrftd+t+8sfN+1i9BtmJPUKoS7CZwtccj0Fg==", + "dev": true, + "requires": { + "mdast-util-find-and-replace": "^1.0.0", + "mdast-util-to-string": "^1.0.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "remark-lint": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/remark-lint/-/remark-lint-8.0.0.tgz", + "integrity": "sha512-ESI8qJQ/TIRjABDnqoFsTiZntu+FRifZ5fJ77yX63eIDijl/arvmDvT+tAf75/Nm5BFL4R2JFUtkHRGVjzYUsg==", + "dev": true, + "requires": { + "remark-message-control": "^6.0.0" + } + }, + "remark-lint-blockquote-indentation": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-blockquote-indentation/-/remark-lint-blockquote-indentation-2.0.1.tgz", + "integrity": "sha512-uJ9az/Ms9AapnkWpLSCJfawBfnBI2Tn1yUsPNqIFv6YM98ymetItUMyP6ng9NFPqDvTQBbiarulkgoEo0wcafQ==", + "dev": true, + "requires": { + "mdast-util-to-string": "^1.0.2", + "pluralize": "^8.0.0", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "remark-lint-checkbox-character-style": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-checkbox-character-style/-/remark-lint-checkbox-character-style-3.0.0.tgz", + "integrity": "sha512-691OJ5RdBRXVpvnOEiBhMB4uhHJSHVttw83O4qyAkNBiqxa1Axqhsz8FgmzYgRLQbOGd2ncVUcXG1LOJt6C0DQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-checkbox-content-indent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-checkbox-content-indent/-/remark-lint-checkbox-content-indent-3.0.0.tgz", + "integrity": "sha512-+T4+hoY85qZE2drD2rCe14vF7fAgD3Kv2fkFd1HRvv3M5Riy148w/4YeoBI5U5BpybGTVUeEUYLCeJ8zbJLjkw==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0", + "vfile-location": "^3.0.0" + } + }, + "remark-lint-code-block-style": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-code-block-style/-/remark-lint-code-block-style-2.0.1.tgz", + "integrity": "sha512-eRhmnColmSxJhO61GHZkvO67SpHDshVxs2j3+Zoc5Y1a4zQT2133ZAij04XKaBFfsVLjhbY/+YOWxgvtjx2nmA==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-definition-case": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-definition-case/-/remark-lint-definition-case-2.0.1.tgz", + "integrity": "sha512-M+XlThtQwEJLQnQb5Gi6xZdkw92rGp7m2ux58WMw/Qlcg02WgHR/O0OcHPe5VO5hMJrtI+cGG5T0svsCgRZd3w==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-definition-spacing": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-definition-spacing/-/remark-lint-definition-spacing-2.0.1.tgz", + "integrity": "sha512-xK9DOQO5MudITD189VyUiMHBIKltW1oc55L7Fti3i9DedXoBG7Phm+V9Mm7IdWzCVkquZVgVk63xQdqzSQRrSQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-emphasis-marker": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-emphasis-marker/-/remark-lint-emphasis-marker-2.0.1.tgz", + "integrity": "sha512-7mpbAUrSnHiWRyGkbXRL5kfSKY9Cs8cdob7Fw+Z02/pufXMF4yRWaegJ5NTUu1RE+SKlF44wtWWjvcIoyY6/aw==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-fenced-code-flag": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-fenced-code-flag/-/remark-lint-fenced-code-flag-2.0.1.tgz", + "integrity": "sha512-+COnWHlS/h02FMxoZWxNlZW3Y8M0cQQpmx3aNCbG7xkyMyCKsMLg9EmRvYHHIbxQCuF3JT0WWx5AySqlc7d+NA==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-fenced-code-marker": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-fenced-code-marker/-/remark-lint-fenced-code-marker-2.0.1.tgz", + "integrity": "sha512-lujpjm04enn3ma6lITlttadld6eQ1OWAEcT3qZzvFHp+zPraC0yr0eXlvtDN/0UH8mrln/QmGiZp3i8IdbucZg==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-file-extension": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/remark-lint-file-extension/-/remark-lint-file-extension-1.0.5.tgz", + "integrity": "sha512-oVQdf5vEomwHkfQ7R/mgmsWW2H/t9kSvnrxtVoNOHr+qnOEafKKDn+AFhioN2kqtjCZBAjSSrePs6xGKmXKDTw==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0" + } + }, + "remark-lint-final-definition": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/remark-lint-final-definition/-/remark-lint-final-definition-2.1.0.tgz", + "integrity": "sha512-83K7n2icOHPfBzbR5Mr1o7cu8gOjD8FwJkFx/ly+rW+8SHfjCj4D3WOFGQ1xVdmHjfomBDXXDSNo2oiacADVXQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-final-newline": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/remark-lint-final-newline/-/remark-lint-final-newline-1.0.5.tgz", + "integrity": "sha512-rfLlW8+Fz2dqnaEgU4JwLA55CQF1T4mfSs/GwkkeUCGPenvEYwSkCN2KO2Gr1dy8qPoOdTFE1rSufLjmeTW5HA==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0" + } + }, + "remark-lint-first-heading-level": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-first-heading-level/-/remark-lint-first-heading-level-2.0.1.tgz", + "integrity": "sha512-XoK/eLfnz1VSA8QkfMbdbvlCqOwgw29MAWEGC4Cv0666nTcY9uWHlZ/SV/20YNmuEVdfCA+92v92mM486qcASQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-hard-break-spaces": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-hard-break-spaces/-/remark-lint-hard-break-spaces-2.0.1.tgz", + "integrity": "sha512-Qfn/BMQFamHhtbfLrL8Co/dbYJFLRL4PGVXZ5wumkUO5f9FkZC2RsV+MD9lisvGTkJK0ZEJrVVeaPbUIFM0OAw==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-heading-style": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-heading-style/-/remark-lint-heading-style-2.0.1.tgz", + "integrity": "sha512-IrFLNs0M5Vbn9qg51AYhGUfzgLAcDOjh2hFGMz3mx664dV6zLcNZOPSdJBBJq3JQR4gKpoXcNwN1+FFaIATj+A==", + "dev": true, + "requires": { + "mdast-util-heading-style": "^1.0.2", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-link-title-style": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-link-title-style/-/remark-lint-link-title-style-2.0.1.tgz", + "integrity": "sha512-+Q7Ew8qpOQzjqbDF6sUHmn9mKgje+m2Ho8Xz7cEnGIRaKJgtJzkn/dZqQM/az0gn3zaN6rOuwTwqw4EsT5EsIg==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0", + "vfile-location": "^3.0.0" + } + }, + "remark-lint-list-item-bullet-indent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-list-item-bullet-indent/-/remark-lint-list-item-bullet-indent-3.0.0.tgz", + "integrity": "sha512-X2rleWP8XReC4LXKF7Qi5vYiPJkA4Grx5zxsjHofFrVRz6j0PYOCuz7vsO+ZzMunFMfom6FODnscSWz4zouDVw==", + "dev": true, + "requires": { + "pluralize": "^8.0.0", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-list-item-indent": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-list-item-indent/-/remark-lint-list-item-indent-2.0.1.tgz", + "integrity": "sha512-4IKbA9GA14Q9PzKSQI6KEHU/UGO36CSQEjaDIhmb9UOhyhuzz4vWhnSIsxyI73n9nl9GGRAMNUSGzr4pQUFwTA==", + "dev": true, + "requires": { + "pluralize": "^8.0.0", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-maximum-heading-length": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-maximum-heading-length/-/remark-lint-maximum-heading-length-2.0.1.tgz", + "integrity": "sha512-1CjJ71YDqEpoOjUnc4wrwZV8ZGXWUIYRYeGoarAy3QKHepJL9M+zkdbOxZDfhc3tjVoDW/LWcgsW+DEpczgiMA==", + "dev": true, + "requires": { + "mdast-util-to-string": "^1.0.2", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "remark-lint-maximum-line-length": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/remark-lint-maximum-line-length/-/remark-lint-maximum-line-length-2.0.3.tgz", + "integrity": "sha512-zyWHBFh1oPAy+gkaVFXiTHYP2WwriIeBtaarDqkweytw0+qmuikjVMJTWbQ3+XfYBreD7KKDM9SI79nkp0/IZQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-auto-link-without-protocol": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-auto-link-without-protocol/-/remark-lint-no-auto-link-without-protocol-2.0.1.tgz", + "integrity": "sha512-TFcXxzucsfBb/5uMqGF1rQA+WJJqm1ZlYQXyvJEXigEZ8EAxsxZGPb/gOQARHl/y0vymAuYxMTaChavPKaBqpQ==", + "dev": true, + "requires": { + "mdast-util-to-string": "^1.0.2", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "remark-lint-no-blockquote-without-marker": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-no-blockquote-without-marker/-/remark-lint-no-blockquote-without-marker-4.0.0.tgz", + "integrity": "sha512-Y59fMqdygRVFLk1gpx2Qhhaw5IKOR9T38Wf7pjR07bEFBGUNfcoNVIFMd1TCJfCPQxUyJzzSqfZz/KT7KdUuiQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.0.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0", + "vfile-location": "^3.0.0" + } + }, + "remark-lint-no-consecutive-blank-lines": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-no-consecutive-blank-lines/-/remark-lint-no-consecutive-blank-lines-3.0.0.tgz", + "integrity": "sha512-kmzLlOLrapBKEngwYFTdCZDmeOaze6adFPB7G0EdymD9V1mpAlnneINuOshRLEDKK5fAhXKiZXxdGIaMPkiXrA==", + "dev": true, + "requires": { + "pluralize": "^8.0.0", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-duplicate-defined-urls": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-duplicate-defined-urls/-/remark-lint-no-duplicate-defined-urls-1.0.1.tgz", + "integrity": "sha512-fUx4grm0oboxl+uwsHsRQGp3A929ujORrFoB/5eIyMDslxrgMTHKYf9ylxcC5yBRypkZi9AhFWBJ/wtVrxYEAg==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.0.0", + "unist-util-position": "^3.0.0", + "unist-util-stringify-position": "^2.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-duplicate-definitions": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-duplicate-definitions/-/remark-lint-no-duplicate-definitions-2.0.1.tgz", + "integrity": "sha512-XL22benJZB01m+aOse91nsu1IMFqeWJWme9QvoJuxIcBROO1BG1VoqLOkwNcawE/M/0CkvTo5rfx0eMlcnXOIw==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-stringify-position": "^2.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-duplicate-headings-in-section": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/remark-lint-no-duplicate-headings-in-section/-/remark-lint-no-duplicate-headings-in-section-2.0.2.tgz", + "integrity": "sha512-qtpTAvXgKkzDas7z3H3tzf/SDQIZ6zPEc9CaGZS/qMA2b5ORfQv+EC8NueK4x6+el19kbS6tX23iEnPXVYq1VQ==", + "dev": true, + "requires": { + "mdast-util-to-string": "^1.0.2", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-stringify-position": "^2.0.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "remark-lint-no-emphasis-as-heading": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-emphasis-as-heading/-/remark-lint-no-emphasis-as-heading-2.0.1.tgz", + "integrity": "sha512-z86+yWtVivtuGIxIC4g9RuATbgZgOgyLcnaleonJ7/HdGTYssjJNyqCJweaWSLoaI0akBQdDwmtJahW5iuX3/g==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-empty-url": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-empty-url/-/remark-lint-no-empty-url-2.0.1.tgz", + "integrity": "sha512-CBO5hgxlHWrnBPex0GfKZy6ORe2wkLrrHODVPUpLplDA72cQbDzQKedHGgh76euGDs+jvP7RO+IljozdLLfSTw==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-file-name-articles": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/remark-lint-no-file-name-articles/-/remark-lint-no-file-name-articles-1.0.5.tgz", + "integrity": "sha512-AQk5eTb3s3TAPPjiglZgqlQj4ycao+gPs8/XkdN1VCPUtewW0GgwoQe7YEuBKayJ6ioN8dGP37Kg/P/PlKaRQA==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0" + } + }, + "remark-lint-no-file-name-consecutive-dashes": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/remark-lint-no-file-name-consecutive-dashes/-/remark-lint-no-file-name-consecutive-dashes-1.0.5.tgz", + "integrity": "sha512-Mg2IDsi790/dSdAzwnBnsMYdZm3qC2QgGwqOWcr0TPABJhhjC3p8r5fX4MNMTXI5It7B7bW9+ImmCeLOZiXkLg==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0" + } + }, + "remark-lint-no-file-name-irregular-characters": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/remark-lint-no-file-name-irregular-characters/-/remark-lint-no-file-name-irregular-characters-1.0.5.tgz", + "integrity": "sha512-Oe5i99qNUKc2bxmiH421o5B/kqlf1dfjAxpHNLhi2X2dXE91zRGavrlRM/4f4oR0N9Bqb3qB9JZPyMPWrzu9XA==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0" + } + }, + "remark-lint-no-file-name-mixed-case": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/remark-lint-no-file-name-mixed-case/-/remark-lint-no-file-name-mixed-case-1.0.5.tgz", + "integrity": "sha512-ilrUCbHZin/ENwr8c3SC2chgkFsizXjBQIB/oZ7gnm1IkCkZPiMyXZAHdpwC/DjbrpGxfMYh9JmIHao4giS5+A==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0" + } + }, + "remark-lint-no-file-name-outer-dashes": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/remark-lint-no-file-name-outer-dashes/-/remark-lint-no-file-name-outer-dashes-1.0.6.tgz", + "integrity": "sha512-rT8CmcIlenegS0Yst4maYXdZfqIjBOiRUY8j/KJkORF5tKH+3O1/S07025qPGmcRihzK3w4yO0K8rgkKQw0b9w==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0" + } + }, + "remark-lint-no-heading-content-indent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-no-heading-content-indent/-/remark-lint-no-heading-content-indent-3.0.0.tgz", + "integrity": "sha512-yULDoVSIqKylLDfW6mVUbrHlyEWUSFtVFiKc+/BA412xDIhm8HZLUnP+FsuBC0OzbIZ+bO9Txy52WtO3LGnK1A==", + "dev": true, + "requires": { + "mdast-util-heading-style": "^1.0.2", + "pluralize": "^8.0.0", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-heading-indent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-no-heading-indent/-/remark-lint-no-heading-indent-3.0.0.tgz", + "integrity": "sha512-b8ImhLv2AnRDxtYUODplzsl/7IwQ+lqRmD1bwbZgSerEP9MLaULW3SjH37EyA6z+8rCDjvEyppKKU6zec0TCjg==", + "dev": true, + "requires": { + "pluralize": "^8.0.0", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-heading-like-paragraph": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-heading-like-paragraph/-/remark-lint-no-heading-like-paragraph-2.0.1.tgz", + "integrity": "sha512-9JDhpIvs4996PnHF5KUnx8/YN39MvZR0uf+EeVILdJbJ2IUL8BOlGNhMFc0CSmxajtIxobjiS+yzAvLG57pUFw==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-heading-punctuation": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-heading-punctuation/-/remark-lint-no-heading-punctuation-2.0.1.tgz", + "integrity": "sha512-lY/eF6GbMeGu4cSuxfGHyvaQQBIq/6T/o+HvAR5UfxSTxmxZFwbZneAI2lbeR1zPcqOU87NsZ5ZZzWVwdLpPBw==", + "dev": true, + "requires": { + "mdast-util-to-string": "^1.0.2", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "remark-lint-no-html": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-html/-/remark-lint-no-html-2.0.1.tgz", + "integrity": "sha512-fDISacCkZCRgl1MeCx5Fx+eWL0iS2GK1EOETR1yAA0av7LYiF8tUwsP4/iRqcxIT30YoDlYoiNRyprD2eyWsUg==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-inline-padding": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-no-inline-padding/-/remark-lint-no-inline-padding-3.0.0.tgz", + "integrity": "sha512-3s9uW3Yux9RFC0xV81MQX3bsYs+UY7nPnRuMxeIxgcVwxQ4E/mTJd9QjXUwBhU9kdPtJ5AalngdmOW2Tgar8Cg==", + "dev": true, + "requires": { + "mdast-util-to-string": "^1.0.2", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "remark-lint-no-literal-urls": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-literal-urls/-/remark-lint-no-literal-urls-2.0.1.tgz", + "integrity": "sha512-IDdKtWOMuKVQIlb1CnsgBoyoTcXU3LppelDFAIZePbRPySVHklTtuK57kacgU5grc7gPM04bZV96eliGrRU7Iw==", + "dev": true, + "requires": { + "mdast-util-to-string": "^1.0.2", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "remark-lint-no-missing-blank-lines": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-missing-blank-lines/-/remark-lint-no-missing-blank-lines-2.0.1.tgz", + "integrity": "sha512-gM46JM8NMFj5PG8pkxOQ0AvkRMEX1lD7UO9b/eqUgYQ6OiJaCG8dInogCd++MVSUDpMMf4FF9dksRM/AOiFgIQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-multiple-toplevel-headings": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-multiple-toplevel-headings/-/remark-lint-no-multiple-toplevel-headings-2.0.1.tgz", + "integrity": "sha512-VKSItR6c+u3OsE5pUiSmNusERNyQS9Nnji26ezoQ1uvy06k3RypIjmzQqJ/hCkSiF+hoyC3ibtrrGT8gorzCmQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-stringify-position": "^2.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-paragraph-content-indent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-no-paragraph-content-indent/-/remark-lint-no-paragraph-content-indent-3.0.0.tgz", + "integrity": "sha512-breI0QSFAxvs2osc8yAzPqWoi4VfY9ccyV+/WQKOIIU8yTj8swN/kFFqnP7wdeY4O9BSmUJ7bPdWCsmrVworXA==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0", + "vfile-location": "^3.0.0" + } + }, + "remark-lint-no-reference-like-url": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-reference-like-url/-/remark-lint-no-reference-like-url-2.0.1.tgz", + "integrity": "sha512-MeZtlimw30Hd74tBQOe5xlKXU9K5EGF6q/rj/VU4vfdwmCWI9LBCarxPmqHYkm7sbD3P7k9g5oB4StmWZYr5pQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-shell-dollars": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/remark-lint-no-shell-dollars/-/remark-lint-no-shell-dollars-2.0.2.tgz", + "integrity": "sha512-zhkHZOuyaD3r/TUUkkVqW0OxsR9fnSrAnHIF63nfJoAAUezPOu8D1NBsni6rX8H2DqGbPYkoeWrNsTwiKP0yow==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-shortcut-reference-image": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-shortcut-reference-image/-/remark-lint-no-shortcut-reference-image-2.0.1.tgz", + "integrity": "sha512-2jcZBdnN6ecP7u87gkOVFrvICLXIU5OsdWbo160FvS/2v3qqqwF2e/n/e7D9Jd+KTq1mR1gEVVuTqkWWuh3cig==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-shortcut-reference-link": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-shortcut-reference-link/-/remark-lint-no-shortcut-reference-link-2.0.1.tgz", + "integrity": "sha512-pTZbslG412rrwwGQkIboA8wpBvcjmGFmvugIA+UQR+GfFysKtJ5OZMPGJ98/9CYWjw9Z5m0/EktplZ5TjFjqwA==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-table-indentation": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-no-table-indentation/-/remark-lint-no-table-indentation-3.0.0.tgz", + "integrity": "sha512-+l7GovI6T+3LhnTtz/SmSRyOb6Fxy6tmaObKHrwb/GAebI/4MhFS1LVo3vbiP/RpPYtyQoFbbuXI55hqBG4ibQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0", + "vfile-location": "^3.0.0" + } + }, + "remark-lint-no-tabs": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-tabs/-/remark-lint-no-tabs-2.0.1.tgz", + "integrity": "sha512-Fy5fMKNA8AsfhRtxyxBnHlGMpDDfns9VSSYv00RiC96qwRD82VhDRM3tYWZRBBxE+j71t6g47x9o/poGC7PThQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "vfile-location": "^3.0.0" + } + }, + "remark-lint-no-undefined-references": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-no-undefined-references/-/remark-lint-no-undefined-references-3.0.0.tgz", + "integrity": "sha512-0hzaJS9GuzSQVOeeNdJr/s66LRQOzp618xuOQPYWHcJdd+SCaRTyWbjMrTM/cCI5L1sYjgurp410NkIBQ32Vqg==", + "dev": true, + "requires": { + "collapse-white-space": "^1.0.4", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.1.0", + "unist-util-visit": "^2.0.0", + "vfile-location": "^3.1.0" + } + }, + "remark-lint-no-unneeded-full-reference-image": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-unneeded-full-reference-image/-/remark-lint-no-unneeded-full-reference-image-2.0.1.tgz", + "integrity": "sha512-ZqkrW6l/n1EmcGdtzBFoDygG2ehd/Wx46Id9Dagg15oLzwvbhp5mJIXArXU2qGrF82w1hfainCaZzyH/OBJtEg==", + "dev": true, + "requires": { + "collapse-white-space": "^1.0.0", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-unneeded-full-reference-link": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-unneeded-full-reference-link/-/remark-lint-no-unneeded-full-reference-link-2.0.1.tgz", + "integrity": "sha512-OcPQiG6meVpvfydzxkxPdVc8jcXdklQW4gMjY2BevLtVoaIJ+dgNBPazyYHP/0EzpVY2RftD3CZ+5hiLW2rgpA==", + "dev": true, + "requires": { + "collapse-white-space": "^1.0.0", + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-no-unused-definitions": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-no-unused-definitions/-/remark-lint-no-unused-definitions-2.0.1.tgz", + "integrity": "sha512-+BMc0BOjc364SvKYLkspmxDch8OaKPbnUGgQBvK0Bmlwy42baR4C9zhwAWBxm0SBy5Z4AyM4G4jKpLXPH40Oxg==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-ordered-list-marker-style": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-ordered-list-marker-style/-/remark-lint-ordered-list-marker-style-2.0.1.tgz", + "integrity": "sha512-Cnpw1Dn9CHn+wBjlyf4qhPciiJroFOEGmyfX008sQ8uGoPZsoBVIJx76usnHklojSONbpjEDcJCjnOvfAcWW1A==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-ordered-list-marker-value": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-ordered-list-marker-value/-/remark-lint-ordered-list-marker-value-2.0.1.tgz", + "integrity": "sha512-blt9rS7OKxZ2NW8tqojELeyNEwPhhTJGVa+YpUkdEH+KnrdcD7Nzhnj6zfLWOx6jFNZk3jpq5nvLFAPteHaNKg==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-rule-style": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-rule-style/-/remark-lint-rule-style-2.0.1.tgz", + "integrity": "sha512-hz4Ff9UdlYmtO6Czz99WJavCjqCer7Cav4VopXt+yVIikObw96G5bAuLYcVS7hvMUGqC9ZuM02/Y/iq9n8pkAg==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-strong-marker": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-strong-marker/-/remark-lint-strong-marker-2.0.1.tgz", + "integrity": "sha512-8X2IsW1jZ5FmW9PLfQjkL0OVy/J3xdXLcZrG1GTeQKQ91BrPFyEZqUM2oM6Y4S6LGtxWer+neZkPZNroZoRPBQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-table-cell-padding": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-table-cell-padding/-/remark-lint-table-cell-padding-3.0.0.tgz", + "integrity": "sha512-sEKrbyFZPZpxI39R8/r+CwUrin9YtyRwVn0SQkNQEZWZcIpylK+bvoKIldvLIXQPob+ZxklL0GPVRzotQMwuWQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-table-pipe-alignment": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-table-pipe-alignment/-/remark-lint-table-pipe-alignment-2.0.1.tgz", + "integrity": "sha512-O89U7bp0ja6uQkT2uQrNB76GaPvFabrHiUGhqEUnld21yEdyj7rgS57kn84lZNSuuvN1Oor6bDyCwWQGzzpoOQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-table-pipes": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remark-lint-table-pipes/-/remark-lint-table-pipes-3.0.0.tgz", + "integrity": "sha512-QPokSazEdl0Y8ayUV9UB0Ggn3Jos/RAQwIo0z1KDGnJlGDiF80Jc6iU9RgDNUOjlpQffSLIfSVxH5VVYF/K3uQ==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-lint-unordered-list-marker-style": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/remark-lint-unordered-list-marker-style/-/remark-lint-unordered-list-marker-style-2.0.1.tgz", + "integrity": "sha512-8KIDJNDtgbymEvl3LkrXgdxPMTOndcux3BHhNGB2lU4UnxSpYeHsxcDgirbgU6dqCAfQfvMjPvfYk19QTF9WZA==", + "dev": true, + "requires": { + "unified-lint-rule": "^1.0.0", + "unist-util-generated": "^1.1.0", + "unist-util-position": "^3.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "remark-message-control": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/remark-message-control/-/remark-message-control-6.0.0.tgz", + "integrity": "sha512-k9bt7BYc3G7YBdmeAhvd3VavrPa/XlKWR3CyHjr4sLO9xJyly8WHHT3Sp+8HPR8lEUv+/sZaffL7IjMLV0f6BA==", + "dev": true, + "requires": { + "mdast-comment-marker": "^1.0.0", + "unified-message-control": "^3.0.0" + } + }, + "remark-parse": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/remark-parse/-/remark-parse-9.0.0.tgz", + "integrity": "sha512-geKatMwSzEXKHuzBNU1z676sGcDcFoChMK38TgdHJNAYfFtsfHDQG7MoJAjs6sgYMqyLduCYWDIWZIxiPeafEw==", + "dev": true, + "requires": { + "mdast-util-from-markdown": "^0.8.0" + } + }, + "remark-preset-lint-recommended": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/remark-preset-lint-recommended/-/remark-preset-lint-recommended-5.0.0.tgz", + "integrity": "sha512-uu+Ab8JCwMMaKvvB0LOWTWtM3uAvJbKQM/oyWCEJqj7lUVNTKZS575Ro5rKM3Dx7kQjjR1iw0e99bpAYTc5xNA==", + "dev": true, + "requires": { + "remark-lint": "^8.0.0", + "remark-lint-final-newline": "^1.0.0", + "remark-lint-hard-break-spaces": "^2.0.0", + "remark-lint-list-item-bullet-indent": "^3.0.0", + "remark-lint-list-item-indent": "^2.0.0", + "remark-lint-no-auto-link-without-protocol": "^2.0.0", + "remark-lint-no-blockquote-without-marker": "^4.0.0", + "remark-lint-no-duplicate-definitions": "^2.0.0", + "remark-lint-no-heading-content-indent": "^3.0.0", + "remark-lint-no-inline-padding": "^3.0.0", + "remark-lint-no-literal-urls": "^2.0.0", + "remark-lint-no-shortcut-reference-image": "^2.0.0", + "remark-lint-no-shortcut-reference-link": "^2.0.0", + "remark-lint-no-undefined-references": "^3.0.0", + "remark-lint-no-unused-definitions": "^2.0.0", + "remark-lint-ordered-list-marker-style": "^2.0.0" + } + }, + "remark-preset-wooorm": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/remark-preset-wooorm/-/remark-preset-wooorm-8.0.1.tgz", + "integrity": "sha512-Dk1eduxMSgyfPTSWMMGhuDlbeoQbx+yjwitrVE+gYmCo1EBn+oKpsTjYbF0jKhDIEMKOfCqMJgH5gfa5UnLByA==", + "dev": true, + "requires": { + "remark-comment-config": "^6.0.0", + "remark-gfm": "^1.0.0", + "remark-github": "^10.0.0", + "remark-lint-blockquote-indentation": "^2.0.0", + "remark-lint-checkbox-character-style": "^3.0.0", + "remark-lint-checkbox-content-indent": "^3.0.0", + "remark-lint-code-block-style": "^2.0.0", + "remark-lint-definition-case": "^2.0.0", + "remark-lint-definition-spacing": "^2.0.0", + "remark-lint-emphasis-marker": "^2.0.0", + "remark-lint-fenced-code-flag": "^2.0.0", + "remark-lint-fenced-code-marker": "^2.0.0", + "remark-lint-file-extension": "^1.0.0", + "remark-lint-final-definition": "^2.0.0", + "remark-lint-first-heading-level": "^2.0.0", + "remark-lint-heading-style": "^2.0.0", + "remark-lint-link-title-style": "^2.0.0", + "remark-lint-maximum-heading-length": "^2.0.0", + "remark-lint-maximum-line-length": "^2.0.0", + "remark-lint-no-consecutive-blank-lines": "^3.0.0", + "remark-lint-no-duplicate-defined-urls": "^1.0.0", + "remark-lint-no-duplicate-definitions": "^2.0.0", + "remark-lint-no-duplicate-headings-in-section": "^2.0.0", + "remark-lint-no-emphasis-as-heading": "^2.0.0", + "remark-lint-no-empty-url": "^2.0.0", + "remark-lint-no-file-name-articles": "^1.0.0", + "remark-lint-no-file-name-consecutive-dashes": "^1.0.0", + "remark-lint-no-file-name-irregular-characters": "^1.0.0", + "remark-lint-no-file-name-mixed-case": "^1.0.0", + "remark-lint-no-file-name-outer-dashes": "^1.0.0", + "remark-lint-no-heading-content-indent": "^3.0.0", + "remark-lint-no-heading-indent": "^3.0.0", + "remark-lint-no-heading-like-paragraph": "^2.0.0", + "remark-lint-no-heading-punctuation": "^2.0.0", + "remark-lint-no-html": "^2.0.0", + "remark-lint-no-missing-blank-lines": "^2.0.0", + "remark-lint-no-multiple-toplevel-headings": "^2.0.0", + "remark-lint-no-paragraph-content-indent": "^3.0.0", + "remark-lint-no-reference-like-url": "^2.0.0", + "remark-lint-no-shell-dollars": "^2.0.0", + "remark-lint-no-table-indentation": "^3.0.0", + "remark-lint-no-tabs": "^2.0.0", + "remark-lint-no-unneeded-full-reference-image": "^2.0.0", + "remark-lint-no-unneeded-full-reference-link": "^2.0.0", + "remark-lint-ordered-list-marker-value": "^2.0.0", + "remark-lint-rule-style": "^2.0.0", + "remark-lint-strong-marker": "^2.0.0", + "remark-lint-table-cell-padding": "^3.0.0", + "remark-lint-table-pipe-alignment": "^2.0.0", + "remark-lint-table-pipes": "^3.0.0", + "remark-lint-unordered-list-marker-style": "^2.0.0", + "remark-preset-lint-recommended": "^5.0.0", + "remark-retext": "^4.0.0", + "remark-toc": "^7.0.0", + "remark-validate-links": "^10.0.0", + "retext-english": "^3.0.0", + "retext-preset-wooorm": "^3.0.0", + "unified": "^9.0.0" + } + }, + "remark-retext": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/remark-retext/-/remark-retext-4.0.0.tgz", + "integrity": "sha512-cYCchalpf25bTtfXF24ribYvqytPKq0TiEhqQDBHvVEEsApebwruPWP1cTcvTFBidmpXyqzycm+y8ng7Kmvc8Q==", + "dev": true, + "requires": { + "mdast-util-to-nlcst": "^4.0.0" + } + }, + "remark-stringify": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/remark-stringify/-/remark-stringify-9.0.1.tgz", + "integrity": "sha512-mWmNg3ZtESvZS8fv5PTvaPckdL4iNlCHTt8/e/8oN08nArHRHjNZMKzA/YW3+p7/lYqIw4nx1XsjCBo/AxNChg==", + "dev": true, + "requires": { + "mdast-util-to-markdown": "^0.6.0" + } + }, + "remark-toc": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/remark-toc/-/remark-toc-7.2.0.tgz", + "integrity": "sha512-ppHepvpbg7j5kPFmU5rzDC4k2GTcPDvWcxXyr/7BZzO1cBSPk0stKtEJdsgAyw2WHKPGxadcHIZRjb2/sHxjkg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.3", + "mdast-util-toc": "^5.0.0" + } + }, + "remark-validate-links": { + "version": "10.0.4", + "resolved": "https://registry.npmjs.org/remark-validate-links/-/remark-validate-links-10.0.4.tgz", + "integrity": "sha512-oNGRcsoQkL35WoZKLMMBugDwvHfyu0JPA5vSYkEcvR6YBsFKBo4RedpecuokTK1wgD9l01rPxaQ9dPmRQYFhyg==", + "dev": true, + "requires": { + "github-slugger": "^1.0.0", + "hosted-git-info": "^3.0.0", + "mdast-util-to-string": "^1.0.0", + "propose": "0.0.5", + "to-vfile": "^6.0.0", + "trough": "^1.0.0", + "unist-util-visit": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-1.1.0.tgz", + "integrity": "sha512-jVU0Nr2B9X3MU4tSK7JP1CMkSvOj7X5l/GboG1tKRw52lLF1x2Ju92Ms9tNetCcbfX3hzlM73zYo2NKkWSfF/A==", + "dev": true + } + } + }, + "repeat-element": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.4.tgz", + "integrity": "sha512-LFiNfRcSu7KK3evMyYOuCzv3L10TW7yC1G2/+StMjK8Y6Vqd2MG7r/Qjw4ghtuCOjFvlnms/iMmLqpvW/ES/WQ==", + "dev": true + }, + "repeat-string": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", + "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=", + "dev": true + }, + "require-directory": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", + "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=", + "dev": true + }, + "require-from-string": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", + "dev": true + }, + "reserved-words": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/reserved-words/-/reserved-words-0.1.2.tgz", + "integrity": "sha1-AKCUD5jNUBrqqsMWQR2a3FKzGrE=", + "dev": true + }, + "resolve": { + "version": "2.0.0-next.3", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.3.tgz", + "integrity": "sha512-W8LucSynKUIDu9ylraa7ueVZ7hc0uAgJBxVsQSKOXOyle8a93qXhcz+XAXZ8bIq2d6i4Ehddn6Evt+0/UwKk6Q==", + "dev": true, + "requires": { + "is-core-module": "^2.2.0", + "path-parse": "^1.0.6" + } + }, + "resolve-cwd": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-3.0.0.tgz", + "integrity": "sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==", + "dev": true, + "requires": { + "resolve-from": "^5.0.0" + } + }, + "resolve-from": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", + "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", + "dev": true + }, + "resolve-url": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", + "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", + "dev": true + }, + "responselike": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", + "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", + "dev": true, + "requires": { + "lowercase-keys": "^1.0.0" + } + }, + "resumer": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/resumer/-/resumer-0.0.0.tgz", + "integrity": "sha1-8ej0YeQGS6Oegq883CqMiT0HZ1k=", + "dev": true, + "requires": { + "through": "~2.3.4" + } + }, + "ret": { + "version": "0.1.15", + "resolved": "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz", + "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==", + "dev": true + }, + "retext-contractions": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/retext-contractions/-/retext-contractions-4.0.0.tgz", + "integrity": "sha512-0T+QE+mFBfYiZHqD+86yM19PjEN3w6Z2boTWpYZb4L6JyzMN4luHUzNHwaL8HtkbxHEe0j8yqLrYnTD+qoOEyw==", + "dev": true, + "requires": { + "nlcst-is-literal": "^1.0.0", + "nlcst-to-string": "^2.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "retext-diacritics": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/retext-diacritics/-/retext-diacritics-3.0.0.tgz", + "integrity": "sha512-QayeY2hpQ1UEsPlderfl6k90sA+mSxnlOMqiA3N5teDPyKo3REwkm+o/fClCxjLSm6NJgqNthOZjjSBUgQvSSw==", + "dev": true, + "requires": { + "match-casing": "^1.0.0", + "nlcst-search": "^2.0.0", + "nlcst-to-string": "^2.0.0", + "quotation": "^1.0.1", + "unist-util-position": "^3.0.0" + } + }, + "retext-english": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/retext-english/-/retext-english-3.0.4.tgz", + "integrity": "sha512-yr1PgaBDde+25aJXrnt3p1jvT8FVLVat2Bx8XeAWX13KXo8OT+3nWGU3HWxM4YFJvmfqvJYJZG2d7xxaO774gw==", + "dev": true, + "requires": { + "parse-english": "^4.0.0", + "unherit": "^1.0.4" + } + }, + "retext-indefinite-article": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/retext-indefinite-article/-/retext-indefinite-article-2.0.3.tgz", + "integrity": "sha512-96D1Vk4l7FIf6egKoFVlml32kMmQbKi6FSxQ7YPDsU+F+JnJeLZFCJh9GBQ/LkBKpcyi2izGqYjDgj4DTBz73A==", + "dev": true, + "requires": { + "format": "^0.2.2", + "nlcst-to-string": "^2.0.0", + "number-to-words": "^1.2.3", + "unist-util-is": "^4.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "retext-preset-wooorm": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/retext-preset-wooorm/-/retext-preset-wooorm-3.0.0.tgz", + "integrity": "sha512-mzxzW+V0iF4ygunqoukVBtjpgNX2cB7eCZ7IF5GNQA3QExqJF40bVQeCkW3fI/c1vC3OitNlpjz3R66i58sslA==", + "dev": true, + "requires": { + "retext-contractions": "^4.0.0", + "retext-diacritics": "^3.0.0", + "retext-indefinite-article": "^2.0.0", + "retext-quotes": "^4.0.0", + "retext-redundant-acronyms": "^3.0.0", + "retext-repeated-words": "^3.0.0", + "retext-sentence-spacing": "^4.0.0" + } + }, + "retext-quotes": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/retext-quotes/-/retext-quotes-4.0.0.tgz", + "integrity": "sha512-YtHJ3Yw0yk8sGp0FMAVWe2a/q0DaHjSKfrAYkO5rZXLofGYYG+LCoqzqlX0tbfae1ImlsqhsLVCuZ0fkUO087g==", + "dev": true, + "requires": { + "nlcst-to-string": "^2.0.0", + "unist-util-is": "^4.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "retext-redundant-acronyms": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/retext-redundant-acronyms/-/retext-redundant-acronyms-3.0.0.tgz", + "integrity": "sha512-pu5um9ObH+j/AguHPVm+u23DK43zey2Jim0dmzccczvilbIRiYh7ZQMSOIuLNpE+7jNP0quX3oe/ommrLlwECQ==", + "dev": true, + "requires": { + "nlcst-normalize": "^2.0.0", + "nlcst-search": "^2.0.0", + "nlcst-to-string": "^2.0.0", + "pluralize": "^8.0.0", + "quotation": "^1.0.0", + "unist-util-find-after": "^3.0.0", + "unist-util-position": "^3.0.0" + } + }, + "retext-repeated-words": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/retext-repeated-words/-/retext-repeated-words-3.0.0.tgz", + "integrity": "sha512-c9awbCxn3h+SVVYwEeJA+rcWWFiOvxrcD8MVFpyVpWu0q1cXG7NIyWclEzXDV12SkqKgR/vmBJh3tIJCfxmDAA==", + "dev": true, + "requires": { + "nlcst-to-string": "^2.0.0", + "unist-util-is": "^4.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "retext-sentence-spacing": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/retext-sentence-spacing/-/retext-sentence-spacing-4.0.0.tgz", + "integrity": "sha512-CKdHlVBbZDkdjxZ1IctBQ1u4/sHQraGoTuI8qvB2C4jSaM0MEY0hxpMdVjnznWAWm4VOqwSXZDkR71Pv6Yw0TA==", + "dev": true, + "requires": { + "nlcst-to-string": "^2.0.0", + "unist-util-is": "^4.0.0", + "unist-util-visit": "^2.0.0" + } + }, + "reusify": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", + "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", + "dev": true + }, + "rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "requires": { + "glob": "^7.1.3" + } + }, + "run-parallel": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", + "dev": true, + "requires": { + "queue-microtask": "^1.2.2" + } + }, + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + }, + "safe-regex": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-2.1.1.tgz", + "integrity": "sha512-rx+x8AMzKb5Q5lQ95Zoi6ZbJqwCLkqi3XuJXp5P3rT8OEc6sZCJG5AE5dU3lsgRr/F4Bs31jSlVN+j5KrsGu9A==", + "dev": true, + "requires": { + "regexp-tree": "~0.1.1" + } + }, + "semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true + }, + "semver-diff": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-3.1.1.tgz", + "integrity": "sha512-GX0Ix/CJcHyB8c4ykpHGIAvLyOwOobtM/8d+TQkAd81/bEjgPHrfba41Vpesr7jX/t8Uh+R3EX9eAS5be+jQYg==", + "dev": true, + "requires": { + "semver": "^6.3.0" + } + }, + "set-value": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.1.tgz", + "integrity": "sha512-JxHc1weCN68wRY0fhCoXpyK55m/XPHafOmK4UWD7m2CI14GMcFypt4w/0+NV5f/ZMby2F6S2wwA7fgynh9gWSw==", + "dev": true, + "requires": { + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.3", + "split-string": "^3.0.1" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, + "shebang-command": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", + "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", + "dev": true, + "requires": { + "shebang-regex": "^3.0.0" + } + }, + "shebang-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", + "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", + "dev": true + }, + "side-channel": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", + "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "dev": true, + "requires": { + "call-bind": "^1.0.0", + "get-intrinsic": "^1.0.2", + "object-inspect": "^1.9.0" + } + }, + "signal-exit": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.3.tgz", + "integrity": "sha512-VUJ49FC8U1OxwZLxIbTTrDvLnf/6TDgxZcK8wxR8zs13xpx7xbG60ndBlhNrFi2EMuFRoeDoJO7wthSLq42EjA==", + "dev": true + }, + "slash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", + "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", + "dev": true + }, + "slice-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-4.0.0.tgz", + "integrity": "sha512-qMCMfhY040cVHT43K9BFygqYbUPFZKHOg7K73mtTWJRb8pyP3fzf4Ixd5SzdEJQ6MRUg/WBnOLxghZtKKurENQ==", + "dev": true, + "requires": { + "ansi-styles": "^4.0.0", + "astral-regex": "^2.0.0", + "is-fullwidth-code-point": "^3.0.0" + } + }, + "sliced": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/sliced/-/sliced-1.0.1.tgz", + "integrity": "sha1-CzpmK10Ewxd7GSa+qCsD+Dei70E=", + "dev": true + }, + "snapdragon": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", + "integrity": "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==", + "dev": true, + "requires": { + "base": "^0.11.1", + "debug": "^2.2.0", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "map-cache": "^0.2.2", + "source-map": "^0.5.6", + "source-map-resolve": "^0.5.0", + "use": "^3.1.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", + "dev": true + }, + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", + "dev": true + } + } + }, + "snapdragon-node": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz", + "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", + "dev": true, + "requires": { + "define-property": "^1.0.0", + "isobject": "^3.0.0", + "snapdragon-util": "^3.0.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, + "snapdragon-util": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz", + "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", + "dev": true, + "requires": { + "kind-of": "^3.2.0" + }, + "dependencies": { + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true + }, + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "source-map": { + "version": "0.7.3", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.3.tgz", + "integrity": "sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ==", + "dev": true + }, + "source-map-resolve": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.3.tgz", + "integrity": "sha512-Htz+RnsXWk5+P2slx5Jh3Q66vhQj1Cllm0zvnaY98+NFx+Dv2CF/f5O/t8x+KaNdrdIAsruNzoh/KpialbqAnw==", + "dev": true, + "requires": { + "atob": "^2.1.2", + "decode-uri-component": "^0.2.0", + "resolve-url": "^0.2.1", + "source-map-url": "^0.4.0", + "urix": "^0.1.0" + } + }, + "source-map-url": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.1.tgz", + "integrity": "sha512-cPiFOTLUKvJFIg4SKVScy4ilPPW6rFgMgfuZJPNoDuMs3nC1HbMUycBoJw77xFIp6z1UJQJOfx6C9GMH80DiTw==", + "dev": true + }, + "spdx-correct": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.1.tgz", + "integrity": "sha512-cOYcUWwhCuHCXi49RhFRCyJEK3iPj1Ziz9DpViV3tbZOwXD49QzIN3MpOLJNxh2qwq2lJJZaKMVw9qNi4jTC0w==", + "dev": true, + "requires": { + "spdx-expression-parse": "^3.0.0", + "spdx-license-ids": "^3.0.0" + } + }, + "spdx-exceptions": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.3.0.tgz", + "integrity": "sha512-/tTrYOC7PPI1nUAgx34hUpqXuyJG+DTHJTnIULG4rDygi4xu/tfgmq1e1cIRwRzwZgo4NLySi+ricLkZkw4i5A==", + "dev": true + }, + "spdx-expression-parse": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.1.tgz", + "integrity": "sha512-cbqHunsQWnJNE6KhVSMsMeH5H/L9EpymbzqTQ3uLwNCLZ1Q481oWaofqH7nO6V07xlXwY6PhQdQ2IedWx/ZK4Q==", + "dev": true, + "requires": { + "spdx-exceptions": "^2.1.0", + "spdx-license-ids": "^3.0.0" + } + }, + "spdx-license-ids": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.10.tgz", + "integrity": "sha512-oie3/+gKf7QtpitB0LYLETe+k8SifzsX4KixvpOsbI6S0kRiRQ5MKOio8eMSAKQ17N06+wdEOXRiId+zOxo0hA==", + "dev": true + }, + "split-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", + "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", + "dev": true, + "requires": { + "extend-shallow": "^3.0.0" + } + }, + "sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", + "dev": true + }, + "static-extend": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz", + "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", + "dev": true, + "requires": { + "define-property": "^0.2.5", + "object-copy": "^0.1.0" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + } + } + }, + "string-width": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.2.tgz", + "integrity": "sha512-XBJbT3N4JhVumXE0eoLU9DCjcaF92KLNqTmFCnG1pf8duUxFGwtP6AD6nkjw9a3IdiRtL3E2w3JDiE/xi3vOeA==", + "dev": true, + "requires": { + "emoji-regex": "^8.0.0", + "is-fullwidth-code-point": "^3.0.0", + "strip-ansi": "^6.0.0" + } + }, + "string.prototype.trim": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.2.4.tgz", + "integrity": "sha512-hWCk/iqf7lp0/AgTF7/ddO1IWtSNPASjlzCicV5irAVdE1grjsneK26YG6xACMBEdCvO8fUST0UzDMh/2Qy+9Q==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3", + "es-abstract": "^1.18.0-next.2" + } + }, + "string.prototype.trimend": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.4.tgz", + "integrity": "sha512-y9xCjw1P23Awk8EvTpcyL2NIr1j7wJ39f+k6lvRnSMz+mz9CGz9NYPelDk42kOz6+ql8xjfK8oYzy3jAP5QU5A==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3" + } + }, + "string.prototype.trimstart": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.4.tgz", + "integrity": "sha512-jh6e984OBfvxS50tdY2nRZnoC5/mLFKOREQfw8t5yytkoUsJRNxvI/E39qu1sD0OtWI3OC0XgKSmcWwziwYuZw==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3" + } + }, + "string_decoder": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "dev": true, + "requires": { + "safe-buffer": "~5.2.0" + }, + "dependencies": { + "safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "dev": true + } + } + }, + "strip-ansi": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.0.tgz", + "integrity": "sha512-AuvKTrTfQNYNIctbR1K/YGTR1756GycPsg7b9bdV9Duqur4gv6aKqHXah67Z8ImS7WEz5QVcOtlfW2rZEugt6w==", + "dev": true, + "requires": { + "ansi-regex": "^5.0.0" + } + }, + "strip-bom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", + "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", + "dev": true + }, + "strip-final-newline": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-2.0.0.tgz", + "integrity": "sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==", + "dev": true + }, + "strip-indent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-indent/-/strip-indent-3.0.0.tgz", + "integrity": "sha512-laJTa3Jb+VQpaC6DseHhF7dXVqHTfJPCRDaEbid/drOhgitgYku/letMUqOXFoWV0zIIUbjpdH2t+tYj4bQMRQ==", + "dev": true, + "requires": { + "min-indent": "^1.0.0" + } + }, + "strip-json-comments": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", + "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", + "dev": true + }, + "supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "requires": { + "has-flag": "^4.0.0" + } + }, + "supports-hyperlinks": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/supports-hyperlinks/-/supports-hyperlinks-2.2.0.tgz", + "integrity": "sha512-6sXEzV5+I5j8Bmq9/vUphGRM/RJNT9SCURJLjwfOg51heRtguGWDzcaBlgAzKhQa0EVNpPEKzQuBwZ8S8WaCeQ==", + "dev": true, + "requires": { + "has-flag": "^4.0.0", + "supports-color": "^7.0.0" + } + }, + "table": { + "version": "6.7.1", + "resolved": "https://registry.npmjs.org/table/-/table-6.7.1.tgz", + "integrity": "sha512-ZGum47Yi6KOOFDE8m223td53ath2enHcYLgOCjGr5ngu8bdIARQk6mN/wRMv4yMRcHnCSnHbCEha4sobQx5yWg==", + "dev": true, + "requires": { + "ajv": "^8.0.1", + "lodash.clonedeep": "^4.5.0", + "lodash.truncate": "^4.4.2", + "slice-ansi": "^4.0.0", + "string-width": "^4.2.0", + "strip-ansi": "^6.0.0" + }, + "dependencies": { + "ajv": { + "version": "8.6.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.6.2.tgz", + "integrity": "sha512-9807RlWAgT564wT+DjeyU5OFMPjmzxVobvDFmNAhY+5zD6A2ly3jDp6sgnfyDtlIQ+7H97oc/DGCzzfu9rjw9w==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2", + "uri-js": "^4.2.2" + } + }, + "json-schema-traverse": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", + "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", + "dev": true + } + } + }, + "tapable": { + "version": "0.1.10", + "resolved": "https://registry.npmjs.org/tapable/-/tapable-0.1.10.tgz", + "integrity": "sha1-KcNXB8K3DlDQdIK10gLo7URtr9Q=", + "dev": true + }, + "tape": { + "version": "5.3.1", + "resolved": "https://registry.npmjs.org/tape/-/tape-5.3.1.tgz", + "integrity": "sha512-Mj3h+/dgfI2xct4kTpzqZaRxhhglXcMg//xGTbB0AQisfiOYa6ZBNQIgv46xi1MqbgthuNLSS1SAySDZsb7MMA==", + "dev": true, + "requires": { + "call-bind": "^1.0.2", + "deep-equal": "^2.0.5", + "defined": "^1.0.0", + "dotignore": "^0.1.2", + "for-each": "^0.3.3", + "get-package-type": "^0.1.0", + "glob": "^7.1.7", + "has": "^1.0.3", + "has-dynamic-import": "^2.0.0", + "inherits": "^2.0.4", + "is-regex": "^1.1.4", + "minimist": "^1.2.5", + "object-inspect": "^1.11.0", + "object-is": "^1.1.5", + "object.assign": "^4.1.2", + "resolve": "^2.0.0-next.3", + "resumer": "^0.0.0", + "string.prototype.trim": "^1.2.4", + "through": "^2.3.8" + } + }, + "test-exclude": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/test-exclude/-/test-exclude-6.0.0.tgz", + "integrity": "sha512-cAGWPIyOHU6zlmg88jwm7VRyXnMN7iV68OGAbYDk/Mh/xC/pzVPlQtY6ngoIH/5/tciuhGfvESU8GrHrcxD56w==", + "dev": true, + "requires": { + "@istanbuljs/schema": "^0.1.2", + "glob": "^7.1.4", + "minimatch": "^3.0.4" + } + }, + "text-table": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", + "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", + "dev": true + }, + "through": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", + "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", + "dev": true + }, + "to-absolute-glob": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/to-absolute-glob/-/to-absolute-glob-2.0.2.tgz", + "integrity": "sha1-GGX0PZ50sIItufFFt4z/fQ98hJs=", + "dev": true, + "requires": { + "is-absolute": "^1.0.0", + "is-negated-glob": "^1.0.0" + } + }, + "to-fast-properties": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-2.0.0.tgz", + "integrity": "sha1-3F5pjL0HkmW8c+A3doGk5Og/YW4=", + "dev": true + }, + "to-object-path": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", + "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", + "dev": true, + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true + }, + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "to-readable-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/to-readable-stream/-/to-readable-stream-1.0.0.tgz", + "integrity": "sha512-Iq25XBt6zD5npPhlLVXGFN3/gyR2/qODcKNNyTMd4vbm39HUaOiAM4PMq0eMVC/Tkxz+Zjdsc55g9yyz+Yq00Q==", + "dev": true + }, + "to-regex": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/to-regex/-/to-regex-3.0.2.tgz", + "integrity": "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==", + "dev": true, + "requires": { + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "regex-not": "^1.0.2", + "safe-regex": "^1.1.0" + }, + "dependencies": { + "safe-regex": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz", + "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", + "dev": true, + "requires": { + "ret": "~0.1.10" + } + } + } + }, + "to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", + "dev": true, + "requires": { + "is-number": "^7.0.0" + } + }, + "to-vfile": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/to-vfile/-/to-vfile-6.1.0.tgz", + "integrity": "sha512-BxX8EkCxOAZe+D/ToHdDsJcVI4HqQfmw0tCkp31zf3dNP/XWIAjU4CmeuSwsSoOzOTqHPOL0KUzyZqJplkD0Qw==", + "dev": true, + "requires": { + "is-buffer": "^2.0.0", + "vfile": "^4.0.0" + } + }, + "trim-newlines": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/trim-newlines/-/trim-newlines-3.0.1.tgz", + "integrity": "sha512-c1PTsA3tYrIsLGkJkzHF+w9F2EyxfXGo4UyJc4pFL++FMjnq0HJS69T3M7d//gKrFKwy429bouPescbjecU+Zw==", + "dev": true + }, + "trough": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/trough/-/trough-1.0.5.tgz", + "integrity": "sha512-rvuRbTarPXmMb79SmzEp8aqXNKcK+y0XaB298IXueQ8I2PsrATcPBCSPyK/dDNa2iWOhKlfNnOjdAOTBU/nkFA==", + "dev": true + }, + "tsconfig-paths": { + "version": "3.10.1", + "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.10.1.tgz", + "integrity": "sha512-rETidPDgCpltxF7MjBZlAFPUHv5aHH2MymyPvh+vEyWAED4Eb/WeMbsnD/JDr4OKPOA1TssDHgIcpTN5Kh0p6Q==", + "dev": true, + "requires": { + "json5": "^2.2.0", + "minimist": "^1.2.0", + "strip-bom": "^3.0.0" + } + }, + "tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "tsutils": { + "version": "3.21.0", + "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-3.21.0.tgz", + "integrity": "sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==", + "dev": true, + "requires": { + "tslib": "^1.8.1" + } + }, + "type-check": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", + "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", + "dev": true, + "requires": { + "prelude-ls": "^1.2.1" + } + }, + "type-fest": { + "version": "0.20.2", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", + "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", + "dev": true + }, + "typedarray": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", + "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=", + "dev": true + }, + "typedarray-to-buffer": { + "version": "3.1.5", + "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", + "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", + "dev": true, + "requires": { + "is-typedarray": "^1.0.0" + } + }, + "typescript": { + "version": "4.3.5", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.3.5.tgz", + "integrity": "sha512-DqQgihaQ9cUrskJo9kIyW/+g0Vxsk8cDtZ52a3NGh0YNTfpUSArXSohyUGnvbPazEPLu398C0UxmKSOrPumUzA==", + "dev": true + }, + "unbox-primitive": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.1.tgz", + "integrity": "sha512-tZU/3NqK3dA5gpE1KtyiJUrEB0lxnGkMFHptJ7q6ewdZ8s12QrODwNbhIJStmJkd1QDXa1NRA8aF2A1zk/Ypyw==", + "dev": true, + "requires": { + "function-bind": "^1.1.1", + "has-bigints": "^1.0.1", + "has-symbols": "^1.0.2", + "which-boxed-primitive": "^1.0.2" + } + }, + "unc-path-regex": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/unc-path-regex/-/unc-path-regex-0.1.2.tgz", + "integrity": "sha1-5z3T17DXxe2G+6xrCufYxqadUPo=", + "dev": true + }, + "unherit": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/unherit/-/unherit-1.1.3.tgz", + "integrity": "sha512-Ft16BJcnapDKp0+J/rqFC3Rrk6Y/Ng4nzsC028k2jdDII/rdZ7Wd3pPT/6+vIIxRagwRc9K0IUX0Ra4fKvw+WQ==", + "dev": true, + "requires": { + "inherits": "^2.0.0", + "xtend": "^4.0.0" + } + }, + "unified": { + "version": "9.2.2", + "resolved": "https://registry.npmjs.org/unified/-/unified-9.2.2.tgz", + "integrity": "sha512-Sg7j110mtefBD+qunSLO1lqOEKdrwBFBrR6Qd8f4uwkhWNlbkaqwHse6e7QvD3AP/MNoJdEDLaf8OxYyoWgorQ==", + "dev": true, + "requires": { + "bail": "^1.0.0", + "extend": "^3.0.0", + "is-buffer": "^2.0.0", + "is-plain-obj": "^2.0.0", + "trough": "^1.0.0", + "vfile": "^4.0.0" + } + }, + "unified-args": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/unified-args/-/unified-args-8.1.0.tgz", + "integrity": "sha512-t1HPS1cQPsVvt/6EtyWIbQGurza5684WGRigNghZRvzIdHm3LPgMdXPyGx0npORKzdiy5+urkF0rF5SXM8lBuQ==", + "dev": true, + "requires": { + "camelcase": "^5.0.0", + "chalk": "^3.0.0", + "chokidar": "^3.0.0", + "fault": "^1.0.2", + "json5": "^2.0.0", + "minimist": "^1.2.0", + "text-table": "^0.2.0", + "unified-engine": "^8.0.0" + } + }, + "unified-engine": { + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/unified-engine/-/unified-engine-8.2.0.tgz", + "integrity": "sha512-ZlMm62ejrf+tJHdyOjQfljszngQjRor95q2XZMGk6rpJUYi7ZIHY/EXEhOcj9PZkMKKdLIM+dqL4s0ceyk9wbA==", + "dev": true, + "requires": { + "concat-stream": "^2.0.0", + "debug": "^4.0.0", + "fault": "^1.0.0", + "figures": "^3.0.0", + "glob": "^7.0.3", + "ignore": "^5.0.0", + "is-buffer": "^2.0.0", + "is-empty": "^1.0.0", + "is-plain-obj": "^2.0.0", + "js-yaml": "^3.6.1", + "load-plugin": "^3.0.0", + "parse-json": "^5.0.0", + "to-vfile": "^6.0.0", + "trough": "^1.0.0", + "unist-util-inspect": "^5.0.0", + "vfile-reporter": "^6.0.0", + "vfile-statistics": "^1.1.0" + } + }, + "unified-lint-rule": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/unified-lint-rule/-/unified-lint-rule-1.0.6.tgz", + "integrity": "sha512-YPK15YBFwnsVorDFG/u0cVVQN5G2a3V8zv5/N6KN3TCG+ajKtaALcy7u14DCSrJI+gZeyYquFL9cioJXOGXSvg==", + "dev": true, + "requires": { + "wrapped": "^1.0.1" + } + }, + "unified-message-control": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/unified-message-control/-/unified-message-control-3.0.3.tgz", + "integrity": "sha512-oY5z2n8ugjpNHXOmcgrw0pQeJzavHS0VjPBP21tOcm7rc2C+5Q+kW9j5+gqtf8vfW/8sabbsK5+P+9QPwwEHDA==", + "dev": true, + "requires": { + "unist-util-visit": "^2.0.0", + "vfile-location": "^3.0.0" + } + }, + "union-value": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.1.tgz", + "integrity": "sha512-tJfXmxMeWYnczCVs7XAEvIV7ieppALdyepWMkHkwciRpZraG/xwT+s2JN8+pr1+8jCRf80FFzvr+MpQeeoF4Xg==", + "dev": true, + "requires": { + "arr-union": "^3.1.0", + "get-value": "^2.0.6", + "is-extendable": "^0.1.1", + "set-value": "^2.0.1" + } + }, + "unique-string": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-2.0.0.tgz", + "integrity": "sha512-uNaeirEPvpZWSgzwsPGtU2zVSTrn/8L5q/IexZmH0eH6SA73CmAA5U4GwORTxQAZs95TAXLNqeLoPPNO5gZfWg==", + "dev": true, + "requires": { + "crypto-random-string": "^2.0.0" + } + }, + "unist-util-find-after": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/unist-util-find-after/-/unist-util-find-after-3.0.0.tgz", + "integrity": "sha512-ojlBqfsBftYXExNu3+hHLfJQ/X1jYY/9vdm4yZWjIbf0VuWF6CRufci1ZyoD/wV2TYMKxXUoNuoqwy+CkgzAiQ==", + "dev": true, + "requires": { + "unist-util-is": "^4.0.0" + } + }, + "unist-util-generated": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/unist-util-generated/-/unist-util-generated-1.1.6.tgz", + "integrity": "sha512-cln2Mm1/CZzN5ttGK7vkoGw+RZ8VcUH6BtGbq98DDtRGquAAOXig1mrBQYelOwMXYS8rK+vZDyyojSjp7JX+Lg==", + "dev": true + }, + "unist-util-inspect": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/unist-util-inspect/-/unist-util-inspect-5.0.1.tgz", + "integrity": "sha512-fPNWewS593JSmg49HbnE86BJKuBi1/nMWhDSccBvbARfxezEuJV85EaARR9/VplveiwCoLm2kWq+DhP8TBaDpw==", + "dev": true, + "requires": { + "is-empty": "^1.0.0" + } + }, + "unist-util-is": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-4.1.0.tgz", + "integrity": "sha512-ZOQSsnce92GrxSqlnEEseX0gi7GH9zTJZ0p9dtu87WRb/37mMPO2Ilx1s/t9vBHrFhbgweUwb+t7cIn5dxPhZg==", + "dev": true + }, + "unist-util-modify-children": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/unist-util-modify-children/-/unist-util-modify-children-2.0.0.tgz", + "integrity": "sha512-HGrj7JQo9DwZt8XFsX8UD4gGqOsIlCih9opG6Y+N11XqkBGKzHo8cvDi+MfQQgiZ7zXRUiQREYHhjOBHERTMdg==", + "dev": true, + "requires": { + "array-iterate": "^1.0.0" + } + }, + "unist-util-position": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/unist-util-position/-/unist-util-position-3.1.0.tgz", + "integrity": "sha512-w+PkwCbYSFw8vpgWD0v7zRCl1FpY3fjDSQ3/N/wNd9Ffa4gPi8+4keqt99N3XW6F99t/mUzp2xAhNmfKWp95QA==", + "dev": true + }, + "unist-util-stringify-position": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-2.0.3.tgz", + "integrity": "sha512-3faScn5I+hy9VleOq/qNbAd6pAx7iH5jYBMS9I1HgQVijz/4mv5Bvw5iw1sC/90CODiKo81G/ps8AJrISn687g==", + "dev": true, + "requires": { + "@types/unist": "^2.0.2" + } + }, + "unist-util-visit": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-2.0.3.tgz", + "integrity": "sha512-iJ4/RczbJMkD0712mGktuGpm/U4By4FfDonL7N/9tATGIF4imikjOuagyMY53tnZq3NP6BcmlrHhEKAfGWjh7Q==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "unist-util-is": "^4.0.0", + "unist-util-visit-parents": "^3.0.0" + } + }, + "unist-util-visit-children": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/unist-util-visit-children/-/unist-util-visit-children-1.1.4.tgz", + "integrity": "sha512-sA/nXwYRCQVRwZU2/tQWUqJ9JSFM1X3x7JIOsIgSzrFHcfVt6NkzDtKzyxg2cZWkCwGF9CO8x4QNZRJRMK8FeQ==", + "dev": true + }, + "unist-util-visit-parents": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-3.1.1.tgz", + "integrity": "sha512-1KROIZWo6bcMrZEwiH2UrXDyalAa0uqzWCxCJj6lPOvTve2WkfgCytoDTPaMnodXh1WrXOq0haVYHj99ynJlsg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "unist-util-is": "^4.0.0" + } + }, + "universalify": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.0.tgz", + "integrity": "sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ==", + "dev": true + }, + "unset-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", + "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", + "dev": true, + "requires": { + "has-value": "^0.3.1", + "isobject": "^3.0.0" + }, + "dependencies": { + "has-value": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz", + "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", + "dev": true, + "requires": { + "get-value": "^2.0.3", + "has-values": "^0.1.4", + "isobject": "^2.0.0" + }, + "dependencies": { + "isobject": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", + "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", + "dev": true, + "requires": { + "isarray": "1.0.0" + } + } + } + }, + "has-values": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz", + "integrity": "sha1-bWHeldkd/Km5oCCJrThL/49it3E=", + "dev": true + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + } + } + }, + "update-notifier": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-5.1.0.tgz", + "integrity": "sha512-ItnICHbeMh9GqUy31hFPrD1kcuZ3rpxDZbf4KUDavXwS0bW5m7SLbDQpGX3UYr072cbrF5hFUs3r5tUsPwjfHw==", + "dev": true, + "requires": { + "boxen": "^5.0.0", + "chalk": "^4.1.0", + "configstore": "^5.0.1", + "has-yarn": "^2.1.0", + "import-lazy": "^2.1.0", + "is-ci": "^2.0.0", + "is-installed-globally": "^0.4.0", + "is-npm": "^5.0.0", + "is-yarn-global": "^0.3.0", + "latest-version": "^5.1.0", + "pupa": "^2.1.1", + "semver": "^7.3.4", + "semver-diff": "^3.1.1", + "xdg-basedir": "^4.0.0" + }, + "dependencies": { + "chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + }, + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + } + } + }, + "uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dev": true, + "requires": { + "punycode": "^2.1.0" + } + }, + "urix": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", + "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=", + "dev": true + }, + "url-parse-lax": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", + "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", + "dev": true, + "requires": { + "prepend-http": "^2.0.0" + } + }, + "use": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/use/-/use-3.1.1.tgz", + "integrity": "sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==", + "dev": true + }, + "util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", + "dev": true + }, + "v8-compile-cache": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", + "integrity": "sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==", + "dev": true + }, + "v8-to-istanbul": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/v8-to-istanbul/-/v8-to-istanbul-8.0.0.tgz", + "integrity": "sha512-LkmXi8UUNxnCC+JlH7/fsfsKr5AU110l+SYGJimWNkWhxbN5EyeOtm1MJ0hhvqMMOhGwBj1Fp70Yv9i+hX0QAg==", + "dev": true, + "requires": { + "@types/istanbul-lib-coverage": "^2.0.1", + "convert-source-map": "^1.6.0", + "source-map": "^0.7.3" + } + }, + "validate-npm-package-license": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz", + "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", + "dev": true, + "requires": { + "spdx-correct": "^3.0.0", + "spdx-expression-parse": "^3.0.0" + } + }, + "vfile": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/vfile/-/vfile-4.2.1.tgz", + "integrity": "sha512-O6AE4OskCG5S1emQ/4gl8zK586RqA3srz3nfK/Viy0UPToBc5Trp9BVFb1u0CjsKrAWwnpr4ifM/KBXPWwJbCA==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "is-buffer": "^2.0.0", + "unist-util-stringify-position": "^2.0.0", + "vfile-message": "^2.0.0" + } + }, + "vfile-location": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/vfile-location/-/vfile-location-3.2.0.tgz", + "integrity": "sha512-aLEIZKv/oxuCDZ8lkJGhuhztf/BW4M+iHdCwglA/eWc+vtuRFJj8EtgceYFX4LRjOhCAAiNHsKGssC6onJ+jbA==", + "dev": true + }, + "vfile-message": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-2.0.4.tgz", + "integrity": "sha512-DjssxRGkMvifUOJre00juHoP9DPWuzjxKuMDrhNbk2TdaYYBNMStsNhEOt3idrtI12VQYM/1+iM0KOzXi4pxwQ==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "unist-util-stringify-position": "^2.0.0" + } + }, + "vfile-reporter": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/vfile-reporter/-/vfile-reporter-6.0.2.tgz", + "integrity": "sha512-GN2bH2gs4eLnw/4jPSgfBjo+XCuvnX9elHICJZjVD4+NM0nsUrMTvdjGY5Sc/XG69XVTgLwj7hknQVc6M9FukA==", + "dev": true, + "requires": { + "repeat-string": "^1.5.0", + "string-width": "^4.0.0", + "supports-color": "^6.0.0", + "unist-util-stringify-position": "^2.0.0", + "vfile-sort": "^2.1.2", + "vfile-statistics": "^1.1.0" + }, + "dependencies": { + "has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true + }, + "supports-color": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-6.1.0.tgz", + "integrity": "sha512-qe1jfm1Mg7Nq/NSh6XE24gPXROEVsWHxC1LIx//XNlD9iw7YZQGjZNjYN7xGaEG6iKdA8EtNFW6R0gjnVXp+wQ==", + "dev": true, + "requires": { + "has-flag": "^3.0.0" + } + } + } + }, + "vfile-sort": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/vfile-sort/-/vfile-sort-2.2.2.tgz", + "integrity": "sha512-tAyUqD2R1l/7Rn7ixdGkhXLD3zsg+XLAeUDUhXearjfIcpL1Hcsj5hHpCoy/gvfK/Ws61+e972fm0F7up7hfYA==", + "dev": true + }, + "vfile-statistics": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/vfile-statistics/-/vfile-statistics-1.1.4.tgz", + "integrity": "sha512-lXhElVO0Rq3frgPvFBwahmed3X03vjPF8OcjKMy8+F1xU/3Q3QU3tKEDp743SFtb74PdF0UWpxPvtOP0GCLheA==", + "dev": true + }, + "which": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", + "dev": true, + "requires": { + "isexe": "^2.0.0" + } + }, + "which-boxed-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz", + "integrity": "sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg==", + "dev": true, + "requires": { + "is-bigint": "^1.0.1", + "is-boolean-object": "^1.1.0", + "is-number-object": "^1.0.4", + "is-string": "^1.0.5", + "is-symbol": "^1.0.3" + } + }, + "which-collection": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/which-collection/-/which-collection-1.0.1.tgz", + "integrity": "sha512-W8xeTUwaln8i3K/cY1nGXzdnVZlidBcagyNFtBdD5kxnb4TvGKR7FfSIS3mYpwWS1QUCutfKz8IY8RjftB0+1A==", + "dev": true, + "requires": { + "is-map": "^2.0.1", + "is-set": "^2.0.1", + "is-weakmap": "^2.0.1", + "is-weakset": "^2.0.1" + } + }, + "which-typed-array": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.6.tgz", + "integrity": "sha512-DdY984dGD5sQ7Tf+x1CkXzdg85b9uEel6nr4UkFg1LoE9OXv3uRuZhe5CoWdawhGACeFpEZXH8fFLQnDhbpm/Q==", + "dev": true, + "requires": { + "available-typed-arrays": "^1.0.4", + "call-bind": "^1.0.2", + "es-abstract": "^1.18.5", + "foreach": "^2.0.5", + "has-tostringtag": "^1.0.0", + "is-typed-array": "^1.1.6" + } + }, + "widest-line": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-3.1.0.tgz", + "integrity": "sha512-NsmoXalsWVDMGupxZ5R08ka9flZjjiLvHVAWYOKtiKM8ujtZWr9cRffak+uSE48+Ob8ObalXpwyeUiyDD6QFgg==", + "dev": true, + "requires": { + "string-width": "^4.0.0" + } + }, + "word-wrap": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.3.tgz", + "integrity": "sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==", + "dev": true + }, + "wrap-ansi": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", + "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", + "dev": true, + "requires": { + "ansi-styles": "^4.0.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0" + } + }, + "wrapped": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/wrapped/-/wrapped-1.0.1.tgz", + "integrity": "sha1-x4PZ2Aeyc+mwHoUWgKk4yHyQckI=", + "dev": true, + "requires": { + "co": "3.1.0", + "sliced": "^1.0.1" + } + }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", + "dev": true + }, + "write-file-atomic": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-3.0.3.tgz", + "integrity": "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==", + "dev": true, + "requires": { + "imurmurhash": "^0.1.4", + "is-typedarray": "^1.0.0", + "signal-exit": "^3.0.2", + "typedarray-to-buffer": "^3.1.5" + } + }, + "xdg-basedir": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-4.0.0.tgz", + "integrity": "sha512-PSNhEJDejZYV7h50BohL09Er9VaIefr2LMAf3OEmpCkjOi34eYyQYAXUTjEQtZJTKcF0E2UKTh+osDLsgNim9Q==", + "dev": true + }, + "xo": { + "version": "0.38.2", + "resolved": "https://registry.npmjs.org/xo/-/xo-0.38.2.tgz", + "integrity": "sha512-bGDGXgyPQyiVYIiqrkbFm4S1IIwlKDrNxgWnz9xWrdT4jdbfDU9fHkW6Mwab7jGms7ymoul+aRZVa3uMhcQlTw==", + "dev": true, + "requires": { + "@typescript-eslint/eslint-plugin": "^4.15.1", + "@typescript-eslint/parser": "^4.15.1", + "arrify": "^2.0.1", + "cosmiconfig": "^7.0.0", + "debug": "^4.3.1", + "eslint": "^7.20.0", + "eslint-config-prettier": "^7.2.0", + "eslint-config-xo": "^0.35.0", + "eslint-config-xo-typescript": "^0.38.0", + "eslint-formatter-pretty": "^4.0.0", + "eslint-import-resolver-webpack": "^0.13.0", + "eslint-plugin-ava": "^11.0.0", + "eslint-plugin-eslint-comments": "^3.2.0", + "eslint-plugin-import": "^2.22.1", + "eslint-plugin-no-use-extend-native": "^0.5.0", + "eslint-plugin-node": "^11.1.0", + "eslint-plugin-prettier": "^3.3.1", + "eslint-plugin-promise": "^4.3.1", + "eslint-plugin-unicorn": "^28.0.2", + "find-cache-dir": "^3.3.1", + "find-up": "^5.0.0", + "fs-extra": "^9.1.0", + "get-stdin": "^8.0.0", + "globby": "^9.2.0", + "has-flag": "^4.0.0", + "imurmurhash": "^0.1.4", + "is-path-inside": "^3.0.2", + "json-stable-stringify-without-jsonify": "^1.0.1", + "json5": "^2.2.0", + "lodash": "^4.17.20", + "meow": "^9.0.0", + "micromatch": "^4.0.2", + "open-editor": "^3.0.0", + "p-reduce": "^2.1.0", + "path-exists": "^4.0.0", + "prettier": "^2.2.1", + "resolve-cwd": "^3.0.0", + "resolve-from": "^5.0.0", + "semver": "^7.3.4", + "slash": "^3.0.0", + "to-absolute-glob": "^2.0.2", + "typescript": "^4.1.5", + "update-notifier": "^5.1.0" + }, + "dependencies": { + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + } + } + }, + "xtend": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", + "dev": true + }, + "y18n": { + "version": "5.0.8", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true + }, + "yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "yaml": { + "version": "1.10.2", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", + "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", + "dev": true + }, + "yargs": { + "version": "16.2.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-16.2.0.tgz", + "integrity": "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==", + "dev": true, + "requires": { + "cliui": "^7.0.2", + "escalade": "^3.1.1", + "get-caller-file": "^2.0.5", + "require-directory": "^2.1.1", + "string-width": "^4.2.0", + "y18n": "^5.0.5", + "yargs-parser": "^20.2.2" + } + }, + "yargs-parser": { + "version": "20.2.9", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.9.tgz", + "integrity": "sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w==", + "dev": true + }, + "yocto-queue": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", + "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", + "dev": true + }, + "zwitch": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/zwitch/-/zwitch-1.0.5.tgz", + "integrity": "sha512-V50KMwwzqJV0NpZIZFwfOD5/lyny3WlSzRiXgA0G7VUnRlqttta1L6UQIHzd6EuBY/cHGfwTIck7w1yH6Q5zUw==", + "dev": true + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/package.json new file mode 100644 index 0000000000000000000000000000000000000000..9e82ef70a0533d4ddecb7837e24e8895552f55fb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/package.json @@ -0,0 +1,109 @@ +{ + "_from": "collapse-white-space", + "_id": "collapse-white-space@2.0.0", + "_inBundle": false, + "_integrity": "sha512-eh9krktAIMDL0KHuN7WTBJ/0PMv8KUvfQRBkIlGmW61idRM2DJjgd1qXEPr4wyk2PimZZeNww3RVYo6CMvDGlg==", + "_location": "/collapse-white-space", + "_phantomChildren": {}, + "_requested": { + "type": "tag", + "registry": true, + "raw": "collapse-white-space", + "name": "collapse-white-space", + "escapedName": "collapse-white-space", + "rawSpec": "", + "saveSpec": null, + "fetchSpec": "latest" + }, + "_requiredBy": [ + "#USER", + "/" + ], + "_resolved": "https://registry.npmjs.org/collapse-white-space/-/collapse-white-space-2.0.0.tgz", + "_shasum": "37d8521344cdd36635db180a7c83e9d515ac281b", + "_spec": "collapse-white-space", + "_where": "/Users/kzantow/projects/syft/test/integration/test-fixtures/npm-lock", + "author": { + "name": "Titus Wormer", + "email": "tituswormer@gmail.com", + "url": "https://wooorm.com" + }, + "bugs": { + "url": "https://github.com/wooorm/collapse-white-space/issues" + }, + "bundleDependencies": false, + "contributors": [ + { + "name": "Titus Wormer", + "email": "tituswormer@gmail.com", + "url": "https://wooorm.com" + } + ], + "deprecated": false, + "description": "Replace multiple white space characters with a single space", + "devDependencies": { + "@types/tape": "^4.0.0", + "c8": "^7.0.0", + "prettier": "^2.0.0", + "remark-cli": "^9.0.0", + "remark-preset-wooorm": "^8.0.0", + "rimraf": "^3.0.0", + "tape": "^5.0.0", + "typescript": "^4.0.0", + "xo": "^0.38.0" + }, + "files": [ + "index.d.ts", + "index.js" + ], + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + }, + "homepage": "https://github.com/wooorm/collapse-white-space#readme", + "keywords": [ + "collapse", + "white", + "space" + ], + "license": "MIT", + "main": "index.js", + "name": "collapse-white-space", + "prettier": { + "tabWidth": 2, + "useTabs": false, + "singleQuote": true, + "bracketSpacing": false, + "semi": false, + "trailingComma": "none" + }, + "remarkConfig": { + "plugins": [ + "preset-wooorm" + ] + }, + "repository": { + "type": "git", + "url": "git+https://github.com/wooorm/collapse-white-space.git" + }, + "scripts": { + "build": "tsc", + "format": "remark . -qfo && prettier . -w --loglevel warn && xo --fix", + "prebuild": "rimraf \"*.d.ts\"", + "prepublishOnly": "npm run build", + "test": "npm run format && npm run build && npm run test-coverage", + "test-api": "node test", + "test-coverage": "c8 --check-coverage --branches 100 --functions 100 --lines 100 --statements 100 --reporter lcov node test.js" + }, + "sideEffects": false, + "type": "module", + "types": "index.d.ts", + "version": "2.0.0", + "xo": { + "prettier": true, + "rules": { + "no-var": "off", + "prefer-arrow-callback": "off" + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/readme.md b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/readme.md new file mode 100644 index 0000000000000000000000000000000000000000..e2600f0c80bf2e63f2a8f7d9b3a4efc4671bfd5f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/collapse-white-space/readme.md @@ -0,0 +1,65 @@ +# collapse-white-space + +[![Build][build-badge]][build] +[![Coverage][coverage-badge]][coverage] +[![Downloads][downloads-badge]][downloads] +[![Size][size-badge]][size] + +Replace multiple whitespace characters with a single space. + +## Install + +This package is ESM only: Node 12+ is needed to use it and it must be `import`ed +instead of `require`d. + +[npm][]: + +```sh +npm install collapse-white-space +``` + +## Use + +```js +import {collapseWhiteSpace} from 'collapse-white-space' + +collapseWhiteSpace('\tfoo \n\tbar \t\r\nbaz') //=> ' foo bar baz' +``` + +## API + +This package exports the following identifiers: `collapseWhiteSpace`. +There is no default export. + +### `collapseWhiteSpace(value)` + +Replace multiple whitespace characters in `value` (`string`) with a single +space. + +## License + +[MIT][license] © [Titus Wormer][author] + + + +[build-badge]: https://github.com/wooorm/collapse-white-space/workflows/main/badge.svg + +[build]: https://github.com/wooorm/collapse-white-space/actions + +[coverage-badge]: https://img.shields.io/codecov/c/github/wooorm/collapse-white-space.svg + +[coverage]: https://codecov.io/github/wooorm/collapse-white-space + +[downloads-badge]: https://img.shields.io/npm/dm/collapse-white-space.svg + +[downloads]: https://www.npmjs.com/package/collapse-white-space + +[size-badge]: https://img.shields.io/bundlephobia/minzip/collapse-white-space.svg + +[size]: https://bundlephobia.com/result?p=collapse-white-space + +[npm]: https://docs.npmjs.com/cli/install + +[license]: license + +[author]: https://wooorm.com diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..757562ec59276bff35792501d88fe83b34acca9a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2014 Mathias Buus + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/README.md b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/README.md new file mode 100644 index 0000000000000000000000000000000000000000..857b14bd7e4ffecbf82d04d2d9f7f54d5b0a9d97 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/README.md @@ -0,0 +1,54 @@ +# end-of-stream + +A node module that calls a callback when a readable/writable/duplex stream has completed or failed. + + npm install end-of-stream + +[![Build status](https://travis-ci.org/mafintosh/end-of-stream.svg?branch=master)](https://travis-ci.org/mafintosh/end-of-stream) + +## Usage + +Simply pass a stream and a callback to the `eos`. +Both legacy streams, streams2 and stream3 are supported. + +``` js +var eos = require('end-of-stream'); + +eos(readableStream, function(err) { + // this will be set to the stream instance + if (err) return console.log('stream had an error or closed early'); + console.log('stream has ended', this === readableStream); +}); + +eos(writableStream, function(err) { + if (err) return console.log('stream had an error or closed early'); + console.log('stream has finished', this === writableStream); +}); + +eos(duplexStream, function(err) { + if (err) return console.log('stream had an error or closed early'); + console.log('stream has ended and finished', this === duplexStream); +}); + +eos(duplexStream, {readable:false}, function(err) { + if (err) return console.log('stream had an error or closed early'); + console.log('stream has finished but might still be readable'); +}); + +eos(duplexStream, {writable:false}, function(err) { + if (err) return console.log('stream had an error or closed early'); + console.log('stream has ended but might still be writable'); +}); + +eos(readableStream, {error:false}, function(err) { + // do not treat emit('error', err) as a end-of-stream +}); +``` + +## License + +MIT + +## Related + +`end-of-stream` is part of the [mississippi stream utility collection](https://github.com/maxogden/mississippi) which includes more useful stream modules similar to this one. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/index.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/index.js new file mode 100644 index 0000000000000000000000000000000000000000..c77f0d5d704e3d4ef95f115d4defc267ee9d528e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/index.js @@ -0,0 +1,94 @@ +var once = require('once'); + +var noop = function() {}; + +var isRequest = function(stream) { + return stream.setHeader && typeof stream.abort === 'function'; +}; + +var isChildProcess = function(stream) { + return stream.stdio && Array.isArray(stream.stdio) && stream.stdio.length === 3 +}; + +var eos = function(stream, opts, callback) { + if (typeof opts === 'function') return eos(stream, null, opts); + if (!opts) opts = {}; + + callback = once(callback || noop); + + var ws = stream._writableState; + var rs = stream._readableState; + var readable = opts.readable || (opts.readable !== false && stream.readable); + var writable = opts.writable || (opts.writable !== false && stream.writable); + var cancelled = false; + + var onlegacyfinish = function() { + if (!stream.writable) onfinish(); + }; + + var onfinish = function() { + writable = false; + if (!readable) callback.call(stream); + }; + + var onend = function() { + readable = false; + if (!writable) callback.call(stream); + }; + + var onexit = function(exitCode) { + callback.call(stream, exitCode ? new Error('exited with error code: ' + exitCode) : null); + }; + + var onerror = function(err) { + callback.call(stream, err); + }; + + var onclose = function() { + process.nextTick(onclosenexttick); + }; + + var onclosenexttick = function() { + if (cancelled) return; + if (readable && !(rs && (rs.ended && !rs.destroyed))) return callback.call(stream, new Error('premature close')); + if (writable && !(ws && (ws.ended && !ws.destroyed))) return callback.call(stream, new Error('premature close')); + }; + + var onrequest = function() { + stream.req.on('finish', onfinish); + }; + + if (isRequest(stream)) { + stream.on('complete', onfinish); + stream.on('abort', onclose); + if (stream.req) onrequest(); + else stream.on('request', onrequest); + } else if (writable && !ws) { // legacy streams + stream.on('end', onlegacyfinish); + stream.on('close', onlegacyfinish); + } + + if (isChildProcess(stream)) stream.on('exit', onexit); + + stream.on('end', onend); + stream.on('finish', onfinish); + if (opts.error !== false) stream.on('error', onerror); + stream.on('close', onclose); + + return function() { + cancelled = true; + stream.removeListener('complete', onfinish); + stream.removeListener('abort', onclose); + stream.removeListener('request', onrequest); + if (stream.req) stream.req.removeListener('finish', onfinish); + stream.removeListener('end', onlegacyfinish); + stream.removeListener('close', onlegacyfinish); + stream.removeListener('finish', onfinish); + stream.removeListener('exit', onexit); + stream.removeListener('end', onend); + stream.removeListener('error', onerror); + stream.removeListener('close', onclose); + }; +}; + +module.exports = eos; diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/package.json new file mode 100644 index 0000000000000000000000000000000000000000..8e3ebab7c70a31349694eafeb6ce9246263d427a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/end-of-stream/package.json @@ -0,0 +1,65 @@ +{ + "_from": "end-of-stream@^1.1.0", + "_id": "end-of-stream@1.4.4", + "_inBundle": false, + "_integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "_location": "/end-of-stream", + "_phantomChildren": {}, + "_requested": { + "type": "range", + "registry": true, + "raw": "end-of-stream@^1.1.0", + "name": "end-of-stream", + "escapedName": "end-of-stream", + "rawSpec": "^1.1.0", + "saveSpec": null, + "fetchSpec": "^1.1.0" + }, + "_requiredBy": [ + "/pump" + ], + "_resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "_shasum": "5ae64a5f45057baf3626ec14da0ca5e4b2431eb0", + "_spec": "end-of-stream@^1.1.0", + "_where": "/Users/kzantow/projects/syft/test/integration/test-fixtures/npm-lock/node_modules/pump", + "author": { + "name": "Mathias Buus", + "email": "mathiasbuus@gmail.com" + }, + "bugs": { + "url": "https://github.com/mafintosh/end-of-stream/issues" + }, + "bundleDependencies": false, + "dependencies": { + "once": "^1.4.0" + }, + "deprecated": false, + "description": "Call a callback when a readable/writable/duplex stream has completed or failed.", + "devDependencies": { + "tape": "^4.11.0" + }, + "files": [ + "index.js" + ], + "homepage": "https://github.com/mafintosh/end-of-stream", + "keywords": [ + "stream", + "streams", + "callback", + "finish", + "close", + "end", + "wait" + ], + "license": "MIT", + "main": "index.js", + "name": "end-of-stream", + "repository": { + "type": "git", + "url": "git://github.com/mafintosh/end-of-stream.git" + }, + "scripts": { + "test": "node test.js" + }, + "version": "1.4.4" +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..ee27ba4b4412b0e4a05af5e3d8a005bc6681fdf3 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/LICENSE @@ -0,0 +1,18 @@ +This software is released under the MIT license: + +Permission is hereby granted, free of charge, to any person obtaining a copy of +this software and associated documentation files (the "Software"), to deal in +the Software without restriction, including without limitation the rights to +use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of +the Software, and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS +FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR +COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER +IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/example.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/example.js new file mode 100644 index 0000000000000000000000000000000000000000..c1b700c39dff64400d1a6012709b8ce7e1adf734 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/example.js @@ -0,0 +1,12 @@ +var on = require('dom-event'); +var insertCss = require('./'); + +document.querySelector('body').innerHTML = '

insert-css example

'; + +on(document.querySelector('#blue'), 'click', function() { + insertCss('body{background: blue}'); +}); + +on(document.querySelector('#red'), 'click', function() { + insertCss('body{background: red}'); +}); diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/index.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/index.js new file mode 100644 index 0000000000000000000000000000000000000000..db46310716b846640f91ae99970ad8ea2741bec1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/index.js @@ -0,0 +1,58 @@ +var containers = []; // will store container HTMLElement references +var styleElements = []; // will store {prepend: HTMLElement, append: HTMLElement} + +var usage = 'insert-css: You need to provide a CSS string. Usage: insertCss(cssString[, options]).'; + +function insertCss(css, options) { + options = options || {}; + + if (css === undefined) { + throw new Error(usage); + } + + var position = options.prepend === true ? 'prepend' : 'append'; + var container = options.container !== undefined ? options.container : document.querySelector('head'); + var containerId = containers.indexOf(container); + + // first time we see this container, create the necessary entries + if (containerId === -1) { + containerId = containers.push(container) - 1; + styleElements[containerId] = {}; + } + + // try to get the correponding container + position styleElement, create it otherwise + var styleElement; + + if (styleElements[containerId] !== undefined && styleElements[containerId][position] !== undefined) { + styleElement = styleElements[containerId][position]; + } else { + styleElement = styleElements[containerId][position] = createStyleElement(); + + if (position === 'prepend') { + container.insertBefore(styleElement, container.childNodes[0]); + } else { + container.appendChild(styleElement); + } + } + + // strip potential UTF-8 BOM if css was read from a file + if (css.charCodeAt(0) === 0xFEFF) { css = css.substr(1, css.length); } + + // actually add the stylesheet + if (styleElement.styleSheet) { + styleElement.styleSheet.cssText += css + } else { + styleElement.textContent += css; + } + + return styleElement; +}; + +function createStyleElement() { + var styleElement = document.createElement('style'); + styleElement.setAttribute('type', 'text/css'); + return styleElement; +} + +module.exports = insertCss; +module.exports.insertCss = insertCss; diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/package.json new file mode 100644 index 0000000000000000000000000000000000000000..c1dfc3f01d78f35fbf4ed7f4be926aa21bc3b560 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/package.json @@ -0,0 +1,85 @@ +{ + "_from": "insert-css", + "_id": "insert-css@2.0.0", + "_inBundle": false, + "_integrity": "sha1-610Ql7dUL0x56jBg067gfQU4gPQ=", + "_location": "/insert-css", + "_phantomChildren": {}, + "_requested": { + "type": "tag", + "registry": true, + "raw": "insert-css", + "name": "insert-css", + "escapedName": "insert-css", + "rawSpec": "", + "saveSpec": null, + "fetchSpec": "latest" + }, + "_requiredBy": [ + "#USER", + "/" + ], + "_resolved": "https://registry.npmjs.org/insert-css/-/insert-css-2.0.0.tgz", + "_shasum": "eb5d1097b7542f4c79ea3060d3aee07d053880f4", + "_spec": "insert-css", + "_where": "/Users/kzantow/projects/syft/test/integration/test-fixtures/npm-lock", + "author": { + "name": "James Halliday", + "email": "mail@substack.net", + "url": "http://substack.net" + }, + "bugs": { + "url": "https://github.com/substack/insert-css/issues" + }, + "bundleDependencies": false, + "dependencies": {}, + "deprecated": false, + "description": "insert a string of css into the ", + "devDependencies": { + "browserify": "^13.0.1", + "budo": "^8.3.0", + "computed-style": "^0.3.0", + "dom-event": "^1.0.0", + "tape": "^4.6.0", + "tape-run": "^2.1.4" + }, + "homepage": "https://github.com/substack/insert-css", + "keywords": [ + "css", + "insert", + "dom", + "browser", + "browserify", + "inject", + "styles", + "stylesheet", + "style", + "html", + "head", + "link" + ], + "license": "MIT", + "main": "index.js", + "name": "insert-css", + "repository": { + "type": "git", + "url": "git://github.com/substack/insert-css.git" + }, + "scripts": { + "example": "budo example.js", + "test": "browserify test.js | tape-run" + }, + "testling": { + "files": "test.js", + "browsers": [ + "ie/6..latest", + "chrome/20..latest", + "firefox/10..latest", + "safari/latest", + "opera/11.0..latest", + "iphone/6", + "ipad/6" + ] + }, + "version": "2.0.0" +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/readme.markdown b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/readme.markdown new file mode 100644 index 0000000000000000000000000000000000000000..64db1494aff1844d27f5167e00d43dc9b9adb9fd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/readme.markdown @@ -0,0 +1,44 @@ +# insert-css + +insert a string of css into the `` + +[![browser support](https://ci.testling.com/substack/insert-css.png)](https://ci.testling.com/substack/insert-css) + +# example + +``` js + var insertCss = require('insert-css'); + var styleElement = insertCss('body { background:blue; }'); +``` + +# api + +``` js + var insertCss = require('insert-css'); +``` + +## var styleElement = insertCss(css, opts); + +Insert some CSS into the page. + +* `opts.container` - Which HTMLElement to use as the base mounting point, defaults to +`document.querySelector('head')`. + +* `opts.prepend` - Add the CSS at the top level of the container instead of at the bottom level (default). + +This is particullary useful for library creators where you may want your default CSS to be prepended so it +can be easily overriden by user styles. + +# development + +## example + +``` sh +npm run example +``` + +## test + +``` sh +npm test +``` diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/test.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/test.js new file mode 100644 index 0000000000000000000000000000000000000000..8611e2d0cd978ccece20c5018d5b1067b8ddba3c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/insert-css/test.js @@ -0,0 +1,78 @@ +var test = require('tape'); + +test(function (t) { + var insertCss = require('./'); + var initialNbStyleTags = nbStyleTags(); + + // basic usage + var baseStyle = 'body{position:relative;text-decoration:overline}'; + insertCss(baseStyle); + t.equal(position(), 'relative', 'initial position is `relative`'); + + // adds one style tag + t.equal(nbStyleTags(), initialNbStyleTags + 1, 'we added one style tag'); + + // default to appending style + var appendStyle = 'body{position:absolute}'; + var appendStyleTag = insertCss(appendStyle); + t.equal(position(), 'absolute', 'new position is `absolute`'); + + // reuse same style tag + t.equal(nbStyleTags(), initialNbStyleTags + 1, 'we kept using the same style tag'); + + // prepend should add a new style tag before the append one + t.equal(textDecoration(), 'overline', 'text-decoration is overline by default'); + var prependStyleTag = insertCss('body{text-decoration:underline !important}', {prepend: true}); + t.equal(nbStyleTags(), initialNbStyleTags + 2, 'we added a new style tag'); + t.equal(textDecoration(), 'underline', 'text-decoration is now underline'); + var tag = prependStyleTag; + while (tag !== appendStyleTag) { + tag = tag.nextSibling; + } + t.equal(tag, appendStyleTag, 'prepend mode should add a style tag before the append one'); + + // uses old school styleSheet prop when present (IE) + if (!appendStyleTag.styleSheet) { + appendStyleTag.styleSheet = {cssText: 'a'}; + insertCss('p{color:blue}'); + t.equal(appendStyleTag.styleSheet.cssText, 'ap{color:blue}', 'we use old school styleSheet prop'); + delete appendStyleTag.styleSheet; + } + + // allow re-adding added style + insertCss(baseStyle); + t.equal(position(), 'relative', 'position is again `relative`'); + + // allow using a custom container + var customContainer = document.createElement('div'); + document.querySelector('body').appendChild(customContainer); + t.equal(nbStyleTags(customContainer), 0, 'no style tag in custom container'); + insertCss('body{position:absolute}', {container: customContainer}); + t.equal(nbStyleTags(customContainer), 1, 'new style tag added in custom container'); + t.equal(position(), 'absolute', 'position is absolute again'); + + t.end(); +}); + +test(function testEmpty(t) { + var insertCss = require('./'); + + t.equal(insertCss(), false, 'insertCss() with no arguments returns `false`'); + + t.end(); +}); + +function position() { + var getStyle = require('computed-style'); + return getStyle(document.querySelector('body'), 'position'); +} + +function textDecoration() { + var getStyle = require('computed-style'); + return getStyle(document.querySelector('body'), 'text-decoration'); +} + +function nbStyleTags(container) { + if (!container) container = document; + return container.querySelectorAll('style').length +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..19129e315fe593965a2fdd50ec0d1253bcbd2ece --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/LICENSE @@ -0,0 +1,15 @@ +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR +IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/README.md b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/README.md new file mode 100644 index 0000000000000000000000000000000000000000..1f1ffca9330e3ceddd54106e1ba63322fc9751f8 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/README.md @@ -0,0 +1,79 @@ +# once + +Only call a function once. + +## usage + +```javascript +var once = require('once') + +function load (file, cb) { + cb = once(cb) + loader.load('file') + loader.once('load', cb) + loader.once('error', cb) +} +``` + +Or add to the Function.prototype in a responsible way: + +```javascript +// only has to be done once +require('once').proto() + +function load (file, cb) { + cb = cb.once() + loader.load('file') + loader.once('load', cb) + loader.once('error', cb) +} +``` + +Ironically, the prototype feature makes this module twice as +complicated as necessary. + +To check whether you function has been called, use `fn.called`. Once the +function is called for the first time the return value of the original +function is saved in `fn.value` and subsequent calls will continue to +return this value. + +```javascript +var once = require('once') + +function load (cb) { + cb = once(cb) + var stream = createStream() + stream.once('data', cb) + stream.once('end', function () { + if (!cb.called) cb(new Error('not found')) + }) +} +``` + +## `once.strict(func)` + +Throw an error if the function is called twice. + +Some functions are expected to be called only once. Using `once` for them would +potentially hide logical errors. + +In the example below, the `greet` function has to call the callback only once: + +```javascript +function greet (name, cb) { + // return is missing from the if statement + // when no name is passed, the callback is called twice + if (!name) cb('Hello anonymous') + cb('Hello ' + name) +} + +function log (msg) { + console.log(msg) +} + +// this will print 'Hello anonymous' but the logical error will be missed +greet(null, once(msg)) + +// once.strict will print 'Hello anonymous' and throw an error when the callback will be called the second time +greet(null, once.strict(msg)) +``` diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/once.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/once.js new file mode 100644 index 0000000000000000000000000000000000000000..235406736d9d9485bbc0dd0820dd661110da7a4d --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/once.js @@ -0,0 +1,42 @@ +var wrappy = require('wrappy') +module.exports = wrappy(once) +module.exports.strict = wrappy(onceStrict) + +once.proto = once(function () { + Object.defineProperty(Function.prototype, 'once', { + value: function () { + return once(this) + }, + configurable: true + }) + + Object.defineProperty(Function.prototype, 'onceStrict', { + value: function () { + return onceStrict(this) + }, + configurable: true + }) +}) + +function once (fn) { + var f = function () { + if (f.called) return f.value + f.called = true + return f.value = fn.apply(this, arguments) + } + f.called = false + return f +} + +function onceStrict (fn) { + var f = function () { + if (f.called) + throw new Error(f.onceError) + f.called = true + return f.value = fn.apply(this, arguments) + } + var name = fn.name || 'Function wrapped with `once`' + f.onceError = name + " shouldn't be called more than once" + f.called = false + return f +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/package.json new file mode 100644 index 0000000000000000000000000000000000000000..bc4b68a50c009fa75260a76cebf5912fe39b2021 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/once/package.json @@ -0,0 +1,67 @@ +{ + "_from": "once@^1.3.1", + "_id": "once@1.4.0", + "_inBundle": false, + "_integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "_location": "/once", + "_phantomChildren": {}, + "_requested": { + "type": "range", + "registry": true, + "raw": "once@^1.3.1", + "name": "once", + "escapedName": "once", + "rawSpec": "^1.3.1", + "saveSpec": null, + "fetchSpec": "^1.3.1" + }, + "_requiredBy": [ + "/end-of-stream", + "/pump" + ], + "_resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "_shasum": "583b1aa775961d4b113ac17d9c50baef9dd76bd1", + "_spec": "once@^1.3.1", + "_where": "/Users/kzantow/projects/syft/test/integration/test-fixtures/npm-lock/node_modules/pump", + "author": { + "name": "Isaac Z. Schlueter", + "email": "i@izs.me", + "url": "http://blog.izs.me/" + }, + "bugs": { + "url": "https://github.com/isaacs/once/issues" + }, + "bundleDependencies": false, + "dependencies": { + "wrappy": "1" + }, + "deprecated": false, + "description": "Run a function exactly one time", + "devDependencies": { + "tap": "^7.0.1" + }, + "directories": { + "test": "test" + }, + "files": [ + "once.js" + ], + "homepage": "https://github.com/isaacs/once#readme", + "keywords": [ + "once", + "function", + "one", + "single" + ], + "license": "ISC", + "main": "once.js", + "name": "once", + "repository": { + "type": "git", + "url": "git://github.com/isaacs/once.git" + }, + "scripts": { + "test": "tap test/*.js" + }, + "version": "1.4.0" +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/.travis.yml b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/.travis.yml new file mode 100644 index 0000000000000000000000000000000000000000..17f94330e70bc85f8a53e57c92b1d1bc0846aa79 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/.travis.yml @@ -0,0 +1,5 @@ +language: node_js +node_js: + - "0.10" + +script: "npm test" diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..757562ec59276bff35792501d88fe83b34acca9a --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2014 Mathias Buus + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/README.md b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/README.md new file mode 100644 index 0000000000000000000000000000000000000000..4c81471a0ef04bdeb2e996d67ae3b95b0938f12f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/README.md @@ -0,0 +1,65 @@ +# pump + +pump is a small node module that pipes streams together and destroys all of them if one of them closes. + +``` +npm install pump +``` + +[![build status](http://img.shields.io/travis/mafintosh/pump.svg?style=flat)](http://travis-ci.org/mafintosh/pump) + +## What problem does it solve? + +When using standard `source.pipe(dest)` source will _not_ be destroyed if dest emits close or an error. +You are also not able to provide a callback to tell when then pipe has finished. + +pump does these two things for you + +## Usage + +Simply pass the streams you want to pipe together to pump and add an optional callback + +``` js +var pump = require('pump') +var fs = require('fs') + +var source = fs.createReadStream('/dev/random') +var dest = fs.createWriteStream('/dev/null') + +pump(source, dest, function(err) { + console.log('pipe finished', err) +}) + +setTimeout(function() { + dest.destroy() // when dest is closed pump will destroy source +}, 1000) +``` + +You can use pump to pipe more than two streams together as well + +``` js +var transform = someTransformStream() + +pump(source, transform, anotherTransform, dest, function(err) { + console.log('pipe finished', err) +}) +``` + +If `source`, `transform`, `anotherTransform` or `dest` closes all of them will be destroyed. + +Similarly to `stream.pipe()`, `pump()` returns the last stream passed in, so you can do: + +``` +return pump(s1, s2) // returns s2 +``` + +If you want to return a stream that combines *both* s1 and s2 to a single stream use +[pumpify](https://github.com/mafintosh/pumpify) instead. + +## License + +MIT + +## Related + +`pump` is part of the [mississippi stream utility collection](https://github.com/maxogden/mississippi) which includes more useful stream modules similar to this one. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/index.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/index.js new file mode 100644 index 0000000000000000000000000000000000000000..c15059f176c7948adac32d2baa17b536b4427cab --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/index.js @@ -0,0 +1,82 @@ +var once = require('once') +var eos = require('end-of-stream') +var fs = require('fs') // we only need fs to get the ReadStream and WriteStream prototypes + +var noop = function () {} +var ancient = /^v?\.0/.test(process.version) + +var isFn = function (fn) { + return typeof fn === 'function' +} + +var isFS = function (stream) { + if (!ancient) return false // newer node version do not need to care about fs is a special way + if (!fs) return false // browser + return (stream instanceof (fs.ReadStream || noop) || stream instanceof (fs.WriteStream || noop)) && isFn(stream.close) +} + +var isRequest = function (stream) { + return stream.setHeader && isFn(stream.abort) +} + +var destroyer = function (stream, reading, writing, callback) { + callback = once(callback) + + var closed = false + stream.on('close', function () { + closed = true + }) + + eos(stream, {readable: reading, writable: writing}, function (err) { + if (err) return callback(err) + closed = true + callback() + }) + + var destroyed = false + return function (err) { + if (closed) return + if (destroyed) return + destroyed = true + + if (isFS(stream)) return stream.close(noop) // use close for fs streams to avoid fd leaks + if (isRequest(stream)) return stream.abort() // request.destroy just do .end - .abort is what we want + + if (isFn(stream.destroy)) return stream.destroy() + + callback(err || new Error('stream was destroyed')) + } +} + +var call = function (fn) { + fn() +} + +var pipe = function (from, to) { + return from.pipe(to) +} + +var pump = function () { + var streams = Array.prototype.slice.call(arguments) + var callback = isFn(streams[streams.length - 1] || noop) && streams.pop() || noop + + if (Array.isArray(streams[0])) streams = streams[0] + if (streams.length < 2) throw new Error('pump requires two streams per minimum') + + var error + var destroys = streams.map(function (stream, i) { + var reading = i < streams.length - 1 + var writing = i > 0 + return destroyer(stream, reading, writing, function (err) { + if (!error) error = err + if (err) destroys.forEach(call) + if (reading) return + destroys.forEach(call) + callback(error) + }) + }) + + return streams.reduce(pipe) +} + +module.exports = pump diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/package.json new file mode 100644 index 0000000000000000000000000000000000000000..c4fbb095ee44711b21552c333de03c029799b25c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/package.json @@ -0,0 +1,60 @@ +{ + "_from": "pump", + "_id": "pump@3.0.0", + "_inBundle": false, + "_integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "_location": "/pump", + "_phantomChildren": {}, + "_requested": { + "type": "tag", + "registry": true, + "raw": "pump", + "name": "pump", + "escapedName": "pump", + "rawSpec": "", + "saveSpec": null, + "fetchSpec": "latest" + }, + "_requiredBy": [ + "#DEV:/", + "#USER" + ], + "_resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "_shasum": "b4a2116815bde2f4e1ea602354e8c75565107a64", + "_spec": "pump", + "_where": "/Users/kzantow/projects/syft/test/integration/test-fixtures/npm-lock", + "author": { + "name": "Mathias Buus Madsen", + "email": "mathiasbuus@gmail.com" + }, + "browser": { + "fs": false + }, + "bugs": { + "url": "https://github.com/mafintosh/pump/issues" + }, + "bundleDependencies": false, + "dependencies": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + }, + "deprecated": false, + "description": "pipe streams together and close all of them if one of them closes", + "homepage": "https://github.com/mafintosh/pump#readme", + "keywords": [ + "streams", + "pipe", + "destroy", + "callback" + ], + "license": "MIT", + "name": "pump", + "repository": { + "type": "git", + "url": "git://github.com/mafintosh/pump.git" + }, + "scripts": { + "test": "node test-browser.js && node test-node.js" + }, + "version": "3.0.0" +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/test-browser.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/test-browser.js new file mode 100644 index 0000000000000000000000000000000000000000..9a06c8a4ccb58cb2b8c51f25aeee8fedfe513c37 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/test-browser.js @@ -0,0 +1,66 @@ +var stream = require('stream') +var pump = require('./index') + +var rs = new stream.Readable() +var ws = new stream.Writable() + +rs._read = function (size) { + this.push(Buffer(size).fill('abc')) +} + +ws._write = function (chunk, encoding, cb) { + setTimeout(function () { + cb() + }, 100) +} + +var toHex = function () { + var reverse = new (require('stream').Transform)() + + reverse._transform = function (chunk, enc, callback) { + reverse.push(chunk.toString('hex')) + callback() + } + + return reverse +} + +var wsClosed = false +var rsClosed = false +var callbackCalled = false + +var check = function () { + if (wsClosed && rsClosed && callbackCalled) { + console.log('test-browser.js passes') + clearTimeout(timeout) + } +} + +ws.on('finish', function () { + wsClosed = true + check() +}) + +rs.on('end', function () { + rsClosed = true + check() +}) + +var res = pump(rs, toHex(), toHex(), toHex(), ws, function () { + callbackCalled = true + check() +}) + +if (res !== ws) { + throw new Error('should return last stream') +} + +setTimeout(function () { + rs.push(null) + rs.emit('close') +}, 1000) + +var timeout = setTimeout(function () { + check() + throw new Error('timeout') +}, 5000) diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/test-node.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/test-node.js new file mode 100644 index 0000000000000000000000000000000000000000..561251a0826c712b11e04f583c955e9aeff85023 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/pump/test-node.js @@ -0,0 +1,53 @@ +var pump = require('./index') + +var rs = require('fs').createReadStream('/dev/random') +var ws = require('fs').createWriteStream('/dev/null') + +var toHex = function () { + var reverse = new (require('stream').Transform)() + + reverse._transform = function (chunk, enc, callback) { + reverse.push(chunk.toString('hex')) + callback() + } + + return reverse +} + +var wsClosed = false +var rsClosed = false +var callbackCalled = false + +var check = function () { + if (wsClosed && rsClosed && callbackCalled) { + console.log('test-node.js passes') + clearTimeout(timeout) + } +} + +ws.on('close', function () { + wsClosed = true + check() +}) + +rs.on('close', function () { + rsClosed = true + check() +}) + +var res = pump(rs, toHex(), toHex(), toHex(), ws, function () { + callbackCalled = true + check() +}) + +if (res !== ws) { + throw new Error('should return last stream') +} + +setTimeout(function () { + rs.destroy() +}, 1000) + +var timeout = setTimeout(function () { + throw new Error('timeout') +}, 5000) diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..19129e315fe593965a2fdd50ec0d1253bcbd2ece --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/LICENSE @@ -0,0 +1,15 @@ +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR +IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/README.md b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/README.md new file mode 100644 index 0000000000000000000000000000000000000000..98eab2522b86e5fe32c92524c4ec778b98066cbf --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/README.md @@ -0,0 +1,36 @@ +# wrappy + +Callback wrapping utility + +## USAGE + +```javascript +var wrappy = require("wrappy") + +// var wrapper = wrappy(wrapperFunction) + +// make sure a cb is called only once +// See also: http://npm.im/once for this specific use case +var once = wrappy(function (cb) { + var called = false + return function () { + if (called) return + called = true + return cb.apply(this, arguments) + } +}) + +function printBoo () { + console.log('boo') +} +// has some rando property +printBoo.iAmBooPrinter = true + +var onlyPrintOnce = once(printBoo) + +onlyPrintOnce() // prints 'boo' +onlyPrintOnce() // does nothing + +// random property is retained! +assert.equal(onlyPrintOnce.iAmBooPrinter, true) +``` diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/package-lock.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/package-lock.json new file mode 100644 index 0000000000000000000000000000000000000000..425c6598fbbf4373fb8c9bc5a7f13b1ddbe10f73 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/package-lock.json @@ -0,0 +1,1859 @@ +{ + "name": "wrappy", + "version": "1.0.2", + "lockfileVersion": 1, + "requires": true, + "dependencies": { + "abbrev": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.0.9.tgz", + "integrity": "sha1-kbR5JYinc4wl813W9jdSovh3YTU=", + "dev": true + }, + "amdefine": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz", + "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=", + "dev": true, + "optional": true + }, + "ansi-regex": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", + "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", + "dev": true + }, + "ansi-styles": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", + "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=", + "dev": true + }, + "argparse": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", + "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "dev": true, + "requires": { + "sprintf-js": "~1.0.2" + } + }, + "asn1": { + "version": "0.1.11", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.1.11.tgz", + "integrity": "sha1-VZvhg3bQik7E2+gId9J4GGObLfc=", + "dev": true, + "optional": true + }, + "assert-plus": { + "version": "0.1.5", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.1.5.tgz", + "integrity": "sha1-7nQAlBMALYTOxyGcasgRgS5yMWA=", + "dev": true, + "optional": true + }, + "async": { + "version": "0.9.2", + "resolved": "https://registry.npmjs.org/async/-/async-0.9.2.tgz", + "integrity": "sha1-rqdNXmHB+JlhO/ZL2mbUx48v0X0=", + "dev": true, + "optional": true + }, + "asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", + "dev": true + }, + "aws-sign2": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.5.0.tgz", + "integrity": "sha1-xXED96F/wDfwLXwuZLYC6iI/fWM=", + "dev": true, + "optional": true + }, + "aws4": { + "version": "1.11.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.11.0.tgz", + "integrity": "sha512-xh1Rl34h6Fi1DC2WWKfxUTVqRsNnr6LsKz2+hfwDxQJWmrx8+c7ylaqBMcHfl1U1r2dsifOvKX3LQuLNZ+XSvA==", + "dev": true + }, + "balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "bcrypt-pbkdf": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", + "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", + "dev": true, + "requires": { + "tweetnacl": "^0.14.3" + } + }, + "bl": { + "version": "0.9.5", + "resolved": "https://registry.npmjs.org/bl/-/bl-0.9.5.tgz", + "integrity": "sha1-wGt5evCF6gC8Unr8jvzxHeIjIFQ=", + "dev": true, + "requires": { + "readable-stream": "~1.0.26" + }, + "dependencies": { + "readable-stream": { + "version": "1.0.34", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", + "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", + "dev": true, + "requires": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.1", + "isarray": "0.0.1", + "string_decoder": "~0.10.x" + } + } + } + }, + "boom": { + "version": "0.4.2", + "resolved": "https://registry.npmjs.org/boom/-/boom-0.4.2.tgz", + "integrity": "sha1-emNune1O/O+xnO9JR6PGffrukRs=", + "dev": true, + "optional": true, + "requires": { + "hoek": "0.9.x" + } + }, + "brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "camelcase": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-2.1.1.tgz", + "integrity": "sha1-fB0W1nmhu+WcoCys7PsBHiAfWh8=", + "dev": true + }, + "caseless": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.6.0.tgz", + "integrity": "sha1-gWfBq4OX+1u5X5bSjlqBxQ8kesQ=", + "dev": true + }, + "chalk": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", + "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "dev": true, + "requires": { + "ansi-styles": "^2.2.1", + "escape-string-regexp": "^1.0.2", + "has-ansi": "^2.0.0", + "strip-ansi": "^3.0.0", + "supports-color": "^2.0.0" + }, + "dependencies": { + "supports-color": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", + "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=", + "dev": true + } + } + }, + "cliui": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", + "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", + "dev": true, + "requires": { + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wrap-ansi": "^2.0.0" + } + }, + "code-point-at": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", + "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=", + "dev": true + }, + "codecov.io": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/codecov.io/-/codecov.io-0.1.6.tgz", + "integrity": "sha1-Wd/QLaH/McL7K5Uq2K0W/TeBtyg=", + "dev": true, + "requires": { + "request": "2.42.0", + "urlgrey": "0.4.0" + } + }, + "color-support": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-support/-/color-support-1.1.3.tgz", + "integrity": "sha512-qiBjkpbMLO/HL68y+lh4q0/O1MZFj2RX6X/KmMa3+gJD3z+WwI1ZzDHysvqHGS3mP6mznPckpXmw1nI9cJjyRg==", + "dev": true + }, + "combined-stream": { + "version": "0.0.7", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-0.0.7.tgz", + "integrity": "sha1-ATfmV7qlp1QcV6w3rF/AfXO03B8=", + "dev": true, + "optional": true, + "requires": { + "delayed-stream": "0.0.5" + } + }, + "commander": { + "version": "2.20.3", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", + "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", + "dev": true + }, + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", + "dev": true + }, + "core-util-is": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", + "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", + "dev": true + }, + "coveralls": { + "version": "2.13.3", + "resolved": "https://registry.npmjs.org/coveralls/-/coveralls-2.13.3.tgz", + "integrity": "sha512-iiAmn+l1XqRwNLXhW8Rs5qHZRFMYp9ZIPjEOVRpC/c4so6Y/f4/lFi0FfR5B9cCqgyhkJ5cZmbvcVRfP8MHchw==", + "dev": true, + "requires": { + "js-yaml": "3.6.1", + "lcov-parse": "0.0.10", + "log-driver": "1.2.5", + "minimist": "1.2.0", + "request": "2.79.0" + }, + "dependencies": { + "assert-plus": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.2.0.tgz", + "integrity": "sha1-104bh+ev/A24qttwIfP+SBAasjQ=", + "dev": true + }, + "aws-sign2": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.6.0.tgz", + "integrity": "sha1-FDQt0428yU0OW4fXY81jYSwOeU8=", + "dev": true + }, + "boom": { + "version": "2.10.1", + "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", + "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=", + "dev": true, + "requires": { + "hoek": "2.x.x" + } + }, + "caseless": { + "version": "0.11.0", + "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.11.0.tgz", + "integrity": "sha1-cVuW6phBWTzDMGeSP17GDr2k99c=", + "dev": true + }, + "combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dev": true, + "requires": { + "delayed-stream": "~1.0.0" + } + }, + "cryptiles": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", + "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=", + "dev": true, + "requires": { + "boom": "2.x.x" + } + }, + "delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", + "dev": true + }, + "forever-agent": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", + "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", + "dev": true + }, + "form-data": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", + "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=", + "dev": true, + "requires": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.5", + "mime-types": "^2.1.12" + } + }, + "hawk": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", + "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=", + "dev": true, + "requires": { + "boom": "2.x.x", + "cryptiles": "2.x.x", + "hoek": "2.x.x", + "sntp": "1.x.x" + } + }, + "hoek": { + "version": "2.16.3", + "resolved": "https://registry.npmjs.org/hoek/-/hoek-2.16.3.tgz", + "integrity": "sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0=", + "dev": true + }, + "http-signature": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", + "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=", + "dev": true, + "requires": { + "assert-plus": "^0.2.0", + "jsprim": "^1.2.2", + "sshpk": "^1.7.0" + } + }, + "js-yaml": { + "version": "3.6.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.6.1.tgz", + "integrity": "sha1-bl/mfYsgXOTSL60Ft3geja3MSzA=", + "dev": true, + "requires": { + "argparse": "^1.0.7", + "esprima": "^2.6.0" + } + }, + "mime-types": { + "version": "2.1.32", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.32.tgz", + "integrity": "sha512-hJGaVS4G4c9TSMYh2n6SQAGrC4RnfU+daP8G7cSCmaqNjiOoUY0VHCMS42pxnQmVF1GWwFhbHWn3RIxCqTmZ9A==", + "dev": true, + "requires": { + "mime-db": "1.49.0" + } + }, + "oauth-sign": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", + "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=", + "dev": true + }, + "punycode": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", + "dev": true + }, + "qs": { + "version": "6.3.2", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.3.2.tgz", + "integrity": "sha1-51vV9uJoEioqDgvaYwslUMFmUCw=", + "dev": true + }, + "request": { + "version": "2.79.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.79.0.tgz", + "integrity": "sha1-Tf5b9r6LjNw3/Pk+BLZVd3InEN4=", + "dev": true, + "requires": { + "aws-sign2": "~0.6.0", + "aws4": "^1.2.1", + "caseless": "~0.11.0", + "combined-stream": "~1.0.5", + "extend": "~3.0.0", + "forever-agent": "~0.6.1", + "form-data": "~2.1.1", + "har-validator": "~2.0.6", + "hawk": "~3.1.3", + "http-signature": "~1.1.0", + "is-typedarray": "~1.0.0", + "isstream": "~0.1.2", + "json-stringify-safe": "~5.0.1", + "mime-types": "~2.1.7", + "oauth-sign": "~0.8.1", + "qs": "~6.3.0", + "stringstream": "~0.0.4", + "tough-cookie": "~2.3.0", + "tunnel-agent": "~0.4.1", + "uuid": "^3.0.0" + } + }, + "sntp": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", + "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=", + "dev": true, + "requires": { + "hoek": "2.x.x" + } + }, + "tough-cookie": { + "version": "2.3.4", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.4.tgz", + "integrity": "sha512-TZ6TTfI5NtZnuyy/Kecv+CnoROnyXn2DN97LontgQpCwsX2XyLYCC0ENhYkehSOwAp8rTQKc/NUIF7BkQ5rKLA==", + "dev": true, + "requires": { + "punycode": "^1.4.1" + } + }, + "uuid": { + "version": "3.4.0", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", + "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", + "dev": true + } + } + }, + "cross-spawn": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-4.0.2.tgz", + "integrity": "sha1-e5JHYhwjrf3ThWAEqCPL45dCTUE=", + "dev": true, + "requires": { + "lru-cache": "^4.0.1", + "which": "^1.2.9" + } + }, + "cryptiles": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-0.2.2.tgz", + "integrity": "sha1-7ZH/HxetE9N0gohZT4pIoNJvMlw=", + "dev": true, + "optional": true, + "requires": { + "boom": "0.4.x" + } + }, + "ctype": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/ctype/-/ctype-0.5.3.tgz", + "integrity": "sha1-gsGMJGH3QRTvFsE1IkrQuRRMoS8=", + "dev": true, + "optional": true + }, + "dashdash": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", + "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", + "dev": true, + "requires": { + "assert-plus": "^1.0.0" + }, + "dependencies": { + "assert-plus": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true + } + } + }, + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, + "decamelize": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=", + "dev": true + }, + "deep-equal": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/deep-equal/-/deep-equal-0.1.2.tgz", + "integrity": "sha1-skbCuApXCkfBG+HZvRBw7IeLh84=", + "dev": true + }, + "deep-is": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", + "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", + "dev": true + }, + "deeper": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/deeper/-/deeper-2.1.0.tgz", + "integrity": "sha1-vFZOX3MXT98gHgiwADDooU2nQ2g=", + "dev": true + }, + "defined": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/defined/-/defined-0.0.0.tgz", + "integrity": "sha1-817qfXBekzuvE7LwOz+D2SFAOz4=", + "dev": true + }, + "delayed-stream": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-0.0.5.tgz", + "integrity": "sha1-1LH0OpPoKW3+AmlPRoC8N6MTxz8=", + "dev": true, + "optional": true + }, + "diff": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", + "integrity": "sha1-fyjS657nsVqX79ic5j3P2qPMur8=", + "dev": true + }, + "duplexer": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.2.tgz", + "integrity": "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==", + "dev": true + }, + "ecc-jsbn": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", + "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", + "dev": true, + "requires": { + "jsbn": "~0.1.0", + "safer-buffer": "^2.1.0" + } + }, + "escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", + "dev": true + }, + "escodegen": { + "version": "1.7.1", + "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.7.1.tgz", + "integrity": "sha1-MOz89mypjcZ80v0WKr626vqM5vw=", + "dev": true, + "requires": { + "esprima": "^1.2.2", + "estraverse": "^1.9.1", + "esutils": "^2.0.2", + "optionator": "^0.5.0", + "source-map": "~0.2.0" + }, + "dependencies": { + "esprima": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-1.2.5.tgz", + "integrity": "sha1-CZNQL+r2aBODJXVvMPmlH+7sEek=", + "dev": true + } + } + }, + "esprima": { + "version": "2.7.3", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", + "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=", + "dev": true + }, + "estraverse": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.9.3.tgz", + "integrity": "sha1-r2fy3JIlgkFZUJJgkaQAXSnJu0Q=", + "dev": true + }, + "esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "dev": true + }, + "events-to-array": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/events-to-array/-/events-to-array-1.1.2.tgz", + "integrity": "sha1-LUH1Y+H+QA7Uli/hpNXGp1Od9/Y=", + "dev": true + }, + "extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "dev": true + }, + "extsprintf": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", + "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", + "dev": true + }, + "fast-levenshtein": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-1.0.7.tgz", + "integrity": "sha1-AXjc3uAjuSkFGTrwlZ6KdjnP3Lk=", + "dev": true + }, + "fileset": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/fileset/-/fileset-0.2.1.tgz", + "integrity": "sha1-WI74lzxmI7KnbfRlEFaWuWqsgGc=", + "dev": true, + "requires": { + "glob": "5.x", + "minimatch": "2.x" + }, + "dependencies": { + "glob": { + "version": "5.0.15", + "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", + "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", + "dev": true, + "requires": { + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "2 || 3", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "minimatch": { + "version": "2.0.10", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-2.0.10.tgz", + "integrity": "sha1-jQh8OcazjAAbl/ynzm0OHoCvusc=", + "dev": true, + "requires": { + "brace-expansion": "^1.0.0" + } + } + } + }, + "foreground-child": { + "version": "1.5.6", + "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-1.5.6.tgz", + "integrity": "sha1-T9ca0t/elnibmApcCilZN8svXOk=", + "dev": true, + "requires": { + "cross-spawn": "^4", + "signal-exit": "^3.0.0" + }, + "dependencies": { + "signal-exit": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.3.tgz", + "integrity": "sha512-VUJ49FC8U1OxwZLxIbTTrDvLnf/6TDgxZcK8wxR8zs13xpx7xbG60ndBlhNrFi2EMuFRoeDoJO7wthSLq42EjA==", + "dev": true + } + } + }, + "forever-agent": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.5.2.tgz", + "integrity": "sha1-bQ4JxJIflKJ/Y9O0nF/v8epMUTA=", + "dev": true + }, + "form-data": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-0.1.4.tgz", + "integrity": "sha1-kavXiKupcCsaq/qLwBAxoqyeOxI=", + "dev": true, + "optional": true, + "requires": { + "async": "~0.9.0", + "combined-stream": "~0.0.4", + "mime": "~1.2.11" + } + }, + "fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", + "dev": true + }, + "generate-function": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/generate-function/-/generate-function-2.3.1.tgz", + "integrity": "sha512-eeB5GfMNeevm/GRYq20ShmsaGcmI81kIX2K9XQx5miC8KdHaC6Jm0qQ8ZNeGOi7wYB8OsdxKs+Y2oVuTFuVwKQ==", + "dev": true, + "requires": { + "is-property": "^1.0.2" + } + }, + "generate-object-property": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/generate-object-property/-/generate-object-property-1.2.0.tgz", + "integrity": "sha1-nA4cQDCM6AT0eDYYuTf6iPmdUNA=", + "dev": true, + "requires": { + "is-property": "^1.0.0" + } + }, + "getpass": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", + "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", + "dev": true, + "requires": { + "assert-plus": "^1.0.0" + }, + "dependencies": { + "assert-plus": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true + } + } + }, + "glob": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/glob/-/glob-6.0.4.tgz", + "integrity": "sha1-DwiGD2oVUSey+t1PnOJLGqtuTSI=", + "dev": true, + "requires": { + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "2 || 3", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "handlebars": { + "version": "4.7.7", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.7.tgz", + "integrity": "sha512-aAcXm5OAfE/8IXkcZvCepKU3VzW1/39Fb5ZuqMtgI/hT8X2YgoMvBY5dLhq/cpOvw7Lk1nK/UF71aLG/ZnVYRA==", + "dev": true, + "requires": { + "minimist": "^1.2.5", + "neo-async": "^2.6.0", + "source-map": "^0.6.1", + "uglify-js": "^3.1.4", + "wordwrap": "^1.0.0" + }, + "dependencies": { + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true + } + } + }, + "har-validator": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-2.0.6.tgz", + "integrity": "sha1-zcvAgYgmWtEZtqWnyKtw7s+10n0=", + "dev": true, + "requires": { + "chalk": "^1.1.1", + "commander": "^2.9.0", + "is-my-json-valid": "^2.12.4", + "pinkie-promise": "^2.0.0" + } + }, + "has-ansi": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", + "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", + "dev": true, + "requires": { + "ansi-regex": "^2.0.0" + } + }, + "has-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", + "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", + "dev": true + }, + "hawk": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/hawk/-/hawk-1.1.1.tgz", + "integrity": "sha1-h81JH5tG5OKurKM1QWdmiF0tHtk=", + "dev": true, + "optional": true, + "requires": { + "boom": "0.4.x", + "cryptiles": "0.2.x", + "hoek": "0.9.x", + "sntp": "0.2.x" + } + }, + "hoek": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/hoek/-/hoek-0.9.1.tgz", + "integrity": "sha1-PTIkYrrfB3Fup+uFuviAec3c5QU=", + "dev": true, + "optional": true + }, + "http-signature": { + "version": "0.10.1", + "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-0.10.1.tgz", + "integrity": "sha1-T72sEyVZqoMjEh5UB3nAoBKyfmY=", + "dev": true, + "optional": true, + "requires": { + "asn1": "0.1.11", + "assert-plus": "^0.1.5", + "ctype": "0.5.3" + } + }, + "inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", + "dev": true, + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "invert-kv": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", + "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", + "dev": true, + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "is-my-ip-valid": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-my-ip-valid/-/is-my-ip-valid-1.0.0.tgz", + "integrity": "sha512-gmh/eWXROncUzRnIa1Ubrt5b8ep/MGSnfAUI3aRp+sqTCs1tv1Isl8d8F6JmkN3dXKc3ehZMrtiPN9eL03NuaQ==", + "dev": true + }, + "is-my-json-valid": { + "version": "2.20.5", + "resolved": "https://registry.npmjs.org/is-my-json-valid/-/is-my-json-valid-2.20.5.tgz", + "integrity": "sha512-VTPuvvGQtxvCeghwspQu1rBgjYUT6FGxPlvFKbYuFtgc4ADsX3U5ihZOYN0qyU6u+d4X9xXb0IT5O6QpXKt87A==", + "dev": true, + "requires": { + "generate-function": "^2.0.0", + "generate-object-property": "^1.1.0", + "is-my-ip-valid": "^1.0.0", + "jsonpointer": "^4.0.0", + "xtend": "^4.0.0" + } + }, + "is-property": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-property/-/is-property-1.0.2.tgz", + "integrity": "sha1-V/4cTkhHTt1lsJkR8msc1Ald2oQ=", + "dev": true + }, + "is-typedarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", + "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", + "dev": true + }, + "is-utf8": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", + "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=", + "dev": true + }, + "isarray": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", + "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", + "dev": true + }, + "isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", + "dev": true + }, + "isstream": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", + "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", + "dev": true + }, + "istanbul": { + "version": "0.3.22", + "resolved": "https://registry.npmjs.org/istanbul/-/istanbul-0.3.22.tgz", + "integrity": "sha1-PhZNhQIf4ZyYXR8OfvDD4i0BLrY=", + "dev": true, + "requires": { + "abbrev": "1.0.x", + "async": "1.x", + "escodegen": "1.7.x", + "esprima": "2.5.x", + "fileset": "0.2.x", + "handlebars": "^4.0.1", + "js-yaml": "3.x", + "mkdirp": "0.5.x", + "nopt": "3.x", + "once": "1.x", + "resolve": "1.1.x", + "supports-color": "^3.1.0", + "which": "^1.1.1", + "wordwrap": "^1.0.0" + }, + "dependencies": { + "async": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", + "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", + "dev": true + }, + "esprima": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.5.0.tgz", + "integrity": "sha1-84ekb9NEwbGjm6+MIL+0O20AWMw=", + "dev": true + }, + "supports-color": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.2.3.tgz", + "integrity": "sha1-ZawFBLOVQXHYpklGsq48u4pfVPY=", + "dev": true, + "requires": { + "has-flag": "^1.0.0" + } + } + } + }, + "js-yaml": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz", + "integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==", + "dev": true, + "requires": { + "argparse": "^1.0.7", + "esprima": "^4.0.0" + }, + "dependencies": { + "esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", + "dev": true + } + } + }, + "jsbn": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", + "dev": true + }, + "json-schema": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", + "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", + "dev": true + }, + "json-stringify-safe": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", + "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", + "dev": true + }, + "jsonify": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", + "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=", + "dev": true + }, + "jsonpointer": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/jsonpointer/-/jsonpointer-4.1.0.tgz", + "integrity": "sha512-CXcRvMyTlnR53xMcKnuMzfCA5i/nfblTnnr74CZb6C4vG39eu6w51t7nKmU5MfLfbTgGItliNyjO/ciNPDqClg==", + "dev": true + }, + "jsprim": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", + "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", + "dev": true, + "requires": { + "assert-plus": "1.0.0", + "extsprintf": "1.3.0", + "json-schema": "0.2.3", + "verror": "1.10.0" + }, + "dependencies": { + "assert-plus": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true + } + } + }, + "lcid": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", + "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", + "dev": true, + "requires": { + "invert-kv": "^1.0.0" + } + }, + "lcov-parse": { + "version": "0.0.10", + "resolved": "https://registry.npmjs.org/lcov-parse/-/lcov-parse-0.0.10.tgz", + "integrity": "sha1-GwuP+ayceIklBYK3C3ExXZ2m2aM=", + "dev": true + }, + "levn": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.2.5.tgz", + "integrity": "sha1-uo0znQykphDjo/FFucr0iAcVUFQ=", + "dev": true, + "requires": { + "prelude-ls": "~1.1.0", + "type-check": "~0.3.1" + } + }, + "lodash": { + "version": "3.10.1", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-3.10.1.tgz", + "integrity": "sha1-W/Rejkm6QYnhfUgnid/RW9FAt7Y=", + "dev": true + }, + "log-driver": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/log-driver/-/log-driver-1.2.5.tgz", + "integrity": "sha1-euTsJXMC/XkNVXyxDJcQDYV7AFY=", + "dev": true + }, + "lru-cache": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.5.tgz", + "integrity": "sha512-sWZlbEP2OsHNkXrMl5GYk/jKk70MBng6UU4YI/qGDYbgf6YbP4EvmqISbXCoJiRKs+1bSpFHVgQxvJ17F2li5g==", + "dev": true, + "requires": { + "pseudomap": "^1.0.2", + "yallist": "^2.1.2" + } + }, + "mime": { + "version": "1.2.11", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.2.11.tgz", + "integrity": "sha1-WCA+7Ybjpe8XrtK32evUfwpg3RA=", + "dev": true, + "optional": true + }, + "mime-db": { + "version": "1.49.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.49.0.tgz", + "integrity": "sha512-CIc8j9URtOVApSFCQIF+VBkX1RwXp/oMMOrqdyXSBXq5RWNEsRfyj1kiRnQgmNXmHxPoFIxOroKA3zcU9P+nAA==", + "dev": true + }, + "mime-types": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-1.0.2.tgz", + "integrity": "sha1-mVrhOSq4r/y/yyZB3QVOlDwNXc4=", + "dev": true + }, + "minimatch": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", + "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", + "dev": true, + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "minimist": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "dev": true + }, + "mkdirp": { + "version": "0.5.5", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", + "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", + "dev": true, + "requires": { + "minimist": "^1.2.5" + }, + "dependencies": { + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + } + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", + "dev": true + }, + "neo-async": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", + "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", + "dev": true + }, + "node-uuid": { + "version": "1.4.8", + "resolved": "https://registry.npmjs.org/node-uuid/-/node-uuid-1.4.8.tgz", + "integrity": "sha1-sEDrCSOWivq/jTL7HxfxFn/auQc=", + "dev": true + }, + "nopt": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-3.0.6.tgz", + "integrity": "sha1-xkZdvwirzU2zWTF/eaxopkayj/k=", + "dev": true, + "requires": { + "abbrev": "1" + } + }, + "number-is-nan": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", + "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", + "dev": true + }, + "nyc": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/nyc/-/nyc-3.2.2.tgz", + "integrity": "sha1-ohIj/82Gvz0tKunhS4oIrq3gRu4=", + "dev": true, + "requires": { + "foreground-child": "1.3.0", + "glob": "^5.0.14", + "istanbul": "^0.3.19", + "lodash": "^3.10.0", + "mkdirp": "^0.5.0", + "rimraf": "^2.4.2", + "signal-exit": "^2.1.1", + "spawn-wrap": "^1.0.1", + "strip-bom": "^2.0.0", + "yargs": "^3.15.0" + }, + "dependencies": { + "foreground-child": { + "version": "1.3.0", + "bundled": true, + "dev": true, + "requires": { + "signal-exit": "^2.0.0", + "win-spawn": "^2.0.0" + }, + "dependencies": { + "win-spawn": { + "version": "2.0.0", + "bundled": true, + "dev": true + } + } + }, + "glob": { + "version": "5.0.15", + "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", + "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", + "dev": true, + "requires": { + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "2 || 3", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "spawn-wrap": { + "version": "1.0.1", + "bundled": true, + "dev": true, + "requires": { + "foreground-child": "^1.2.0", + "mkdirp": "^0.5.0", + "os-homedir": "^1.0.1", + "rimraf": "^2.3.3", + "signal-exit": "^2.0.0" + }, + "dependencies": { + "os-homedir": { + "version": "1.0.1", + "bundled": true, + "dev": true + } + } + } + } + }, + "oauth-sign": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.4.0.tgz", + "integrity": "sha1-8ilW8x6nFRqCHl8vsywRPK2Ln2k=", + "dev": true, + "optional": true + }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dev": true, + "requires": { + "wrappy": "1" + } + }, + "only-shallow": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/only-shallow/-/only-shallow-1.2.0.tgz", + "integrity": "sha1-cc7O26kyS8BRiu8Q7AgNMkncJGU=", + "dev": true + }, + "opener": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/opener/-/opener-1.5.2.tgz", + "integrity": "sha512-ur5UIdyw5Y7yEj9wLzhqXiy6GZ3Mwx0yGI+5sMn2r0N0v3cKJvUmFH5yPP+WXh9e0xfyzyJX95D8l088DNFj7A==", + "dev": true + }, + "optionator": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.5.0.tgz", + "integrity": "sha1-t1qJlaLUF98ltuTjhi9QqohlE2g=", + "dev": true, + "requires": { + "deep-is": "~0.1.2", + "fast-levenshtein": "~1.0.0", + "levn": "~0.2.5", + "prelude-ls": "~1.1.1", + "type-check": "~0.3.1", + "wordwrap": "~0.0.2" + }, + "dependencies": { + "wordwrap": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz", + "integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=", + "dev": true + } + } + }, + "os-locale": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", + "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", + "dev": true, + "requires": { + "lcid": "^1.0.0" + } + }, + "path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", + "dev": true + }, + "pinkie": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", + "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=", + "dev": true + }, + "pinkie-promise": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", + "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", + "dev": true, + "requires": { + "pinkie": "^2.0.0" + } + }, + "prelude-ls": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", + "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=", + "dev": true + }, + "process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", + "dev": true + }, + "pseudomap": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", + "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=", + "dev": true + }, + "psl": { + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.8.0.tgz", + "integrity": "sha512-RIdOzyoavK+hA18OGGWDqUTsCLhtA7IcZ/6NCs4fFJaHBDab+pDDmDIByWFRQJq2Cd7r1OoQxBGKOaztq+hjIQ==", + "dev": true, + "optional": true + }, + "punycode": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true, + "optional": true + }, + "qs": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/qs/-/qs-1.2.2.tgz", + "integrity": "sha1-GbV/8k3CqZzh+L32r82ln472H4g=", + "dev": true + }, + "readable-stream": { + "version": "2.3.7", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", + "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", + "dev": true, + "requires": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + }, + "dependencies": { + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dev": true, + "requires": { + "safe-buffer": "~5.1.0" + } + } + } + }, + "request": { + "version": "2.42.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.42.0.tgz", + "integrity": "sha1-VyvQFIk4VkBArHqxSLlkI6BjMEo=", + "dev": true, + "requires": { + "aws-sign2": "~0.5.0", + "bl": "~0.9.0", + "caseless": "~0.6.0", + "forever-agent": "~0.5.0", + "form-data": "~0.1.0", + "hawk": "1.1.1", + "http-signature": "~0.10.0", + "json-stringify-safe": "~5.0.0", + "mime-types": "~1.0.1", + "node-uuid": "~1.4.0", + "oauth-sign": "~0.4.0", + "qs": "~1.2.0", + "stringstream": "~0.0.4", + "tough-cookie": ">=0.12.0", + "tunnel-agent": "~0.4.0" + } + }, + "resolve": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.1.7.tgz", + "integrity": "sha1-IDEU2CrSxe2ejgQRs5ModeiJ6Xs=", + "dev": true + }, + "resumer": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/resumer/-/resumer-0.0.0.tgz", + "integrity": "sha1-8ej0YeQGS6Oegq883CqMiT0HZ1k=", + "dev": true, + "requires": { + "through": "~2.3.4" + } + }, + "rimraf": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", + "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", + "dev": true, + "requires": { + "glob": "^7.1.3" + }, + "dependencies": { + "glob": { + "version": "7.1.7", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.7.tgz", + "integrity": "sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ==", + "dev": true, + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + } + } + }, + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + }, + "safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "dev": true + }, + "signal-exit": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-2.1.2.tgz", + "integrity": "sha1-N1h5sfkuvDszRIDQONxUam1VhWQ=", + "dev": true + }, + "sntp": { + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/sntp/-/sntp-0.2.4.tgz", + "integrity": "sha1-+4hfGLDzqtGJ+CSGJTa87ux1CQA=", + "dev": true, + "optional": true, + "requires": { + "hoek": "0.9.x" + } + }, + "source-map": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.2.0.tgz", + "integrity": "sha1-2rc/vPwrqBm03gO9b26qSBZLP50=", + "dev": true, + "optional": true, + "requires": { + "amdefine": ">=0.0.4" + } + }, + "split": { + "version": "0.2.10", + "resolved": "https://registry.npmjs.org/split/-/split-0.2.10.tgz", + "integrity": "sha1-Zwl8YB1pfOE2j0GPBs0gHPBSGlc=", + "dev": true, + "requires": { + "through": "2" + } + }, + "sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", + "dev": true + }, + "sshpk": { + "version": "1.16.1", + "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", + "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", + "dev": true, + "requires": { + "asn1": "~0.2.3", + "assert-plus": "^1.0.0", + "bcrypt-pbkdf": "^1.0.0", + "dashdash": "^1.12.0", + "ecc-jsbn": "~0.1.1", + "getpass": "^0.1.1", + "jsbn": "~0.1.0", + "safer-buffer": "^2.0.2", + "tweetnacl": "~0.14.0" + }, + "dependencies": { + "asn1": { + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", + "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", + "dev": true, + "requires": { + "safer-buffer": "~2.1.0" + } + }, + "assert-plus": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true + } + } + }, + "stream-combiner": { + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/stream-combiner/-/stream-combiner-0.0.4.tgz", + "integrity": "sha1-TV5DPBhSYd3mI8o/RMWGvPXErRQ=", + "dev": true, + "requires": { + "duplexer": "~0.1.1" + } + }, + "string-width": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "dev": true, + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, + "string_decoder": { + "version": "0.10.31", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", + "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", + "dev": true + }, + "stringstream": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.6.tgz", + "integrity": "sha512-87GEBAkegbBcweToUrdzf3eLhWNg06FJTebl4BVJz/JgWy8CvEr9dRtX5qWphiynMSQlxxi+QqN0z5T32SLlhA==", + "dev": true + }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "dev": true, + "requires": { + "ansi-regex": "^2.0.0" + } + }, + "strip-bom": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", + "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", + "dev": true, + "requires": { + "is-utf8": "^0.2.0" + } + }, + "supports-color": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-1.3.1.tgz", + "integrity": "sha1-FXWN8J2P87SswwdTn6vicJXhBC0=", + "dev": true + }, + "tap": { + "version": "2.3.4", + "resolved": "https://registry.npmjs.org/tap/-/tap-2.3.4.tgz", + "integrity": "sha1-x7a9OX/x2fv5Pljr5Yx5Ff2ogLQ=", + "dev": true, + "requires": { + "codecov.io": "^0.1.6", + "coveralls": "^2.11.2", + "deeper": "^2.1.0", + "foreground-child": "^1.2.0", + "glob": "^6.0.1", + "js-yaml": "^3.3.1", + "mkdirp": "^0.5.0", + "nyc": "^3.1.0", + "only-shallow": "^1.0.2", + "opener": "^1.4.1", + "readable-stream": "^2.0.2", + "signal-exit": "^2.0.0", + "supports-color": "^1.3.1", + "tap-mocha-reporter": "0.0 || 1", + "tap-parser": "^1.2.2", + "tmatch": "^1.0.2" + } + }, + "tap-mocha-reporter": { + "version": "0.0.27", + "resolved": "https://registry.npmjs.org/tap-mocha-reporter/-/tap-mocha-reporter-0.0.27.tgz", + "integrity": "sha1-svcvPh6Lp4DuApGPzes6QNqAGPc=", + "dev": true, + "requires": { + "color-support": "^1.1.0", + "debug": "^2.1.3", + "diff": "^1.3.2", + "escape-string-regexp": "^1.0.3", + "glob": "^7.0.5", + "js-yaml": "^3.3.1", + "readable-stream": "^1.1.13", + "tap-parser": "^1.0.4", + "unicode-length": "^1.0.0" + }, + "dependencies": { + "glob": { + "version": "7.1.7", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.7.tgz", + "integrity": "sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ==", + "dev": true, + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "readable-stream": { + "version": "1.1.14", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz", + "integrity": "sha1-fPTFTvZI44EwhMY23SB54WbAgdk=", + "dev": true, + "optional": true, + "requires": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.1", + "isarray": "0.0.1", + "string_decoder": "~0.10.x" + } + } + } + }, + "tap-parser": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/tap-parser/-/tap-parser-1.3.2.tgz", + "integrity": "sha1-EgxQiciMPIp5PvKIhn3jIeGPjCI=", + "dev": true, + "requires": { + "events-to-array": "^1.0.1", + "inherits": "~2.0.1", + "js-yaml": "^3.2.7", + "readable-stream": "^2" + } + }, + "tape": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/tape/-/tape-2.3.0.tgz", + "integrity": "sha1-Df7scJIn+8yRcKvn8EaWKycUMds=", + "dev": true, + "requires": { + "deep-equal": "~0.1.0", + "defined": "~0.0.0", + "inherits": "~2.0.1", + "jsonify": "~0.0.0", + "resumer": "~0.0.0", + "split": "~0.2.10", + "stream-combiner": "~0.0.2", + "through": "~2.3.4" + } + }, + "through": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", + "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", + "dev": true + }, + "tmatch": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/tmatch/-/tmatch-1.0.2.tgz", + "integrity": "sha1-RYx5SN4L1SLHgfxBI1dpqjxEclc=", + "dev": true + }, + "tough-cookie": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-4.0.0.tgz", + "integrity": "sha512-tHdtEpQCMrc1YLrMaqXXcj6AxhYi/xgit6mZu1+EDWUn+qhUf8wMQoFIy9NXuq23zAwtcB0t/MjACGR18pcRbg==", + "dev": true, + "optional": true, + "requires": { + "psl": "^1.1.33", + "punycode": "^2.1.1", + "universalify": "^0.1.2" + } + }, + "tunnel-agent": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.4.3.tgz", + "integrity": "sha1-Y3PbdpCf5XDgjXNYM2Xtgop07us=", + "dev": true + }, + "tweetnacl": { + "version": "0.14.5", + "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", + "dev": true + }, + "type-check": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", + "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", + "dev": true, + "requires": { + "prelude-ls": "~1.1.2" + } + }, + "uglify-js": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.14.1.tgz", + "integrity": "sha512-JhS3hmcVaXlp/xSo3PKY5R0JqKs5M3IV+exdLHW99qKvKivPO4Z8qbej6mte17SOPqAOVMjt/XGgWacnFSzM3g==", + "dev": true, + "optional": true + }, + "unicode-length": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/unicode-length/-/unicode-length-1.0.3.tgz", + "integrity": "sha1-Wtp6f+1RhBpBijKM8UlHisg1irs=", + "dev": true, + "requires": { + "punycode": "^1.3.2", + "strip-ansi": "^3.0.1" + }, + "dependencies": { + "punycode": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", + "dev": true + } + } + }, + "universalify": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-0.1.2.tgz", + "integrity": "sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg==", + "dev": true, + "optional": true + }, + "urlgrey": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/urlgrey/-/urlgrey-0.4.0.tgz", + "integrity": "sha1-8GU1cED7NcOzEdTl3DZITZbb6gY=", + "dev": true, + "requires": { + "tape": "2.3.0" + } + }, + "util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", + "dev": true + }, + "verror": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", + "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", + "dev": true, + "requires": { + "assert-plus": "^1.0.0", + "core-util-is": "1.0.2", + "extsprintf": "^1.2.0" + }, + "dependencies": { + "assert-plus": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true + } + } + }, + "which": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", + "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", + "dev": true, + "requires": { + "isexe": "^2.0.0" + } + }, + "window-size": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.4.tgz", + "integrity": "sha1-+OGqHuWlPsW/FR/6CXQqatdpeHY=", + "dev": true + }, + "wordwrap": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", + "integrity": "sha1-J1hIEIkUVqQXHI0CJkQa3pDLyus=", + "dev": true + }, + "wrap-ansi": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz", + "integrity": "sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=", + "dev": true, + "requires": { + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1" + } + }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", + "dev": true + }, + "xtend": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", + "dev": true + }, + "y18n": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.2.tgz", + "integrity": "sha512-uGZHXkHnhF0XeeAPgnKfPv1bgKAYyVvmNL1xlKsPYZPaIHxGti2hHqvOCQv71XMsLxu1QjergkqogUnms5D3YQ==", + "dev": true + }, + "yallist": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", + "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=", + "dev": true + }, + "yargs": { + "version": "3.32.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.32.0.tgz", + "integrity": "sha1-AwiOnr+edWtpdRYR0qXvWRSCyZU=", + "dev": true, + "requires": { + "camelcase": "^2.0.1", + "cliui": "^3.0.3", + "decamelize": "^1.1.1", + "os-locale": "^1.4.0", + "string-width": "^1.0.1", + "window-size": "^0.1.4", + "y18n": "^3.2.0" + } + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/package.json new file mode 100644 index 0000000000000000000000000000000000000000..6d6034d864785c8353c2bb5080c2628c14b4ba4e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/package.json @@ -0,0 +1,58 @@ +{ + "_from": "wrappy@1", + "_id": "wrappy@1.0.2", + "_inBundle": false, + "_integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", + "_location": "/wrappy", + "_phantomChildren": {}, + "_requested": { + "type": "range", + "registry": true, + "raw": "wrappy@1", + "name": "wrappy", + "escapedName": "wrappy", + "rawSpec": "1", + "saveSpec": null, + "fetchSpec": "1" + }, + "_requiredBy": [ + "/once" + ], + "_resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "_shasum": "b5243d8f3ec1aa35f1364605bc0d1036e30ab69f", + "_spec": "wrappy@1", + "_where": "/Users/kzantow/projects/syft/test/integration/test-fixtures/npm-lock/node_modules/once", + "author": { + "name": "Isaac Z. Schlueter", + "email": "i@izs.me", + "url": "http://blog.izs.me/" + }, + "bugs": { + "url": "https://github.com/npm/wrappy/issues" + }, + "bundleDependencies": false, + "dependencies": {}, + "deprecated": false, + "description": "Callback wrapping utility", + "devDependencies": { + "tap": "^2.3.1" + }, + "directories": { + "test": "test" + }, + "files": [ + "wrappy.js" + ], + "homepage": "https://github.com/npm/wrappy", + "license": "ISC", + "main": "wrappy.js", + "name": "wrappy", + "repository": { + "type": "git", + "url": "git+https://github.com/npm/wrappy.git" + }, + "scripts": { + "test": "tap --coverage test/*.js" + }, + "version": "1.0.2" +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/wrappy.js b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/wrappy.js new file mode 100644 index 0000000000000000000000000000000000000000..bb7e7d6fcf70fdff4c5a48b7fa2ae3c9ba36fe47 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/node_modules/wrappy/wrappy.js @@ -0,0 +1,33 @@ +// Returns a wrapper function that returns a wrapped callback +// The wrapper function should do some stuff, and return a +// presumably different callback function. +// This makes sure that own properties are retained, so that +// decorations and such are not lost along the way. +module.exports = wrappy +function wrappy (fn, cb) { + if (fn && cb) return wrappy(fn)(cb) + + if (typeof fn !== 'function') + throw new TypeError('need wrapper function') + + Object.keys(fn).forEach(function (k) { + wrapper[k] = fn[k] + }) + + return wrapper + + function wrapper() { + var args = new Array(arguments.length) + for (var i = 0; i < args.length; i++) { + args[i] = arguments[i] + } + var ret = fn.apply(this, args) + var cb = args[args.length-1] + if (typeof ret === 'function' && ret !== cb) { + Object.keys(cb).forEach(function (k) { + ret[k] = cb[k] + }) + } + return ret + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/package-lock.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/package-lock.json new file mode 100644 index 0000000000000000000000000000000000000000..f18505de8a109fd854f5bcd3f9e32024b7784e23 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/package-lock.json @@ -0,0 +1,52 @@ +{ + "name": "npm-lock", + "version": "1.0.0", + "lockfileVersion": 1, + "requires": true, + "dependencies": { + "collapse-white-space": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/collapse-white-space/-/collapse-white-space-2.0.0.tgz", + "integrity": "sha512-eh9krktAIMDL0KHuN7WTBJ/0PMv8KUvfQRBkIlGmW61idRM2DJjgd1qXEPr4wyk2PimZZeNww3RVYo6CMvDGlg==" + }, + "end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "dev": true, + "requires": { + "once": "^1.4.0" + } + }, + "insert-css": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/insert-css/-/insert-css-2.0.0.tgz", + "integrity": "sha1-610Ql7dUL0x56jBg067gfQU4gPQ=" + }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dev": true, + "requires": { + "wrappy": "1" + } + }, + "pump": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "dev": true, + "requires": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", + "dev": true + } + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/package.json new file mode 100644 index 0000000000000000000000000000000000000000..e13065b69f8e2536a9dc12ba4bd283ae8f8ce6fd --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/npm-lock/package.json @@ -0,0 +1,18 @@ +{ + "name": "npm-lock", + "version": "1.0.0", + "description": "", + "main": "index.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1" + }, + "author": "", + "license": "ISC", + "dependencies": { + "collapse-white-space": "^2.0.0", + "insert-css": "^2.0.0" + }, + "devDependencies": { + "pump": "^3.0.0" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..b18aed69219562718858d972467ba0a68b1ce178 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/LICENSE @@ -0,0 +1,19 @@ +Copyright (c) 2010-2018 Caolan McMahon + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/bower.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/bower.json new file mode 100644 index 0000000000000000000000000000000000000000..390c6502f581075c067713444865d08b81a8bbd5 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/bower.json @@ -0,0 +1,17 @@ +{ + "name": "async", + "main": "dist/async.js", + "ignore": [ + "bower_components", + "lib", + "test", + "node_modules", + "perf", + "support", + "**/.*", + "*.config.js", + "*.json", + "index.js", + "Makefile" + ] +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/package.json new file mode 100644 index 0000000000000000000000000000000000000000..2c729a808b165d3702798f94c0582a5aa6b3a37c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/async/package.json @@ -0,0 +1,80 @@ +{ + "name": "async", + "description": "Higher-order functions and common patterns for asynchronous code", + "version": "3.2.3", + "main": "dist/async.js", + "author": "Caolan McMahon", + "homepage": "https://caolan.github.io/async/", + "repository": { + "type": "git", + "url": "https://github.com/caolan/async.git" + }, + "bugs": { + "url": "https://github.com/caolan/async/issues" + }, + "keywords": [ + "async", + "callback", + "module", + "utility" + ], + "devDependencies": { + "babel-core": "^6.26.3", + "babel-eslint": "^8.2.6", + "babel-minify": "^0.5.0", + "babel-plugin-add-module-exports": "^0.2.1", + "babel-plugin-istanbul": "^5.1.4", + "babel-plugin-syntax-async-generators": "^6.13.0", + "babel-plugin-transform-es2015-modules-commonjs": "^6.26.2", + "babel-preset-es2015": "^6.3.13", + "babel-preset-es2017": "^6.22.0", + "babel-register": "^6.26.0", + "babelify": "^8.0.0", + "benchmark": "^2.1.1", + "bluebird": "^3.4.6", + "browserify": "^16.2.3", + "chai": "^4.2.0", + "cheerio": "^0.22.0", + "coveralls": "^3.0.4", + "es6-promise": "^2.3.0", + "eslint": "^6.0.1", + "eslint-plugin-prefer-arrow": "^1.1.5", + "fs-extra": "^0.26.7", + "jsdoc": "^3.6.2", + "karma": "^4.1.0", + "karma-browserify": "^5.3.0", + "karma-edge-launcher": "^0.4.2", + "karma-firefox-launcher": "^1.1.0", + "karma-junit-reporter": "^1.2.0", + "karma-mocha": "^1.2.0", + "karma-mocha-reporter": "^2.2.0", + "karma-safari-launcher": "^1.0.0", + "mocha": "^6.1.4", + "mocha-junit-reporter": "^1.18.0", + "native-promise-only": "^0.8.0-a", + "nyc": "^14.1.1", + "rollup": "^0.63.4", + "rollup-plugin-node-resolve": "^2.0.0", + "rollup-plugin-npm": "^2.0.0", + "rsvp": "^3.0.18", + "semver": "^5.5.0", + "yargs": "^11.0.0" + }, + "scripts": { + "coverage": "nyc npm run mocha-node-test -- --grep @nycinvalid --invert", + "coveralls": "npm run coverage && nyc report --reporter=text-lcov | coveralls", + "jsdoc": "jsdoc -c ./support/jsdoc/jsdoc.json && node support/jsdoc/jsdoc-fix-html.js", + "lint": "eslint --fix lib/ test/ perf/memory.js perf/suites.js perf/benchmark.js support/build/ support/*.js karma.conf.js", + "mocha-browser-test": "karma start", + "mocha-node-test": "mocha", + "mocha-test": "npm run mocha-node-test && npm run mocha-browser-test", + "test": "npm run lint && npm run mocha-node-test" + }, + "license": "MIT", + "nyc": { + "exclude": [ + "test" + ] + }, + "module": "dist/async.mjs" +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/merge-objects/LICENSE.md b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/merge-objects/LICENSE.md new file mode 100644 index 0000000000000000000000000000000000000000..e8e78380394b1824fe0cf1a18b1b3be100bdae4f --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/merge-objects/LICENSE.md @@ -0,0 +1,19 @@ +Copyright (c) 2015 Oleksii Shevchenko (http://shevaroller.me) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/merge-objects/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/merge-objects/package.json new file mode 100644 index 0000000000000000000000000000000000000000..78b6c76b09ff0095fe3e8708b922e7399c523a87 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/merge-objects/package.json @@ -0,0 +1,23 @@ +{ + "name": "merge-objects", + "version": "1.0.5", + "description": "Merge two objects and concatenate arrays that are values of the same object key.", + "main": "lib/merge-objects.js", + "scripts": { + "test": "node test/test.js" + }, + "repository": { + "type": "git", + "url": "git@github.com:shevaroller/node-merge-objects.git" + }, + "keywords": [ + "merge", + "object", + "extend", + "concat", + "array", + "mixin" + ], + "author": "Oleksii Shevchenko (http://shevaroller.me)", + "license": "MIT" +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/resize-observer-polyfill/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/resize-observer-polyfill/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..43ced45a3c5d6f3eaeee953b860c910857dc3f36 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/resize-observer-polyfill/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2016 Denis Rul + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/resize-observer-polyfill/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/resize-observer-polyfill/package.json new file mode 100644 index 0000000000000000000000000000000000000000..9d67cf0f4f791d11027bd083526050a135bc8f0e --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/resize-observer-polyfill/package.json @@ -0,0 +1,64 @@ +{ + "name": "@4lolo/resize-observer-polyfill", + "author": "Denis Rul ", + "version": "1.5.2", + "description": "A polyfill for the Resize Observer API", + "main": "dist/ResizeObserver.js", + "module": "dist/ResizeObserver.es.js", + "scripts": { + "build": "rollup -c && cpy src/index.js.flow dist --rename=ResizeObserver.js.flow", + "test": "npm run test:lint && npm run test:spec", + "test:ci": "npm run test:lint && npm run test:spec:sauce && npm run test:spec:node", + "test:ci:pull": "npm run test:lint && karma start --browsers Firefox && npm run test:spec:node", + "test:lint": "node ./node_modules/eslint/bin/eslint.js \"**/*.js\" --ignore-pattern \"/dist/\"", + "test:spec": "karma start --browsers Chrome && npm run test:spec:node", + "test:spec:sauce": "karma start --sauce=windows && karma start --sauce=linux && karma start --sauce=osx", + "test:spec:node": "npm run build && node tests/node/index.js", + "test:spec:custom": "karma start --no-browsers", + "test:spec:native": "karma start --no-browsers --native" + }, + "repository": { + "type": "git", + "url": "https://github.com/que-etc/resize-observer-polyfill.git" + }, + "license": "MIT", + "bugs": { + "url": "https://github.com/que-etc/resize-observer-polyfill/issues" + }, + "types": "src/index.d.ts", + "files": [ + "src/", + "dist/" + ], + "keywords": [ + "ResizeObserver", + "resize", + "observer", + "util", + "client", + "browser", + "polyfill", + "ponyfill" + ], + "homepage": "https://github.com/que-etc/resize-observer-polyfill", + "devDependencies": { + "babel-eslint": "10.0.1", + "cpy-cli": "2.0.0", + "eslint": "5.10.0", + "jasmine": "2.8.0", + "jasmine-core": "2.8.0", + "karma": "3.1.3", + "karma-chrome-launcher": "2.2.0", + "karma-firefox-launcher": "1.1.0", + "karma-jasmine": "1.1.2", + "karma-jasmine-html-reporter": "0.2.2", + "karma-rollup-preprocessor": "6.1.1", + "karma-sauce-launcher": "1.2.0", + "karma-sourcemap-loader": "0.3.7", + "karma-spec-reporter": "0.0.32", + "promise-polyfill": "8.1.0", + "rollup": "0.67.4", + "rollup-plugin-typescript": "1.0.0", + "typescript": "3.2.2" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/should-type/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/should-type/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..d7e0e57ac00cb2090bc47916bd51c6e1932b6f96 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/should-type/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2014 + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/should-type/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/should-type/package.json new file mode 100644 index 0000000000000000000000000000000000000000..1c984c99b84998282328f56dd020742898c23519 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/node_modules/should-type/package.json @@ -0,0 +1,38 @@ +{ + "name": "should-type", + "version": "1.3.0", + "description": "Simple module to get instance type. Like a bit more advanced version of typeof", + "main": "cjs/should-type.js", + "jsnext:main": "es6/should-type.js", + "repository": { + "type": "git", + "url": "https://github.com/shouldjs/type.git" + }, + "keywords": [ + "should", + "type" + ], + "files": [ + "cjs/*", + "es6/*", + "README.md", + "LICENSE" + ], + "scripts": { + "cjs": "rollup --format=cjs --output=cjs/should-type.js index.js", + "es6": "rollup --format=es --output=es6/should-type.js index.js", + "build": "npm run cjs && npm run es6", + "prepublish": "npm run build" + }, + "author": "Denis Bardadym ", + "license": "MIT", + "bugs": { + "url": "https://github.com/shouldjs/type/issues" + }, + "homepage": "https://github.com/shouldjs/type", + "devDependencies": { + "eslint": "^3.0.0", + "eslint-config-shouldjs": "^1.0.2", + "rollup": "^0.34.3" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/package.json new file mode 100644 index 0000000000000000000000000000000000000000..694aad3c3374b83892b91d20cd981e7868a441d7 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/package.json @@ -0,0 +1,19 @@ +{ + "name": "yarn-lock", + "version": "1.0.0", + "main": "index.js", + "license": "MIT", + "private": true, + "workspaces": { + "packages": [ + "packages/*" + ] + }, + "dependencies": { + "async": "^3.2.3" + }, + "devDependencies": { + "merge-objects": "^1.0.5", + "should-type": "https://github.com/shouldjs/type.git#1.3.0" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/LICENSE b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..8f29698588533b535c9989361c44abacf23512ae --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/LICENSE @@ -0,0 +1,19 @@ +Copyright (c) 2010-2014 Caolan McMahon + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/bower.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/bower.json new file mode 100644 index 0000000000000000000000000000000000000000..18176881e0075ffcd0ad3734cf1af6c80349b917 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/bower.json @@ -0,0 +1,38 @@ +{ + "name": "async", + "description": "Higher-order functions and common patterns for asynchronous code", + "version": "0.9.2", + "main": "lib/async.js", + "keywords": [ + "async", + "callback", + "utility", + "module" + ], + "license": "MIT", + "repository": { + "type": "git", + "url": "https://github.com/caolan/async.git" + }, + "devDependencies": { + "nodeunit": ">0.0.0", + "uglify-js": "1.2.x", + "nodelint": ">0.0.0", + "lodash": ">=2.4.1" + }, + "moduleType": [ + "amd", + "globals", + "node" + ], + "ignore": [ + "**/.*", + "node_modules", + "bower_components", + "test", + "tests" + ], + "authors": [ + "Caolan McMahon" + ] +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/component.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/component.json new file mode 100644 index 0000000000000000000000000000000000000000..5003a7c52ce7fdfb3710e27c9b27e70da0df92e4 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/component.json @@ -0,0 +1,16 @@ +{ + "name": "async", + "description": "Higher-order functions and common patterns for asynchronous code", + "version": "0.9.2", + "keywords": [ + "async", + "callback", + "utility", + "module" + ], + "license": "MIT", + "repository": "caolan/async", + "scripts": [ + "lib/async.js" + ] +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/package.json new file mode 100644 index 0000000000000000000000000000000000000000..1424c76cbbd7245cc71cb4c6fa8da60baed908cb --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/node_modules/async/package.json @@ -0,0 +1,54 @@ +{ + "name": "async", + "description": "Higher-order functions and common patterns for asynchronous code", + "main": "lib/async.js", + "author": "Caolan McMahon", + "version": "0.9.2", + "keywords": [ + "async", + "callback", + "utility", + "module" + ], + "repository": { + "type": "git", + "url": "https://github.com/caolan/async.git" + }, + "bugs": { + "url": "https://github.com/caolan/async/issues" + }, + "license": "MIT", + "devDependencies": { + "nodeunit": ">0.0.0", + "uglify-js": "1.2.x", + "nodelint": ">0.0.0", + "lodash": ">=2.4.1" + }, + "jam": { + "main": "lib/async.js", + "include": [ + "lib/async.js", + "README.md", + "LICENSE" + ], + "categories": [ + "Utilities" + ] + }, + "scripts": { + "test": "nodeunit test/test-async.js" + }, + "spm": { + "main": "lib/async.js" + }, + "volo": { + "main": "lib/async.js", + "ignore": [ + "**/.*", + "node_modules", + "bower_components", + "test", + "tests" + ] + } +} \ No newline at end of file diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/package.json b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/package.json new file mode 100644 index 0000000000000000000000000000000000000000..548be34b2f160882edca92c2883805028b69fa09 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/packages/nested-package/package.json @@ -0,0 +1,10 @@ +{ + "name": "yarn-lock-nested-package", + "version": "1.0.0", + "main": "index.js", + "license": "MIT", + "dependencies": { + "async": "0.9.2", + "resize-observer-polyfill": "^1.5.1" + } +} diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/yarn.lock b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/yarn.lock new file mode 100644 index 0000000000000000000000000000000000000000..90845fa18874412abd376f3da1fbea15dc6e15ce --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/test-fixtures/yarn-lock/yarn.lock @@ -0,0 +1,28 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +async@0.9.2: + version "0.9.2" + resolved "https://registry.yarnpkg.com/async/-/async-0.9.2.tgz#aea74d5e61c1f899613bf64bda66d4c78f2fd17d" + integrity sha1-rqdNXmHB+JlhO/ZL2mbUx48v0X0= + +async@^3.2.3: + version "3.2.3" + resolved "https://registry.yarnpkg.com/async/-/async-3.2.3.tgz#ac53dafd3f4720ee9e8a160628f18ea91df196c9" + integrity sha512-spZRyzKL5l5BZQrr/6m/SqFdBN0q3OCI0f9rjfBzCMBIP4p75P620rR3gTmaksNOhmzgdxcaxdNfMy6anrbM0g== + +merge-objects@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/merge-objects/-/merge-objects-1.0.5.tgz#ad923ff3910091acc1438f53eb75b8f37d862a86" + integrity sha1-rZI/85EAkazBQ49T63W4832GKoY= + +resize-observer-polyfill@^1.5.1: + name "resize-observer-polyfill" + version "1.5.2" + resolved "https://registry.yarnpkg.com/@4lolo/resize-observer-polyfill/-/resize-observer-polyfill-1.5.2.tgz#58868fc7224506236b5550d0c68357f0a874b84b" + integrity sha512-HY4JYLITsWBOdeqCF/x3q7Aa2PVl/BmfkPv4H/Qzplc4Lrn9cKmWz6jHyAREH9tFuD0xELjJVgX3JaEmdcXu3g== + +"should-type@https://github.com/shouldjs/type.git#1.3.0": + version "1.3.0" + resolved "https://github.com/shouldjs/type.git#31d26945cb3b4ad21d2308776e4442c461666390" diff --git a/ci/tools/openeuler-purl/syft-dev/test/integration/utils_test.go b/ci/tools/openeuler-purl/syft-dev/test/integration/utils_test.go new file mode 100644 index 0000000000000000000000000000000000000000..81bd76061b274ef5859e031394e3f9355b6f986c --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/test/integration/utils_test.go @@ -0,0 +1,79 @@ +package integration + +import ( + "testing" + + "github.com/stretchr/testify/require" + + "github.com/anchore/syft/syft/pkg/cataloger" + + "github.com/anchore/syft/syft/sbom" + + "github.com/anchore/stereoscope/pkg/imagetest" + "github.com/anchore/syft/syft" + "github.com/anchore/syft/syft/source" +) + +func catalogFixtureImage(t *testing.T, fixtureImageName string, scope source.Scope, catalogerCfg []string) (sbom.SBOM, *source.Source) { + imagetest.GetFixtureImage(t, "docker-archive", fixtureImageName) + tarPath := imagetest.GetFixtureImageTarPath(t, fixtureImageName) + userInput := "docker-archive:" + tarPath + sourceInput, err := source.ParseInput(userInput, "", false) + require.NoError(t, err) + theSource, cleanupSource, err := source.New(*sourceInput, nil, nil) + t.Cleanup(cleanupSource) + require.NoError(t, err) + + c := cataloger.DefaultConfig() + c.Catalogers = catalogerCfg + + c.Search.Scope = scope + pkgCatalog, relationships, actualDistro, err := syft.CatalogPackages(theSource, c) + if err != nil { + t.Fatalf("failed to catalog image: %+v", err) + } + + return sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: pkgCatalog, + LinuxDistribution: actualDistro, + }, + Relationships: relationships, + Source: theSource.Metadata, + Descriptor: sbom.Descriptor{ + Name: "syft", + Version: "v0.42.0-bogus", + // the application configuration should be persisted here, however, we do not want to import + // the application configuration in this package (it's reserved only for ingestion by the cmd package) + Configuration: map[string]string{ + "config-key": "config-value", + }, + }, + }, theSource +} + +func catalogDirectory(t *testing.T, dir string) (sbom.SBOM, *source.Source) { + userInput := "dir:" + dir + sourceInput, err := source.ParseInput(userInput, "", false) + require.NoError(t, err) + theSource, cleanupSource, err := source.New(*sourceInput, nil, nil) + t.Cleanup(cleanupSource) + require.NoError(t, err) + + // TODO: this would be better with functional options (after/during API refactor) + c := cataloger.DefaultConfig() + c.Search.Scope = source.AllLayersScope + pkgCatalog, relationships, actualDistro, err := syft.CatalogPackages(theSource, c) + if err != nil { + t.Fatalf("failed to catalog image: %+v", err) + } + + return sbom.SBOM{ + Artifacts: sbom.Artifacts{ + PackageCatalog: pkgCatalog, + LinuxDistribution: actualDistro, + }, + Relationships: relationships, + Source: theSource.Metadata, + }, theSource +} diff --git a/ci/tools/openeuler-purl/syft-dev/ui/event_handlers.go b/ci/tools/openeuler-purl/syft-dev/ui/event_handlers.go new file mode 100644 index 0000000000000000000000000000000000000000..43c04a9fb2dd85cd79339a4f5335645af5456988 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/ui/event_handlers.go @@ -0,0 +1,573 @@ +package ui + +import ( + "context" + "fmt" + "io" + "strings" + "sync" + "time" + + stereoEventParsers "github.com/anchore/stereoscope/pkg/event/parsers" + "github.com/anchore/stereoscope/pkg/image/docker" + "github.com/anchore/syft/internal" + "github.com/anchore/syft/internal/ui/components" + syftEventParsers "github.com/anchore/syft/syft/event/parsers" + "github.com/dustin/go-humanize" + "github.com/gookit/color" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/go-progress" + "github.com/wagoodman/go-progress/format" + "github.com/wagoodman/jotframe/pkg/frame" +) + +const maxBarWidth = 50 +const statusSet = components.SpinnerDotSet +const completedStatus = "✔" +const tileFormat = color.Bold +const interval = 150 * time.Millisecond + +// StatusTitleColumn is the column index in a given row where status text will be displayed. +const StatusTitleColumn = 31 + +var ( + auxInfoFormat = color.HEX("#777777") + dockerPullCompletedColor = color.HEX("#fcba03") + dockerPullDownloadColor = color.HEX("#777777") + dockerPullExtractColor = color.White + dockerPullStageChars = strings.Split("▁▃▄▅▆▇█", "") + statusTitleTemplate = fmt.Sprintf(" %%s %%-%ds ", StatusTitleColumn) +) + +// startProcess is a helper function for providing common elements for long-running UI elements (such as a +// progress bar formatter and status spinner) +func startProcess() (format.Simple, *components.Spinner) { + width, _ := frame.GetTerminalSize() + barWidth := int(0.25 * float64(width)) + if barWidth > maxBarWidth { + barWidth = maxBarWidth + } + formatter := format.NewSimpleWithTheme(barWidth, format.HeavyNoBarTheme, format.ColorCompleted, format.ColorTodo) + spinner := components.NewSpinner(statusSet) + + return formatter, &spinner +} + +// formatDockerPullPhase returns a single character that represents the status of a layer pull. +func formatDockerPullPhase(phase docker.PullPhase, inputStr string) string { + switch phase { + case docker.WaitingPhase: + // ignore any progress related to waiting + return " " + case docker.PullingFsPhase, docker.DownloadingPhase: + return dockerPullDownloadColor.Sprint(inputStr) + case docker.DownloadCompletePhase: + return dockerPullDownloadColor.Sprint(dockerPullStageChars[len(dockerPullStageChars)-1]) + case docker.ExtractingPhase: + return dockerPullExtractColor.Sprint(inputStr) + case docker.VerifyingChecksumPhase, docker.PullCompletePhase: + return dockerPullCompletedColor.Sprint(inputStr) + case docker.AlreadyExistsPhase: + return dockerPullCompletedColor.Sprint(dockerPullStageChars[len(dockerPullStageChars)-1]) + default: + return inputStr + } +} + +// formatDockerImagePullStatus writes the docker image pull status summarized into a single line for the given state. +// +//nolint:funlen +func formatDockerImagePullStatus(pullStatus *docker.PullStatus, spinner *components.Spinner, line *frame.Line) { + var size, current uint64 + + title := tileFormat.Sprint("Pulling image") + + layers := pullStatus.Layers() + status := make(map[docker.LayerID]docker.LayerState) + completed := make([]string, len(layers)) + + // fetch the current state + for idx, layer := range layers { + completed[idx] = " " + status[layer] = pullStatus.Current(layer) + } + + numCompleted := 0 + for idx, layer := range layers { + prog := status[layer].PhaseProgress + current := prog.Current() + size := prog.Size() + + if progress.IsCompleted(prog) { + input := dockerPullStageChars[len(dockerPullStageChars)-1] + completed[idx] = formatDockerPullPhase(status[layer].Phase, input) + } else if current != 0 { + var ratio float64 + switch { + case current == 0 || size < 0: + ratio = 0 + case current >= size: + ratio = 1 + default: + ratio = float64(current) / float64(size) + } + + i := int(ratio * float64(len(dockerPullStageChars)-1)) + input := dockerPullStageChars[i] + completed[idx] = formatDockerPullPhase(status[layer].Phase, input) + } + + if progress.IsErrCompleted(status[layer].DownloadProgress.Error()) { + numCompleted++ + } + } + + for _, layer := range layers { + prog := status[layer].DownloadProgress + size += uint64(prog.Size()) + current += uint64(prog.Current()) + } + + var progStr, auxInfo string + if len(layers) > 0 { + render := strings.Join(completed, "") + prefix := dockerPullCompletedColor.Sprintf("%d Layers", len(layers)) + auxInfo = auxInfoFormat.Sprintf("[%s / %s]", humanize.Bytes(current), humanize.Bytes(size)) + if len(layers) == numCompleted { + auxInfo = auxInfoFormat.Sprintf("[%s] Extracting...", humanize.Bytes(size)) + } + + progStr = fmt.Sprintf("%s▕%s▏", prefix, render) + } + + spin := color.Magenta.Sprint(spinner.Next()) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s%s", spin, title, progStr, auxInfo)) +} + +// PullDockerImageHandler periodically writes a formatted line widget representing a docker image pull event. +func PullDockerImageHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + _, pullStatus, err := stereoEventParsers.ParsePullDockerImage(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + wg.Add(1) + + _, spinner := startProcess() + + go func() { + defer wg.Done() + + loop: + for { + select { + case <-ctx.Done(): + break loop + case <-time.After(interval): + formatDockerImagePullStatus(pullStatus, spinner, line) + if pullStatus.Complete() { + break loop + } + } + } + + if pullStatus.Complete() { + spin := color.Green.Sprint(completedStatus) + title := tileFormat.Sprint("Pulled image") + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate, spin, title)) + } + }() + return err +} + +// FetchImageHandler periodically writes a the image save and write-to-disk process in the form of a progress bar. +func FetchImageHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + _, prog, err := stereoEventParsers.ParseFetchImage(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + wg.Add(1) + + formatter, spinner := startProcess() + stream := progress.Stream(ctx, prog, interval) + title := tileFormat.Sprint("Loading image") + + formatFn := func(p progress.Progress) { + progStr, err := formatter.Format(p) + spin := color.Magenta.Sprint(spinner.Next()) + if err != nil { + _, _ = io.WriteString(line, fmt.Sprintf("Error: %+v", err)) + } else { + auxInfo := auxInfoFormat.Sprintf("[%s]", prog.Stage()) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s %s", spin, title, progStr, auxInfo)) + } + } + + go func() { + defer wg.Done() + + formatFn(progress.Progress{}) + for p := range stream { + formatFn(p) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprint("Loaded image") + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate, spin, title)) + }() + return err +} + +func UploadAttestationHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + prog, err := syftEventParsers.ParseUploadAttestation(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + wg.Add(1) + + formatter, spinner := startProcess() + stream := progress.Stream(ctx, prog, interval) + title := tileFormat.Sprint("Uploading attestation") + + formatFn := func(p progress.Progress) { + progStr, err := formatter.Format(p) + spin := color.Magenta.Sprint(spinner.Next()) + if err != nil { + _, _ = io.WriteString(line, fmt.Sprintf("Error: %+v", err)) + } else { + auxInfo := auxInfoFormat.Sprintf("[%s]", prog.Stage()) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s %s", spin, title, progStr, auxInfo)) + } + } + + go func() { + defer wg.Done() + + formatFn(progress.Progress{}) + for p := range stream { + formatFn(p) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprint("Uploaded attestation") + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate, spin, title)) + }() + return err +} + +// ReadImageHandler periodically writes a the image read/parse/build-tree status in the form of a progress bar. +func ReadImageHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + _, prog, err := stereoEventParsers.ParseReadImage(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + + wg.Add(1) + + formatter, spinner := startProcess() + stream := progress.Stream(ctx, prog, interval) + title := tileFormat.Sprint("Parsing image") + + formatFn := func(p progress.Progress) { + progStr, err := formatter.Format(p) + spin := color.Magenta.Sprint(spinner.Next()) + if err != nil { + _, _ = io.WriteString(line, fmt.Sprintf("Error: %+v", err)) + } else { + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s", spin, title, progStr)) + } + } + + go func() { + defer wg.Done() + + formatFn(progress.Progress{}) + for p := range stream { + formatFn(p) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprint("Parsed image") + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate, spin, title)) + }() + + return nil +} + +// PackageCatalogerStartedHandler periodically writes catalog statistics to a single line. +func PackageCatalogerStartedHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + monitor, err := syftEventParsers.ParsePackageCatalogerStarted(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + + wg.Add(1) + + _, spinner := startProcess() + stream := progress.StreamMonitors(ctx, []progress.Monitorable{monitor.FilesProcessed, monitor.PackagesDiscovered}, interval) + title := tileFormat.Sprint("Cataloging packages") + + formatFn := func(p int64) { + spin := color.Magenta.Sprint(spinner.Next()) + auxInfo := auxInfoFormat.Sprintf("[packages %d]", p) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s", spin, title, auxInfo)) + } + + go func() { + defer wg.Done() + + formatFn(0) + for p := range stream { + formatFn(p[1]) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprint("Cataloged packages") + auxInfo := auxInfoFormat.Sprintf("[%d packages]", monitor.PackagesDiscovered.Current()) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s", spin, title, auxInfo)) + }() + + return nil +} + +// SecretsCatalogerStartedHandler shows the intermittent secrets searching progress. +func SecretsCatalogerStartedHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + prog, err := syftEventParsers.ParseSecretsCatalogingStarted(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + wg.Add(1) + + formatter, spinner := startProcess() + stream := progress.Stream(ctx, prog, interval) + title := tileFormat.Sprint("Cataloging secrets") + + formatFn := func(p progress.Progress) { + progStr, err := formatter.Format(p) + spin := color.Magenta.Sprint(spinner.Next()) + if err != nil { + _, _ = io.WriteString(line, fmt.Sprintf("Error: %+v", err)) + } else { + auxInfo := auxInfoFormat.Sprintf("[%d secrets]", prog.SecretsDiscovered.Current()) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s %s", spin, title, progStr, auxInfo)) + } + } + + go func() { + defer wg.Done() + + formatFn(progress.Progress{}) + for p := range stream { + formatFn(p) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprint("Cataloged secrets") + auxInfo := auxInfoFormat.Sprintf("[%d secrets]", prog.SecretsDiscovered.Current()) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s", spin, title, auxInfo)) + }() + return err +} + +// FileMetadataCatalogerStartedHandler shows the intermittent secrets searching progress. +// +//nolint:dupl +func FileMetadataCatalogerStartedHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + prog, err := syftEventParsers.ParseFileMetadataCatalogingStarted(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + wg.Add(1) + + formatter, spinner := startProcess() + stream := progress.Stream(ctx, prog, interval) + title := tileFormat.Sprint("Cataloging file metadata") + + formatFn := func(p progress.Progress) { + progStr, err := formatter.Format(p) + spin := color.Magenta.Sprint(spinner.Next()) + if err != nil { + _, _ = io.WriteString(line, fmt.Sprintf("Error: %+v", err)) + } else { + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s", spin, title, progStr)) + } + } + + go func() { + defer wg.Done() + + formatFn(progress.Progress{}) + for p := range stream { + formatFn(p) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprint("Cataloged file metadata") + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate, spin, title)) + }() + return err +} + +// FileIndexingStartedHandler shows the intermittent indexing progress from a directory resolver. +func FileIndexingStartedHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + path, prog, err := syftEventParsers.ParseFileIndexingStarted(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + wg.Add(1) + + _, spinner := startProcess() + stream := progress.Stream(ctx, prog, interval) + title := tileFormat.Sprintf("Indexing %s", path) + + formatFn := func(_ progress.Progress) { + spin := color.Magenta.Sprint(spinner.Next()) + if err != nil { + _, _ = io.WriteString(line, fmt.Sprintf("Error: %+v", err)) + } else { + auxInfo := auxInfoFormat.Sprintf("[file: %s]", internal.TruncateMiddleEllipsis(prog.Stage(), 100)) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s", spin, title, auxInfo)) + } + } + + go func() { + defer wg.Done() + + formatFn(progress.Progress{}) + for p := range stream { + formatFn(p) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprintf("Indexed %s", path) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate, spin, title)) + }() + return err +} + +// FileMetadataCatalogerStartedHandler shows the intermittent secrets searching progress. +// +//nolint:dupl +func FileDigestsCatalogerStartedHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + prog, err := syftEventParsers.ParseFileDigestsCatalogingStarted(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + wg.Add(1) + + formatter, spinner := startProcess() + stream := progress.Stream(ctx, prog, interval) + title := tileFormat.Sprint("Cataloging file digests") + + formatFn := func(p progress.Progress) { + progStr, err := formatter.Format(p) + spin := color.Magenta.Sprint(spinner.Next()) + if err != nil { + _, _ = io.WriteString(line, fmt.Sprintf("Error: %+v", err)) + } else { + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s", spin, title, progStr)) + } + } + + go func() { + defer wg.Done() + + formatFn(progress.Progress{}) + for p := range stream { + formatFn(p) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprint("Cataloged file digests") + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate, spin, title)) + }() + return err +} + +// ImportStartedHandler shows the intermittent upload progress to Anchore Enterprise. +func ImportStartedHandler(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + host, prog, err := syftEventParsers.ParseImportStarted(event) + if err != nil { + return fmt.Errorf("bad %s event: %w", event.Type, err) + } + + line, err := fr.Append() + if err != nil { + return err + } + wg.Add(1) + + formatter, spinner := startProcess() + stream := progress.Stream(ctx, prog, interval) + title := tileFormat.Sprint("Uploading image") + + formatFn := func(p progress.Progress) { + progStr, err := formatter.Format(p) + spin := color.Magenta.Sprint(spinner.Next()) + if err != nil { + _, _ = io.WriteString(line, fmt.Sprintf("Error: %+v", err)) + } else { + auxInfo := auxInfoFormat.Sprintf("[%s]", prog.Stage()) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s %s", spin, title, progStr, auxInfo)) + } + } + + go func() { + defer wg.Done() + + formatFn(progress.Progress{}) + for p := range stream { + formatFn(p) + } + + spin := color.Green.Sprint(completedStatus) + title = tileFormat.Sprint("Uploaded image") + auxInfo := auxInfoFormat.Sprintf("[%s]", host) + _, _ = io.WriteString(line, fmt.Sprintf(statusTitleTemplate+"%s", spin, title, auxInfo)) + }() + return err +} diff --git a/ci/tools/openeuler-purl/syft-dev/ui/handler.go b/ci/tools/openeuler-purl/syft-dev/ui/handler.go new file mode 100644 index 0000000000000000000000000000000000000000..bf9eb81d364172957523ed620012aedf0085f049 --- /dev/null +++ b/ci/tools/openeuler-purl/syft-dev/ui/handler.go @@ -0,0 +1,80 @@ +/* +Package ui provides all public UI elements intended to be repurposed in other applications. Specifically, a single +Handler object is provided to allow consuming applications (such as grype) to check if there are UI elements the handler +can respond to (given a specific event type) and handle the event in context of the given screen frame object. +*/ +package ui + +import ( + "context" + "sync" + + stereoscopeEvent "github.com/anchore/stereoscope/pkg/event" + syftEvent "github.com/anchore/syft/syft/event" + "github.com/wagoodman/go-partybus" + "github.com/wagoodman/jotframe/pkg/frame" +) + +// Handler is an aggregated event handler for the set of supported events (PullDockerImage, ReadImage, FetchImage, PackageCatalogerStarted) +type Handler struct { +} + +// NewHandler returns an empty Handler +func NewHandler() *Handler { + return &Handler{} +} + +// RespondsTo indicates if the handler is capable of handling the given event. +func (r *Handler) RespondsTo(event partybus.Event) bool { + switch event.Type { + case stereoscopeEvent.PullDockerImage, + stereoscopeEvent.ReadImage, + stereoscopeEvent.FetchImage, + syftEvent.UploadAttestation, + syftEvent.PackageCatalogerStarted, + syftEvent.SecretsCatalogerStarted, + syftEvent.FileDigestsCatalogerStarted, + syftEvent.FileMetadataCatalogerStarted, + syftEvent.FileIndexingStarted, + syftEvent.ImportStarted: + return true + default: + return false + } +} + +// Handle calls the specific event handler for the given event within the context of the screen frame. +func (r *Handler) Handle(ctx context.Context, fr *frame.Frame, event partybus.Event, wg *sync.WaitGroup) error { + switch event.Type { + case stereoscopeEvent.PullDockerImage: + return PullDockerImageHandler(ctx, fr, event, wg) + + case stereoscopeEvent.ReadImage: + return ReadImageHandler(ctx, fr, event, wg) + + case stereoscopeEvent.FetchImage: + return FetchImageHandler(ctx, fr, event, wg) + + case syftEvent.UploadAttestation: + return UploadAttestationHandler(ctx, fr, event, wg) + + case syftEvent.PackageCatalogerStarted: + return PackageCatalogerStartedHandler(ctx, fr, event, wg) + + case syftEvent.SecretsCatalogerStarted: + return SecretsCatalogerStartedHandler(ctx, fr, event, wg) + + case syftEvent.FileDigestsCatalogerStarted: + return FileDigestsCatalogerStartedHandler(ctx, fr, event, wg) + + case syftEvent.FileMetadataCatalogerStarted: + return FileMetadataCatalogerStartedHandler(ctx, fr, event, wg) + + case syftEvent.FileIndexingStarted: + return FileIndexingStartedHandler(ctx, fr, event, wg) + + case syftEvent.ImportStarted: + return ImportStartedHandler(ctx, fr, event, wg) + } + return nil +} diff --git a/ci/tools/openeuler-purl/syft.py b/ci/tools/openeuler-purl/syft.py new file mode 100644 index 0000000000000000000000000000000000000000..687c6c874f7a016abbf1888c59f5a7be680d82c1 --- /dev/null +++ b/ci/tools/openeuler-purl/syft.py @@ -0,0 +1,294 @@ +import asyncio +import json +import os +import ast +import sys +import urllib.parse + +import aiofiles +from loguru import logger +from tqdm import tqdm + +# logging.basicConfig(level=logging.DEBUG) +logger.remove() +default_id = logger.add(sys.stderr, level="INFO", filter=lambda x: 'INFO' == x['level'].name) +logger.add("./logs/syft.log", level="DEBUG", backtrace=True, diagnose=True, mode="w") +# err_id = logger.add("./logs/syft_error.log", level="ERROR", backtrace=True, diagnose=True, mode="w", +# filter=lambda x: 'ERROR' == x['level'].name) +# debug_id = logger.add("./logs/syft_debug.log", level="DEBUG", backtrace=True, diagnose=True, mode="w", +# filter=lambda x: 'DEBUG' == x['level'].name) +# 自定义日志记录器 +# logger.level("ERR_FILE", no=40, color='', icon='❌') + +# 记录已解析的文件数量 +global cataloged_count + +# 记录解析失败的包 +global catalog_error_packages + +# 记录解析结果为空的包 +global catalog_none_packages + + +async def show_bar(max_length): + """ + 显示进度条 + :param max_length: + :return: + """ + # 初始化已解析个数为 0 + bar = tqdm(file=sys.stderr, initial=0, total=max_length, mininterval=0.1, maxinterval=0.1) + bar.set_description("Processing: ") + current_count = 0 + while cataloged_count <= max_length: + update_step = cataloged_count - current_count + bar.update(update_step) + current_count = cataloged_count + if cataloged_count == max_length: + bar.close() + return + await asyncio.sleep(0.1) + + +class SyftResolver: + """ + syft 批处理解析器工作的类,处理解析流程中的各种逻辑 + """ + + def __init__(self, basedir, syft_executable, template_path): + """ + 初始化必要的参数 + :param basedir: + :param syft_executable: + :param template_path: + """ + self.__version_cmds_dict = None + self.__version = None + self.__output_dict = None + self.__basedir = basedir + self.__syft_executable = syft_executable + self.__template_path = template_path + + def set_version(self, version): + self.__version = version + self.__output_dict = {"version": version, "data": []} + self.__version_cmds_dict = {"version": version, "cmd_dicts": []} + + @property + def output_dict(self): + return self.__output_dict + + @property + def version(self): + return self.__version + + @property + def basedir(self): + return self.__basedir + + @property + def version_cmds_dict(self): + return self.__version_cmds_dict + + async def run_syft_async(self, semaphore, cmd_dict): + """ + 异步执行 syft 命令解析包数据 + :param semaphore: 信号量以限制并发数量 + :param cmd_dict: 要解析的文件以及解析所用的命令 + 解析得到的数据结构 {"filename": string, "cmd": string} + :return: + """ + global cataloged_count + async with semaphore: + syft_output_success_purl_dict = {} + filename = cmd_dict["filename"] + cmd = cmd_dict["cmd"] + proc = await asyncio.subprocess.create_subprocess_shell( + cmd, + stdout=asyncio.subprocess.PIPE, + stderr=asyncio.subprocess.PIPE + ) + stdout, stderr = await proc.communicate() + stdout_str = stdout.decode("utf-8") + # 去除不必要的 unicode 字符,避免输出到日志文件中的乱码 + stderr_str = stderr.decode("utf-8")\ + .replace("", "")\ + .replace(" ", "")\ + .replace("", "") + if stderr_str: + logger.error(f"\n{stderr_str}") + catalog_error_packages.append(filename) + cataloged_count += 1 + return + begin = stdout_str.find("{") + end = stdout_str.rfind("}") + 1 + syft_out_str = stdout_str[begin:end] + if syft_out_str: + # 尝试解决输出的文本中 npm 包解析时带 @ 的包名转义的问题 + # 如"pkg:npm/@types/d3-time@1.0.10" 转义 为 "pkg:npm/%40types/d3-time@1.0.10" + syft_out_str = urllib.parse.unquote_plus(syft_out_str) + # 删除转义字符 \, 否则会影响下面解析 json 字符串为python对象的过程 + syft_out_str = syft_out_str.replace("\\", "") + try: + syft_output_success_purl_dict = ast.literal_eval(syft_out_str) + except SyntaxError as e: + logger.error("analysing {} has error: {}", filename, e.text) + logger.error(f"stdout: {stdout_str} \n stderr: {stderr_str}") + catalog_error_packages.append(filename) + cataloged_count += 1 + return + else: + logger.error("execute error: unable to get syft analysed result") + if len(syft_output_success_purl_dict.get("purls")) != 0: + self.output_dict["data"].append(syft_output_success_purl_dict) + else: + logger.debug("syft can not resolve purl in the package: {}", filename) + catalog_none_packages.append(filename) + cataloged_count += 1 + + def dump_to_json(self, output_filepath): + """ + 异步保存内容到指定的 json 文件 + :return: + """ + # 写入 JSON 数据 + with open(output_filepath, "w") as fs: + json.dump(self.output_dict, fs) + + def get_versions(self): + """ + 获取包已下载的所有系统版本 + :return: + """ + return [dirname for dirname in os.listdir(self.basedir) if "openEuler-2" in dirname] + + def set_cmds_dict(self): + """ + 获取当前系统版本所有包的解析命令 + """ + logger.info("current catalog version: {}", self.version) + cmd_dict_list = [] + syft_exec = self.__syft_executable + template_path = self.__template_path + version_path = os.path.realpath(os.path.join(self.basedir, self.version)) + package_path = os.path.join(version_path, "packages") + filename_list = os.listdir(package_path) + for filename in filename_list: + if ".rpm" in filename: + cmd_dict = {} + filepath = os.path.join(package_path, filename) + cmd = f"{syft_exec} {filepath} -o template -t {template_path}" + cmd_dict["filename"] = filename + cmd_dict["cmd"] = cmd + cmd_dict_list.append(cmd_dict) + self.version_cmds_dict["cmd_dicts"] = cmd_dict_list + + async def save_catalog_error_packages(self, packages): + """ + 保存解析异常的包到日志 + :param packages: + :return: + """ + async with aiofiles.open(f"./logs/syft_catalog_error_list-{self.version}.log", "w") as fs: + for package_name in packages: + await fs.write(f"{package_name}\n") + + async def save_catalog_none_packages(self, packages): + """ + 保存解析结果为空的包到日志 + :param packages: + :return: + """ + async with aiofiles.open(f"./logs/syft_catalog_none_list-{self.version}.log", "w") as fs: + for package_name in packages: + await fs.write(f"{package_name}\n") + + async def run(self, limit=5): + """ + 异步主函数,包括三个步骤 + 1. 根据当前系统版本的所有包,构造 syft 的解析命令语句 + 2. 提交所有解析任务,并发运行 + 3. 记录解析结果,将解析异常的包记录到日志中 + :param limit: + :return: + """ + global cataloged_count + self.set_cmds_dict() + semaphore = asyncio.Semaphore(limit) + tasks = [self.run_syft_async(semaphore, cmd_dict) for cmd_dict in self.version_cmds_dict["cmd_dicts"]] + tasks_count = len(tasks) + + # 初始化进度条显示变化需要的变量 + cataloged_count = 0 + + tasks.append(show_bar(tasks_count)) + await asyncio.gather(*tasks) + # 保存解析有问题的包到日志中 + await self.save_catalog_error_packages(catalog_error_packages) + await self.save_catalog_none_packages(catalog_none_packages) + logger.info("{} Catalog Finished, But Some Package Have A Some Problem When Catalogging " + ", Try Check Or Manually Catalog Them!!!", + self.version) + logger.info("These Packages Catalog Error: ") + for p in catalog_error_packages: + logger.info(" {}", p) + logger.info("\n\n") + logger.info("These Packages Catalog Success, But Purls Item Is None: ") + for p in catalog_none_packages: + logger.info(" {}", p) + logger.info("You Can Also Look What These Packages In ./logs/syft_catalog_error_list-{} " + "And ./logs/syft_catalog_error_list-{} \n\n", + self.version, self.version) + + +if __name__ == '__main__': + dir_path = "" + syft = "" + template = "" + syft_limit = 10 + with open("configs.json", "r") as f: + configs = json.load(f) + # 从配置文件中获取必要的变量 + if configs.get('dir_path'): + dir_path = configs["dir_path"] + else: + logger.error("dir_path is not set") + exit(0) + if configs.get('syft'): + syft = configs["syft"] + syft = os.path.realpath(syft) + if not os.path.exists(syft): + logger.error("syft config is error") + exit(0) + else: + logger.error("syft executable path is not set") + exit(0) + if configs.get('template'): + template = configs["template"] + template = os.path.realpath(template) + if not os.path.exists(template): + logger.error("template config is error") + exit(0) + else: + logger.error("template path path is not set") + exit(0) + syft_limit = configs["syft_limit"] if configs.get('syft_limit') else 10 + resolver = SyftResolver(basedir=dir_path, syft_executable=syft, template_path=template) + + versions = resolver.get_versions() + if not versions: + raise "没有获取到版本,请检查工作目录!!" + logger.info("待解析的版本列表:") + for v in versions: + logger.info(" {}", v) + for ver in versions: + # 初始化解析异常的包的存放列表 + catalog_error_packages = [] + catalog_none_packages = [] + resolver.set_version(version=ver) + asyncio.run(resolver.run(limit=syft_limit)) + # 输出到解析结果到文件中 + output = resolver.output_dict + output_json_path = f"{os.path.join(dir_path, ver)}/all_packages_purls.json" + resolver.dump_to_json(output_filepath=output_json_path) + logger.info("全部解析完成!!")