This script below is an extension of this script PowerShell Download Latest WordPress Plugin.
This download script uses two XML files, primary XML will serve as the configuration file where the secondary will have the plugins that we currently have installed and then this script will run through the XML and download any free plugins that need an update.
This script will read the latest version of the plugin from WordPress.org and update the XML file’s
Source Code
<?xml version="1.0" encoding="UTF-8"?>
<pluginconfig>
<SFTP>
<FTPHost>ftp://192.168.1.16/html/</FTPHost>
<FTPUser>UserName</FTPUser>
<FTPPass>Password</FTPPass>
<FTPSource>C:\temp\WordPress\WordPressUpdates\</FTPSource>
</SFTP>
</pluginconfig>
<?xml version="1.0" encoding="UTF-8"?>
<pluginlist>
<plugin>
<title>Akismet</title>
<url>https://wordpress.org/plugins/akismet/</url>
<downloadurl>https://downloads.wordpress.org/plugin/akismet.3.1.5.zip</downloadurl>
<currentversion>3.1.5</currentversion>
<installedversion>3.1.4</installedversion>
</plugin>
</pluginlist>
clear
# Variables - Start
$XMLServerConfig = "c:\temp\WordPress\WordPress_Free_Plugin_Config.xml"
$XMLPluginList = "c:\temp\WordPress\WordPress_Free_Plugin_List.xml"
$UpdatedPluginFound = 0
# Variables - Stop
# Plugin Config (XML) - Start
[xml]$pluginconfig = Get-Content $XMLServerConfig
foreach ($obj in $pluginconfig.pluginconfig.SFTP)
{
$FTPHost = $obj.FTPHost
$FTPUser = $obj.FTPUser
$FTPPass = $obj.FTPPass
$UploadFolder = $obj.FTPSource
}
# Plugin Config (XML) - Start
# Plugin List (XML)
[xml]$pluginlist = Get-Content $XMLPluginList
# Update current version on our XML from WordPress.org - Start
foreach ($obj in $pluginlist.pluginlist.Plugin)
{
#[System.Console]::Write("`r`nPlugin: {0}", $obj.title)
#[System.Console]::Write("`r`n URL: {0}", $obj.url)
#[System.Console]::Write("`r`n Installed Version: {0}", $obj.installedversion)
# Plugin URL
$URI = $obj.url
# Plugin Download URL
$DownloadURL = $obj.downloadurl
# This is the plugin version to check against
$PluginVersion = $obj.installedversion
$HTML = Invoke-WebRequest -Uri $URI
#$HTML.Links.Count
$PluginName = $HTML.AllElements | WHERE -Property itemprop -eq "name" | Select -First 1 -ExpandProperty innerText
$PluginName = $PluginName.Trim()
$downloadURL = $HTML.Links | WHERE -Property itemprop -eq "downloadUrl" | SELECT -Property href
$downloadURLText = $HTML.Links | WHERE -Property itemprop -eq "downloadUrl" | SELECT -Property innerText
$downloadURL = $downloadURL -replace "@{href=", ""
$downloadURL = $downloadURL -replace "}", ""
$downloadURL = $downloadURL.Trim()
$downloadURLText = $downloadURLText -replace "@{innerText=Download Version ", ""
$downloadURLText = $downloadURLText -replace "}", ""
$downloadURLText = $downloadURLText.Trim()
$pluginlist.pluginlist.Plugin | Where-Object {$_.title -eq $obj.title} | ForEach-Object {$_.currentversion = $downloadURLText}
$pluginlist.pluginlist.Plugin | Where-Object {$_.title -eq $obj.title} | ForEach-Object {$_.downloadurl = $downloadURL}
$pluginlist.Save("C:\temp\WordPress_Free_Plugin_List.xml")
}
# Update current version on our XML from WordPress.org - Stop
# Download latest version if different - start
foreach ($obj in $pluginlist.pluginlist.Plugin)
{
if($obj.installedversion -eq $obj.currentversion)
{
#Write-Output "`r`nLastest Version, move on to the next link"
}
else
{
[System.Console]::Write("`r`nPlugin: {0}", $obj.title)
[System.Console]::Write("`r`n URL: {0}", $obj.url)
[System.Console]::Write("`r`n Current Version: {0}", $obj.installedversion)
[System.Console]::Write("`r`n Installed Version: {0}", $obj.installedversion)
Write-Output "`r`nOut Dated Version, will now download"
# URL Parameter
$WebURL = $obj.downloadurl
# If directory doesn't exist create the directory
if((Test-Path $UploadFolder) -eq 0)
{
mkdir $UploadFolder;
#cd $UploadFolder;
}
# We assume the file you download is named what you want it to be on your computer
$FileName = [System.IO.Path]::GetFileName($WebURL)
# Concatenate the two values to prepare the download
$FullFilePath = "$($UploadFolder)$($FileName)"
# Give a basic message to the user to let them know what we are doing
Write-Output "Downloading '$WebURL' to '$FullFilePath'"
$uri = New-Object "System.Uri" "$WebURL"
$request = [System.Net.HttpWebRequest]::Create($uri)
$request.set_Timeout(15000) #15 second timeout
$response = $request.GetResponse()
$totalLength = [System.Math]::Floor($response.get_ContentLength()/1024)
$responseStream = $response.GetResponseStream()
$targetStream = New-Object -TypeName System.IO.FileStream -ArgumentList $FullFilePath, Create
$buffer = new-object byte[] 10KB
$count = $responseStream.Read($buffer,0,$buffer.length)
$downloadedBytes = $count
while ($count -gt 0)
{
[System.Console]::Write("`r`nDownloaded {0}K of {1}K", [System.Math]::Floor($downloadedBytes/1024), $totalLength)
$targetStream.Write($buffer, 0, $count)
$count = $responseStream.Read($buffer,0,$buffer.length)
$downloadedBytes = $downloadedBytes + $count
}
$targetStream.Flush()
$targetStream.Close()
$targetStream.Dispose()
$responseStream.Dispose()
# Give a basic message to the user to let them know we are done
Write-Output "`r`nDownload complete"
# Extract Download - Start
$Shell = new-object -com shell.application
# Get the name of the Zip file
$Zip = $Shell.NameSpace($FullFilePath)
#Expand/Extract each file from the zip file
foreach($Item in $Zip.items())
{
$Shell.Namespace($UploadFolder).copyhere($Item)
}
# Extract Download - Stop
$pluginlist.pluginlist.Plugin | Where-Object {$_.title -eq $obj.title} | ForEach-Object {$_.installedversion = $obj.currentversion}
$pluginlist.Save($XMLPluginList)
Remove-Item $FullFilePath
}
}
# Download latest version if different - stop
#Upload Plugins - Start
$webclient = New-Object System.Net.WebClient
$webclient.Credentials = New-Object System.Net.NetworkCredential($FTPUser,$FTPPass)
$SrcEntries = Get-ChildItem $UploadFolder -Recurse
$Srcfolders = $SrcEntries | Where-Object{$_.PSIsContainer}
$SrcFiles = $SrcEntries | Where-Object{!$_.PSIsContainer}
# Create FTP Directory/SubDirectory If Needed - Start
foreach($folder in $Srcfolders)
{
$SrcFolderPath = $UploadFolder -replace "\\","\\" -replace "\:","\:"
$DesFolder = $folder.Fullname -replace $SrcFolderPath,$FTPHost
$DesFolder = $DesFolder -replace "\\", "/"
# Write-Output $DesFolder
try
{
$makeDirectory = [System.Net.WebRequest]::Create($DesFolder);
$makeDirectory.Credentials = New-Object System.Net.NetworkCredential($FTPUser,$FTPPass);
$makeDirectory.Method = [System.Net.WebRequestMethods+FTP]::MakeDirectory;
$makeDirectory.GetResponse();
#folder created successfully
}
catch [Net.WebException]
{
try {
#if there was an error returned, check if folder already existed on server
$checkDirectory = [System.Net.WebRequest]::Create($DesFolder);
$checkDirectory.Credentials = New-Object System.Net.NetworkCredential($FTPUser,$FTPPass);
$checkDirectory.Method = [System.Net.WebRequestMethods+FTP]::PrintWorkingDirectory;
$response = $checkDirectory.GetResponse();
#folder already exists!
}
catch [Net.WebException] {
#if the folder didn't exist
}
}
}
# Create FTP Directory/SubDirectory If Needed - Stop
# Upload Files - Start
foreach($entry in $SrcFiles)
{
$SrcFullname = $entry.fullname
$SrcName = $entry.Name
$SrcFilePath = $UploadFolder -replace "\\","\\" -replace "\:","\:"
$DesFile = $SrcFullname -replace $SrcFilePath,$FTPHost
$DesFile = $DesFile -replace "\\", "/"
# Write-Output $DesFile
$uri = New-Object System.Uri($DesFile)
$webclient.UploadFile($uri, $SrcFullname)
}
# Upload Files - Stop
Originally Posted on November 19, 2015
Last Updated on November 23, 2015
Last Updated on November 23, 2015
All information on this site is shared with the intention to help. Before any source code or program is ran on a production (non-development) system it is suggested you test it and fully understand what it is doing not just what it appears it is doing. I accept no responsibility for any damage you may do with this code.