1+ <# PSScriptInfo
2+
3+ .VERSION 2.0
4+
5+ .GUID a6048a09-3e66-467a-acd4-ce3e97098a65
6+
7+ .AUTHOR velecky@velecky.onmicrosoft.com modified by Nick Rodriguez
8+
9+ .PROJECTURI https://www.powershellgallery.com/packages/Speedtest/2.0
10+
11+ . DESCRIPTION
12+ WAN speed test
13+
14+ #>
15+
16+ [CmdletBinding ()]
17+ param (
18+ [int ]$Repetitions = 4
19+ )
20+
21+ function Invoke-SpeedTest {
22+ param (
23+ [string ]$UploadUrl
24+ )
25+
26+ $topServerUrlSpilt = $UploadUrl -split ' upload'
27+ $url = $topServerUrlSpilt [0 ] + ' random2000x2000.jpg'
28+ $col = New-Object System.Collections.Specialized.NameValueCollection
29+ $wc = New-Object System.Net.WebClient
30+ $wc.QueryString = $col
31+ $downloadElaspedTime = (Measure-Command { $webpage1 = $wc.DownloadData ($url ) }).TotalMilliseconds
32+ $downSize = ($webpage1.length + $webpage2.length ) / 1 MB
33+ $downloadSize = [Math ]::Round($downSize , 2 )
34+ $downloadTimeSec = $downloadElaspedTime * 0.001
35+ $downSpeed = ($downloadSize / $downloadTimeSec ) * 8
36+ $downloadSpeed = [Math ]::Round($downSpeed , 2 )
37+
38+ Write-Verbose " Downloaded $downloadSize MB in $downloadTimeSec seconds at a speed of $downloadSpeed mbps"
39+
40+ return $downloadSpeed
41+ }
42+
43+ # Interact with speedtest page avoiding api
44+ $objXmlHttp = New-Object - ComObject MSXML2.ServerXMLHTTP
45+ $objXmlHttp.Open (" GET" , " http://www.speedtest.net/speedtest-config.php" , $False )
46+ $objXmlHttp.Send ()
47+ [xml ]$content = $objXmlHttp.responseText
48+
49+ # Select closest server based on lat/lon
50+ $oriLat = $content.settings.client.lat
51+ $oriLon = $content.settings.client.lon
52+ Write-Verbose " Latitude: $oriLat "
53+ Write-Verbose " Longitude: $oriLon "
54+
55+ # Make another request, this time to get the server list from the site
56+ $objXmlHttp.Open (" GET" , " http://www.speedtest.net/speedtest-servers.php" , $False )
57+ $objXmlHttp.Send ()
58+ [xml ]$ServerList = $objXmlHttp.responseText
59+
60+ # Cons contains all of the information about every server in the speedtest.net database
61+ $cons = $ServerList.settings.servers.server
62+
63+ # Calculate servers relative closeness by doing math against latitude and longitude
64+ Write-Verbose " Searching for closest geographical servers from list of $ ( $cons.Count ) ..."
65+ foreach ($val in $cons ) {
66+ $R = 6371
67+ $pi = [Math ]::PI
68+
69+ [float ]$dlat = ([float ]$oriLat - [float ]$val.lat ) * $pi / 180
70+ [float ]$dlon = ([float ]$oriLon - [float ]$val.lon ) * $pi / 180
71+ [float ]$a = [math ]::Sin([float ]$dLat / 2 ) * [math ]::Sin([float ]$dLat / 2 ) + [math ]::Cos([float ]$oriLat * $pi / 180 ) * [math ]::Cos([float ]$val.lat * $pi / 180 ) * [math ]::Sin([float ]$dLon / 2 ) * [math ]::Sin([float ]$dLon / 2 )
72+ [float ]$c = 2 * [math ]::Atan2([math ]::Sqrt([float ]$a ), [math ]::Sqrt(1 - [float ]$a ))
73+ [float ]$d = [float ]$R * [float ]$c
74+
75+ $serverInformation += @ ([pscustomobject ]@ {
76+ Distance = $d
77+ Country = $val.country
78+ Sponsor = $val.sponsor
79+ Url = $val.url
80+ })
81+ }
82+
83+ $serverInformation = $serverInformation | Sort-Object - Property distance
84+
85+ $speedResults = @ ()
86+
87+ for ($i = 0 ; $i -lt $Repetitions ; $i ++ ) {
88+ $url = $serverInformation [$i ].url
89+ Write-Verbose " Download attempt ($ ( $i + 1 ) of $Repetitions ) from $url ..."
90+ $speed = Invoke-SpeedTest $url
91+ $speedResults += $speed
92+ }
93+
94+ $results = $speedResults | Measure-Object - Average - Minimum - Maximum
95+
96+ New-Object psobject - Property @ {
97+ " Fastest (mbps)" = $results.Maximum
98+ " Slowest (mbps)" = $results.Minimum
99+ " Average (mbps)" = $results.Average
100+ }
0 commit comments