Downloads the latest FFmpeg Win64 static build from GitHub then extracts ffmpeg.exe, ffprobe.exe, and ffplay.exe to ./bin.
# #############################################################################
# FFmpeg update script
#
# Downloads the latest FFmpeg Win64 static build from https://github.com/BtbN/FFmpeg-Builds/releases/latest
# then extracts ffmpeg.exe, ffprobe.exe, and ffplay.exe to ./bin
#
# Usage:
# PS> .\update-ffmpeg.ps1
#
# Author....: Jon LaBelle
# Date......: July 29, 2023
# Snippet...: https://jonlabelle.com/snippets/view/powershell/download-latest-ffmpeg-static-build
# #############################################################################
$SCRIPTDIR = Split-Path $script:MyInvocation.MyCommand.Path
# $ProgressPreference = 'SilentlyContinue'
function DownloadWithRetry([string] $Url, [string] $DownloadLocation, [int] $Retries)
{
while ($true)
{
try
{
Invoke-WebRequest $Url -OutFile $DownloadLocation
break
}
catch
{
$exceptionMessage = $_.Exception.Message
Write-Output "Failed to download '$Url': $exceptionMessage"
if ($Retries -gt 0)
{
$Retries--
Write-Output "Waiting 10 seconds before retrying. Retries left: $Retries"
Start-Sleep -Seconds 10
}
else
{
$exception = $_.Exception
throw $exception
}
}
}
}
function ExtractFromArchive([string] $Path, [string] $DestinationPath, [string] $Filter)
{
# ensure the output folder exists
if ((Test-Path -Path $DestinationPath) -eq $false)
{
$null = New-Item -Path $DestinationPath -ItemType Directory -Force
Write-Output "Created output directory: $DestinationPath"
}
# load ZIP methods
Add-Type -AssemblyName System.IO.Compression.FileSystem
# open ZIP archive for reading
$zip = [System.IO.Compression.ZipFile]::OpenRead($Path)
# find all files in ZIP that match the filter (i.e. file extension)
$zip.Entries | Where-Object { $_.FullName -like $Filter } | ForEach-Object {
# extract the selected items from the ZIP archive and copy them to the out folder
$fileName = $_.Name
$outFile = Join-Path -Path $DestinationPath -ChildPath $fileName
[System.IO.Compression.ZipFileExtensions]::ExtractToFile($_, $outFile, $true)
Write-Output "Extracted $fileName to $outFile"
}
# close ZIP file
$zip.Dispose()
}
function DownloadLatestRelease([string] $DownloadLocation)
{
$response = Invoke-RestMethod -Method Get -Uri "https://api.github.com/repos/BtbN/FFmpeg-Builds/releases/latest"
$downloadUrl = $response.assets.browser_download_url | Where-Object { $_ -match "win64-gpl\.zip" } | Select-Object -First 1
if ($downloadUrl.length -eq 0)
{
Write-Error "Latest release not found."
exit 1
}
Write-Output "Downloading latest release from '$downloadUrl' to '$DownloadLocation' ..."
DownloadWithRetry -Url $downloadUrl -DownloadLocation $DownloadLocation -Retries 5
}
function main()
{
# Download latest release
$downloadLocation = Join-Path -Path $SCRIPTDIR -ChildPath "latest.zip"
DownloadLatestRelease -DownloadLocation $downloadLocation
# Extract *.exe files to ./bin directory
$outputDirectory = Join-Path -Path $SCRIPTDIR -ChildPath "bin"
ExtractFromArchive -Path $downloadLocation -DestinationPath $outputDirectory -Filter "*.exe"
}
main