English | 简体中文
一个轻巧的命令行工具,帮助你查询一个项目/软件的最新版本号及各种相关信息,比如下载链接。
lastversion
可以从下面的网站找到一个项目的格式良好的最新的版本号。
- GitHub
- GitLab
- BitBucket
- PyPI
- Mercurial
- SourceForge
- Wikipedia
- 任何以 RSS/ATOM 订阅方式发布软件网站。
通常情况下,许多项目作者的一些做法会让我们难以寻找一个项目的最新版本及其版本号。
- 发布一个候选版本的时候忘记将其标记为预发布版本,而是作为一个正式版本去发布。比如版本标签为
v2.0.1-rc
但是在发布时并未标记为预发布版本。 - 在版本标签中加入无关的文本,例如
release-1.2.3
或name-1.2.3-2019
,或者其它类似的文本。 - 版本标签是否带有
v
前缀?今天可能带,但明天可能就不带了。我也是这样的 :)。 - 切换到另一种版本标签格式,例如从
v20150121
切换到v2.0.1
。
人与人之间难以保持一致。
有时候我们希望所有的软件都有一个固定格式的版本号,lastversion
可以帮助你,它可以让你查询某个项目的最新版本的同时返回一个固定格式的版本号,并可以获取下载链接等额外信息。
lastversion
主要用于自动化脚本,比如自动更新和持续集成等。
lastversion
使用了简单的 AI 来参与到检测中,
比如清理版本号中的无用信息,比如将 name-v1.2.3
修改为 1.2.3
,
也用它来检测发布者是否混淆了测试版和稳定版。
lastversion apache/incubator-pagespeed-ngx
#> 1.13.35.2
lastversion apache/incubator-pagespeed-ngx -d
#> downloaded incubator-pagespeed-ngx-v1.13.35.2-stable.tar.gz
lastversion apache/incubator-pagespeed-ngx -d pagespeed.tar.gz
#> downloads with chosen filename
lastversion https://transmissionbt.com/
#> 3.0
sudo yum -y install https://extras.getpagespeed.com/release-latest.rpm
sudo yum install lastversion
用 pip
安装是最简单的方法。
pip install lastversion
一般来说,lastversion
只需要一个参数,即一个仓库的 URL(或 用户名/仓库名),例如:
lastversion https://github.com/gperftools/gperftools
与之等价的命令为
lastversion gperftools/gperftools
如果你想偷懒,不想复制粘贴项目的 URL, 你可以直接使用项目的名字作为参数,这将会使用仓库搜索 API(速度比较慢)。
下面的这条命令可以让你知道 Linux 的最新版本。
lastversion linux
或者查询 Wordpress 的最新版本。
lastversion wordpress
self
是主参数中的一个特殊值,它可以查找 lastversion
的最新版本,例如:
lastversion self
你可以通过 --help
查看和输出控制(行为)相关的选项。
usage: lastversion [-h] [--pre] [--verbose] [-d [FILENAME]]
[--format {version,assets,source,json,tag}] [--assets]
[--source] [-gt VER] [-b MAJOR] [--only ONLY]
[--filter REGEX] [-su]
[--at {github,gitlab,bitbucket,pip,hg,sf,website-feed,local}]
[-y] [--version]
[action] <repo or URL>
Find the latest software release.
positional arguments:
action Special action to run, e.g. download, install, test
<repo or URL> GitHub/GitLab/BitBucket/etc. repository in format
owner/name or any URL that belongs to it
optional arguments:
-h, --help show this help message and exit
--pre Include pre-releases in potential versions
--verbose Will give you an idea of what is happening under the hood
-d [FILENAME], --download [FILENAME]
Download with custom filename
--format {version,assets,source,json,tag}
Output format
--assets Returns assets download URLs for last release
--source Returns only source URL for last release
-gt VER, --newer-than VER
Output only if last version is newer than given
version
-b MAJOR, --major MAJOR, --branch MAJOR
Only consider releases of a specific major version,
e.g. 2.1.x
--only ONLY Only consider releases containing this text. Useful
for repos with multiple projects inside
--filter REGEX Filters --assets result by a regular expression
--having-asset [ASSET]
Only consider releases with this asset
-su, --shorter-urls A tiny bit shorter URLs produced
--at {github,gitlab,bitbucket,pip,hg,sf,website-feed,local}
If the repo argument is one word, specifies where to
look up the project. The default is via internal
lookup or GitHub Search
-y, --assumeyes Automatically answer yes for all questions
--version show program's version number and exit
--format
选项将会指定输出的格式。
version
默认值,输出格式最新的,格式良好的版本号。assets
会以换行分割的最新版本的 asset 的 URL(如果有多个 asset 的话),否则将为最新源码链接(通常为 *.tar.gz 或 *.zip)。source
将输出最新源码的链接(通常为 *.tar.gz 或 *.zip),即使最新版本同时发布了其它的 asset。json
此格式可以被 Python 程序处理。tag
只输出最新版本的标签名。
asset
在本文是指一个可下载的文件,
一般为可执行文件。例如一个项目发布的时候会连带发布各个平台的可执行程序,让用户无需编译源代码即可使用。
你可以查看最新版本的 asset 或源代码文件的 URL 通过选择适当的 --format flag
。
你也可以使用 --source
去代替 --format source
,用 --assets
代替 --format assets
,例如:
lastversion --assets mautic/mautic
#> https://github.com/mautic/mautic/archive/2.15.1/mautic-2.15.1.tar.gz
默认情况下, lastversion
会根据不同的 OS 过滤掉一些 --assets
的输出。
在 Linux 上谁需要 .exe
呢?
你可以使用 --filter
来覆盖掉这一行为,
它使用一个正则表达式作为参数。
如果你不想根据 OS 过滤掉 asset,你可以直接使用 --filter
来匹配所有的asset。
你你可以很优雅地使用 --filter
来代替 grep
命令,例如:
lastversion --assets --filter win REPO
你可以使用 lastversion
来下载最新版本的 asset 和源代码。
下载最新的 Mautic 源码:
lastversion mautic/mautic --download
自定义下载的文件名(只对下载源代码有效并且此为默认设置):
lastversion mautic/mautic --download mautic.tar.gz
你也可以使用 lastversion
输出源代码或者 asset 的 URL 并下载它,例如:
wget $(lastversion --assets mautic/mautic)
上面这行命令会下载所有的最新的稳定版的 asset,即两个 .zip
文件。
为什么会这样能够?
因为 lastversion
会输出在两个 .zip
文件的 URL 并通过换行分割,wget
也很聪明地下载每行的 URL,很神奇吧 :)。
如果最新发布中没有 asset,则会直接下载源代码。
如果你只想下载源代码,你可以使用 --source
,例如:
wget $(lastversion --source mautic/mautic)
lastversion
认为最新版本是稳定版本或者没有被标记为测试的版本。
如果你不这么认为,你可以使用 --pre
将预发布版本作为最新版。
lastversion --pre mautic/mautic
#> 2.15.2b0
一些项目可能会一起在不同的分支上发布稳定版本,
典型的例子就是 PHP,你可以使用 --major
去指定某个主版本,例如:
lastversion php/php-src --major 7.2
这行命令会输出当前的 PHP 稳定的版本,其版本格式为 7.2.x
。
你也可以使用下面这种简单的写法来达到几乎相同的效果,即在冒号后指定主版本。
lastversion php:7.2
你可以直接指定一个具体的版本,例如:
lastversion php:7.2.33 --assets
有时候一个项目可能已经发布了新的版本,但是相关的 assets 并没有第一时间发布,比如各大平台的可执行程序。
如果你只想要某些 assets,你可以使用 --having-asset
来实现。
lastversion telegramdesktop/tdesktop --having-asset "Linux 64 bit: Binary"
--having-asset
接收一个正则表达式用于匹配 assets 的名称。
获取包含 macOS 平台的安装程序的最新版本号。
lastversion telegramdesktop/tdesktop --having-asset "~\.dmg$"
如果你不为 --having-asset
指定任何值,那么将匹配所有 assets,及只要包含任意的 assets 均可。
lastversion telegramdesktop/tdesktop --having-asset
操作系统通常不会在 Github 发布版本,你通常只能通过官方网站等渠道才能获取,
不过 lastversion
可以做到这一点。
lastversion
的做法简单粗暴,将常见的操作系统名称及其对应的 Wikipedia 联系起来并硬编码到程序中。
lastversion rocky #> 8.4
lastversion windows #> 10.0.19043.1081
lastversion ios #> 14.6
你也可以提供某个软件/操作系统的完整的 Wikipedia 的 URL 来完成相同的操作。
lastversion https://en.wikipedia.org/wiki/Rocky_Linux #> 8.4
lastversion https://nginx.org --major stable #> 1.16.1
lastversion https://nginx.org --major mainline #> 1.17.9
上面这行命令其实是检查 hg.nginx.org
,它是一个 Mercurial 网络仓库。
下面这样也是可以的:
lastversion https://hg.example.com/project/
Mercurial 仓库现在比较少见,lastversion
支持它主要是为了 NGINX。
大多数 Python 的库和应用程序都托管在 PyPI 上。要获取 PyPI 上项目的版本,你可以执行下面的命令。
lastversion https://pypi.org/project/requests/
如果您不想写太长的参数,只想写仓库名的话,可以使用--at pip
,就像下面这样。
lastversion requests --at pip
如果一个项目提供 .rpm
资源且你的 OS 可以使用 yum
或 dnf
,
你可以直接安装该项目的 RPM,就像下面这样:
sudo lastversion install mailspring
上面这行命令从 MailSpring
的最新版本中找到 .rpm
并传递给 yum
或 dnf
。
你甚至可以通过 cron 实现自动更新,这将确保你在某个包为最新版本,就像下面这样:
@daily /usr/bin/lastversion install mailspring -y 2>/dev/null
如果 MailSpring 的 Github 仓库发布了一个更新的 .rpm
,
那么这个 .rpm
会被自动安装,以确保你的版本的最新的。
你甚至可以在更新完毕后收到邮件提醒(cron 的标准功能)。
不用说都知道,这种方式会导致我们不知道潜在的缺失的依赖。
所以,只有当 yum
库没有你所需要的东西的时候才使用 lastversion install ...
。
test
命令可以用来排除故障或者简单地格式化一个版本标签。
lastversion test 'blah-1.2.3-devel' # > 1.2.3.dev0
lastversion test '1.2.x' # > False (no clear version)
lastversion test '1.2.3-rc1' # > 1.2.3rc1
你可以使用 lastversion
轻松地比较两个版本号并输出更加新的那个。
lastversion 1.2.3 -gt 1.2.4
#> 1.2.4
当你想要构建某个上游的包的时候,而且此时你也有这个包上次构建时的版本号,那么自动构建将会十分容易。
CURRENTLY_BUILT_VER=1.2.3 # 存储在其它位置比如文件中
LASTVER=$(lastversion repo/owner -gt ${CURRENTLY_BUILT_VER})
if [[ $? -eq 0 ]]; then
# 检测到最新版本,触发构建流程。
# ....
fi
注意,-gt
参数的功能类似于 bash
中的 -gt
比较。
还有更多内容,如果你想让这变得更靠谱的话,
请听我唠叨:
RPM auto-builds with lastversion
LATEST_KERNEL=$(lastversion linux -gt $(uname -r | cut -d '-' -f 1))
if [[ $? -eq 0 ]]; then
echo "I better update my kernel now, because ${LATEST_KERNEL} is there"
else
echo "My kernel is latest and greatest."
fi
退出状态码是传递命令执行成功与否的常用手段。对于lastversion
来说,
如果命令执行成功则返回 0
,其它返回值的含义:
返回值 1
代表仓库不存在或者没有发布过版本。
返回值 2
代表没有比 -gt
所指定的版本更新的版本。
返回值 3
代表 --filter
过滤掉了所有的 URL,即正则表达式没有匹配到任何 URL。
通过 API 来获取最新版本很难,因为 Github API 不允许按照时间顺序获取 tag, 而且一些仓库会更换它的版本号格式,所以我们不能认为最高版本号代表着最新版本。
我们必须获取每个标签的提交日期,并检查它是否真的是最近提交的。 因此,对于大型仓库来说速度会比较慢,因为这些仓库可能有很多标签。
因此,lastversion
会缓存的 API 响应内容以提高响应速度,
它做了有条件的 ETag 验证,根据 GitHub API 的规定,ETag 验证不计入速率限制。
在 Linux 下缓存内容存储在 ~/.cache/lastversion
。
建议设置你的 GitHub API token。
仅仅只需要 API token,你可以取消这个 Token 的所有权限,
然后你可以在 ~/.bashrc
文件中添加下列内容来提升你的请求速度上限。
export GITHUB_API_TOKEN=xxxxxxxxxxxxxxx
GITHUB_API_TOKEN
和 GITHUB_TOKEN
这两个环境变量均可被识别,
且当两者同时存在时优先使用前者。
对于 GitLab, 你可以使用 Personal Access Token:
export GITLAB_PA_TOKEN=xxxxxxxxxxxxxxx
然后运行 source ~/.bashrc
,之后,lastversion
将会使用 TOKEN 来更快地调用 API。
你可以使用 lastversion.has_update(...)
来查找某个项目是否已经有更新。
from lastversion import lastversion
latest_version = lastversion.has_update(repo="mautic/mautic", current_version='1.2.3')
if latest_version:
print(f'Newer Mautic version is available: {latest_version}')
else:
print('No update is available')
lastversion.has_update(...)
函数接受一个仓库的 URL,或者形如 用户名/仓库名
这样的字符串,第二个参数为当前版本。
如果你要检查 PyPI 上的项目版本,请使用参数 at='pip'
,
这样就不用传递一个完整的 PyPI 项目的 URL 了,并且避免错误地从其它平台如 Github 上获取信息。
下面的示例代码可以检查 Requests
最新的版本。
from lastversion import lastversion
latest_version = lastversion.has_update(repo="requests", at='pip', current_version='1.2.3')
if latest_version:
print(f'Newer Requests library is available: {latest_version}')
else:
print('No update is available')
然后它会返回下面的一个返回值:
- Version 对象
False
如果没有更加新的版本
你也可以调用 lastversion.latest(...)
函数来获取最新版本的信息。
from lastversion import lastversion
from packaging import version
latest_mautic_version = lastversion.latest("mautic/mautic", output_format='version', pre_ok=True)
print(f'Latest Mautic version: {latest_mautic_version}')
if latest_mautic_version >= version.parse('1.8.1'):
print('It is newer')
如果 output_format='version'
(默认),函数会返回一个
Version 对象
或者 none
。所以你可以进行如版本比较等工作。
如果指定参数 output_format='dict'
,
函数会返回一个 dict
(字典)或 False
,
如果函数从不同的平台(如 Github 和 BitBucket)获取同一个项目的版本信息,
那么字典的 Key
(键)可能会不同,
但可以保证一定会有下列的 Key
(键)。
version
:Version
对象,包含被找到的版本,如 1.2.3
。
source
:字符串,表示来源平台, 如github
或gitlab
。tag_date
:datetime
对象, 表示发布的时间,如2020-12-15 14:41:39
。from
:字符串, 项目的完整 URL。tag_name
:字符串,版本标签名。
lastversion.latest
函数接受三个参数
repo
,仓库的 URL,或者形如用户名/仓库名
这样的字符串,例如https://github.com/dvershinin/lastversion/issues
。format
,它接受的值同--help
所说明的一样。不过在Python
代码中还可以指定为dict
。pre_ok
,布尔值,表示预发布版本是否可以作为最新版本。at
,该项目所在的平台,取值仅可能为github
,gitlab
,bitbucket
,pip
,hg
,sf
,website-feed
,local
。