├── LICENSE ├── README.md ├── benchmark ├── .cargo │ └── config ├── .gitignore ├── Cargo.toml ├── README.md └── src │ ├── main.rs │ ├── run.bat │ ├── run.command │ └── run.sh ├── cf.png ├── cf_219kb.png ├── cloudinary_36kb.png ├── curl-format.txt ├── test.py └── wp.png /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2021 Speed Test Demon 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # How to run speed test. 2 | 3 | ## the image to use 4 | 5 | The image you should probably use is: cf_219kb.png 6 | 7 | cf_219kb.png is an image that won't be compressed by Jetpack Wordpress. So, 8 | uploading that image to both Jetpack and CloudFront CDN will result in the same 9 | image being downloaded. 10 | 11 | curl-format.txt is how to run the speed test. 12 | 13 | Here is a shell script of how the speed test is run: 14 | 15 | ## the curl command 16 | 17 | ``` 18 | speedtest() { 19 | curl -w "@curl-format.txt" -o tmp -s $@ 20 | } 21 | ``` 22 | 23 | Please note that you do NOT want to `-o /dev/null`, as this will make curl 24 | will cleverly skip the data transfer (i.e. download) phase. Which will throw 25 | off your speed test measurement. So it is important to have `-o tmp` to 26 | actually download the file. 27 | 28 | ## the measurement 29 | 30 | the very first curl you should copy-paste into your notes. This curl is very 31 | interesting to measure because the 1st curl is always the slowest. This is 32 | usually the biggest variance between the CDNs. The first curl is an indicator 33 | of how fast the CDN loads for 1st-time visitors. 34 | 35 | the 2nd measurement is doing at least 10 subsequent curls, and taking the average. 36 | This measures how well a CDN caches content for multiple page visitors. 37 | # The script 38 | 39 | ## Installation: 40 | The script uses the pycurl module. To install it run: 41 | 42 | ``` 43 | $ pip3 install pycurl 44 | ``` 45 | 46 | If the installation fails you may need to install these dependencies: 47 | - libssl-dev 48 | - libcurl4-openssl-dev 49 | On Linux: 50 | 51 | ``` 52 | $ sudo apt-get install libssl-dev libcurl4-openssl-dev 53 | ``` 54 | 55 | ## Testing: 56 | 57 | To run it just run: 58 | 59 | ``` 60 | $python3 script.py < url > 61 | ``` 62 | ### Example: 63 | ``` 64 | $ python3 script.py 'https://d3va53q3li7xt1.cloudfront.net/wp-content/uploads/2021/05/shoeb-1024x576.png' 65 | ``` 66 | #### Output: 67 | ``` 68 | 10 requests done. Average: 69 | time_namelookup: 0.004422 70 | time_connect: 0.014404 71 | time_appconnect: 0.036274900000000006 72 | time_pretransfer: 0.03636879999999999 73 | time_redirect: 0.0 74 | time_starttransfer: 0.049656500000000006 75 | time_total: 0.0496897 76 | ``` 77 | 78 | # The other files 79 | 80 | ``` 81 | cf.png is 703KB. 82 | wp.png is 329KB. 83 | ``` 84 | 85 | Jetpack Wordpress compressed cf.png down to wp.png, which is why Jetpack won 86 | the initial speed test. 87 | -------------------------------------------------------------------------------- /benchmark/.cargo/config: -------------------------------------------------------------------------------- 1 | [target.x86_64-apple-darwin] 2 | rustflags=["-C", "link-arg=-mmacosx-version-min=10.8"] 3 | -------------------------------------------------------------------------------- /benchmark/.gitignore: -------------------------------------------------------------------------------- 1 | /target 2 | Cargo.lock 3 | -------------------------------------------------------------------------------- /benchmark/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "benchmark" 3 | version = "0.1.0" 4 | edition = "2018" 5 | 6 | # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html 7 | [profile.release] 8 | lto = true 9 | opt-level = 3 10 | codegen-units = 1 11 | 12 | [dependencies] 13 | anyhow = "1.0.42" 14 | curl = { version = "0.4.38", features = ["static-ssl", "static-curl"] } 15 | 16 | [target.'cfg(windows)'.dependencies] 17 | ipconfig = "0.2.2" 18 | 19 | [target.'cfg(unix)'.dependencies] 20 | sysinfo = "0.19.2" 21 | rustc-hash = "1.1.0" 22 | -------------------------------------------------------------------------------- /benchmark/README.md: -------------------------------------------------------------------------------- 1 | # The benchmark takes 36 Minutes in total to finish 2 | 3 | # How To Run the benchmark? 4 | 5 | ## For Windows 6 | 7 | Simply double click on the **"run"** file. 8 | 9 | ## For Mac OS 10 | 11 | Simply double click on the **"run"** file. 12 | 13 | ## For Linux 14 | 15 | Execute the **"run.sh"** script on the command-line. 16 | -------------------------------------------------------------------------------- /benchmark/src/main.rs: -------------------------------------------------------------------------------- 1 | use curl::easy::Easy; 2 | use std::{ 3 | thread::{self, JoinHandle}, 4 | env, 5 | io::{Write, Read}, 6 | fs::OpenOptions, 7 | time::Duration, 8 | fmt, 9 | sync::{Arc, atomic::{AtomicBool, Ordering}} 10 | }; 11 | 12 | #[cfg(target_family = "unix")] 13 | use rustc_hash::FxHashMap; 14 | #[cfg(target_family = "unix")] 15 | use sysinfo::{System, SystemExt, NetworkExt}; 16 | 17 | const COLLECT_URL: &str = "https://origin.speedtestdemon.com/collect.php"; 18 | 19 | fn main() -> Result<(), anyhow::Error> { 20 | let using_vpn = Arc::new(AtomicBool::new(false)); 21 | let finished = Arc::new(AtomicBool::new(false)); 22 | 23 | let using_vpn_clone = using_vpn.clone(); 24 | let finished_clone = finished.clone(); 25 | 26 | 27 | let vpn_check_thread = thread::spawn(move || vpn_check(&using_vpn_clone, &finished_clone)); 28 | 29 | let mut urls: Vec = env::args().collect(); 30 | 31 | let mut thread_handles: Vec> = vec![]; 32 | 33 | urls.remove(0); 34 | 35 | for url in urls { 36 | let using_vpn_clone = using_vpn.clone(); 37 | let handle = thread::spawn(move || benchmark(url, &using_vpn_clone)); 38 | thread_handles.push(handle); 39 | thread::sleep(Duration::from_secs(60)); 40 | } 41 | 42 | for handle in thread_handles { 43 | handle.join().unwrap().unwrap(); 44 | } 45 | 46 | finished.store(true, Ordering::Relaxed); 47 | 48 | vpn_check_thread.join().unwrap(); 49 | 50 | Ok(()) 51 | } 52 | 53 | fn benchmark(url: impl AsRef, using_vpn: &AtomicBool) -> Result<(), anyhow::Error> { 54 | let url = url.as_ref(); 55 | // The vector that'll contain all results i.e cold, hot and warm 56 | let mut end_results: Vec = vec![]; 57 | 58 | let cold_cache = make_request(url)?; 59 | 60 | let cold_cache_result = format!( 61 | "\n{}\n-------------------- Cold Cache --------------------\n{}\n-------------------- Cold Cache End --------------------\n", 62 | url, 63 | cold_cache 64 | ); 65 | 66 | println!("{}", cold_cache_result); 67 | 68 | end_results.push(cold_cache_result); 69 | 70 | drop(cold_cache); 71 | 72 | let mut results_vec: Vec = vec![]; 73 | 74 | let n = 10; 75 | 76 | for _ in 0..n { 77 | let result = make_request(url)?; 78 | 79 | results_vec.push(result); 80 | } 81 | 82 | let mut hot_cache = results_vec.remove(0); 83 | 84 | for result in results_vec { 85 | hot_cache = hot_cache + result; 86 | } 87 | 88 | hot_cache.namelookup_time /= n; 89 | hot_cache.connect_time /= n; 90 | hot_cache.appconnect_time /= n; 91 | hot_cache.pretransfer_time /= n; 92 | hot_cache.redirect_time /= n; 93 | hot_cache.starttransfer_time /= n; 94 | hot_cache.download_time /= n; 95 | hot_cache.total_time /= n; 96 | 97 | let hot_cache_result = format!( 98 | "\n{}\n-------------------- Hot Cache --------------------\n{}\n-------------------- Hot Cache End --------------------", 99 | url, 100 | hot_cache 101 | ); 102 | 103 | println!("{}", hot_cache_result); 104 | 105 | end_results.push(hot_cache_result); 106 | 107 | drop(hot_cache); 108 | 109 | let mut minutes: u8 = 0; 110 | 111 | println!("Sleeping for 30 minutes\n"); 112 | 113 | while minutes < 30 { 114 | if using_vpn.load(Ordering::Relaxed) { 115 | return Ok(()); 116 | } 117 | // Wait for half an hour for cache to get warm 118 | thread::sleep(Duration::from_secs(60)); 119 | minutes += 1; 120 | } 121 | 122 | let warm_cache = make_request(url)?; 123 | 124 | let warm_cache_result = format!( 125 | "\n{}\n-------------------- Warm Cache --------------------\n{}\n-------------------- Warm Cache End --------------------", 126 | url, 127 | warm_cache 128 | ); 129 | 130 | end_results.push(warm_cache_result); 131 | 132 | drop(warm_cache); 133 | 134 | let request_body = end_results.join("\n"); 135 | 136 | let mut file = OpenOptions::new() 137 | .create(true) 138 | .append(true) 139 | .open("results.txt")?; 140 | 141 | let mut bytes = request_body.as_bytes(); 142 | 143 | file.write(bytes)?; 144 | 145 | let mut handle = Easy::new(); 146 | 147 | handle.url(COLLECT_URL)?; 148 | 149 | handle.post(true)?; 150 | 151 | let mut transfer = handle.transfer(); 152 | 153 | transfer.read_function(|into| Ok(bytes.read(into).unwrap()))?; 154 | 155 | transfer.perform()?; 156 | 157 | println!("Benchmarked {} successfully.", url); 158 | 159 | Ok(()) 160 | } 161 | 162 | #[cfg(target_family = "unix")] 163 | fn vpn_check(atomic_bool: &AtomicBool, finished: &AtomicBool) { 164 | let mut system = System::new(); 165 | let mut track_map: FxHashMap = FxHashMap::default(); 166 | 167 | while !finished.load(Ordering::Relaxed) { 168 | if atomic_bool.load(Ordering::Relaxed) { 169 | println!("VPN Detected."); 170 | break; 171 | } 172 | thread::sleep(Duration::from_millis(500)); 173 | system.refresh_networks(); 174 | for (interface, network) in system.networks() { 175 | if !interface.contains("tun") { 176 | continue; 177 | } 178 | 179 | let (total_received, total_transmitted) = match track_map.get(interface) { 180 | Some(tuple) => *tuple, 181 | None => { 182 | track_map.insert(interface.to_owned(), (network.total_received(), network.total_transmitted())); 183 | continue; 184 | } 185 | }; 186 | 187 | if total_received != network.total_received() || total_transmitted != network.total_transmitted() { 188 | atomic_bool.store(true, Ordering::Relaxed); 189 | break; 190 | } 191 | 192 | } 193 | 194 | } 195 | } 196 | 197 | #[cfg(target_family = "windows")] 198 | fn vpn_check(atomic_bool: &AtomicBool, _: &AtomicBool){ 199 | for adapter in ipconfig::get_adapters().expect("Couldn't get adapters") { 200 | if adapter.if_type() == ipconfig::IfType::Unsupported || adapter.if_type() == ipconfig::IfType::Ppp{ 201 | if adapter.oper_status() == ipconfig::OperStatus::IfOperStatusUp { 202 | println!("-------------- VPN Detected --------------"); 203 | atomic_bool.store(true, Ordering::Relaxed); 204 | break; 205 | } 206 | } 207 | } 208 | } 209 | 210 | struct CurlResult { 211 | pub headers: String, 212 | pub namelookup_time: Duration, 213 | pub connect_time: Duration, 214 | pub appconnect_time: Duration, 215 | pub pretransfer_time: Duration, 216 | pub redirect_time: Duration, 217 | pub starttransfer_time: Duration, 218 | pub total_time: Duration, 219 | pub download_time: Duration, 220 | pub speed: usize, 221 | pub bytes: Vec 222 | } 223 | 224 | impl CurlResult { 225 | // Transform cumulative seconds into individual seconds 226 | pub fn normalize(&mut self){ 227 | self.download_time -= self.starttransfer_time; 228 | 229 | if self.starttransfer_time.as_nanos() > 0{ 230 | self.starttransfer_time -= self.pretransfer_time; 231 | } 232 | if self.redirect_time.as_nanos() > 0{ 233 | self.redirect_time -= self.starttransfer_time; 234 | } 235 | if self.pretransfer_time.as_nanos() > 0 { 236 | self.pretransfer_time -= self.appconnect_time; 237 | } 238 | if self.appconnect_time.as_nanos() > 0 { 239 | self.appconnect_time -= self.connect_time; 240 | } 241 | if self.connect_time.as_nanos() > 0 { 242 | self.connect_time -= self.namelookup_time; 243 | } 244 | } 245 | } 246 | 247 | impl std::ops::Add for CurlResult { 248 | type Output = Self; 249 | fn add(self, other: Self) -> Self { 250 | Self { 251 | headers: self.headers, 252 | namelookup_time: self.namelookup_time + other.namelookup_time, 253 | connect_time: self.connect_time + other.connect_time, 254 | appconnect_time: self.appconnect_time + other.appconnect_time, 255 | pretransfer_time: self.pretransfer_time + other.pretransfer_time, 256 | redirect_time: self.redirect_time + other.redirect_time, 257 | starttransfer_time: self.starttransfer_time + other.starttransfer_time, 258 | total_time: self.total_time + other.total_time, 259 | download_time: self.download_time + other.download_time, 260 | speed: self.speed + other.speed, 261 | bytes: self.bytes 262 | } 263 | } 264 | } 265 | impl fmt::Display for CurlResult { 266 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { 267 | write!( 268 | f, 269 | "{}\nName Lookup Time: {}ms | {}ns\nConnect Time: {}ms | {}ns\nApp Connect Time: {}ms | {}ns\nPretransfer Time: {}ms | {}ns\nRedirect Time: {}ms | {}ns\nStartTransfer Time: {}ms | {}ns\nDownload Time: {}ms | {}ns\nTotal Time: {}ms | {}ns\nDownloaded: {} bytes\nSpeed: {} Mbps", 270 | self.headers, 271 | self.namelookup_time.as_millis(), 272 | self.namelookup_time.as_nanos(), 273 | self.connect_time.as_millis(), 274 | self.connect_time.as_nanos(), 275 | self.appconnect_time.as_millis(), 276 | self.appconnect_time.as_nanos(), 277 | self.pretransfer_time.as_millis(), 278 | self.pretransfer_time.as_nanos(), 279 | self.redirect_time.as_millis(), 280 | self.redirect_time.as_nanos(), 281 | self.starttransfer_time.as_millis(), 282 | self.starttransfer_time.as_nanos(), 283 | self.download_time.as_millis(), 284 | self.download_time.as_nanos(), 285 | self.total_time.as_millis(), 286 | self.total_time.as_nanos(), 287 | self.bytes.len(), 288 | self.speed 289 | ) 290 | } 291 | } 292 | 293 | fn make_request(url: &str) -> Result { 294 | let mut handle = Easy::new(); 295 | 296 | let mut buffer: Vec = vec![]; 297 | 298 | let mut headers: Vec = vec![]; 299 | 300 | handle.url(url)?; 301 | 302 | { 303 | let mut transfer = handle.transfer(); 304 | 305 | transfer.write_function(|data| { 306 | buffer.extend_from_slice(data); 307 | Ok(data.len()) 308 | })?; 309 | 310 | transfer.header_function(|header_data| { 311 | headers.extend_from_slice(header_data); 312 | true 313 | })?; 314 | 315 | transfer.perform()?; 316 | } 317 | 318 | let mut result = CurlResult{ 319 | headers: String::from_utf8_lossy(&headers).to_string(), 320 | namelookup_time: handle.namelookup_time()?, 321 | connect_time: handle.connect_time()?, 322 | appconnect_time: handle.appconnect_time()?, 323 | pretransfer_time: handle.pretransfer_time()?, 324 | redirect_time: handle.redirect_time()?, 325 | starttransfer_time: handle.starttransfer_time()?, 326 | total_time: handle.total_time()?, 327 | download_time: handle.total_time()?, 328 | speed: 0, 329 | bytes: buffer 330 | }; 331 | 332 | result.normalize(); 333 | 334 | result.speed = ((result.bytes.len() as f32 * 0.000008) / result.download_time.as_secs_f32()) as usize; 335 | 336 | Ok(result) 337 | 338 | } 339 | -------------------------------------------------------------------------------- /benchmark/src/run.bat: -------------------------------------------------------------------------------- 1 | pushd "%~dp0" 2 | benchmark.exe "https://cdnspeedtest.club/wp-content/uploads/2021/07/shoeb-1-1024x576.png" "https://cdnspeedtest.xyz/wp-content/uploads/2021/07/test-1024x576.png" "https://www.cdnspeedtest.rest/wp-content/uploads/2021/07/shoeb-1024x576.png" "https://yslravvvpots.cdn.shift8web.com/wp-content/uploads/2021/08/cf-1024x576.png" "https://k7x8t5h4.hostrycdn.com/wp-content/uploads/2021/08/cf-1-1024x576.png" "https://cdnspeeds.club/wp-content/uploads/2021/08/cf-4-1024x576.png" 3 | popd 4 | PAUSE 5 | -------------------------------------------------------------------------------- /benchmark/src/run.command: -------------------------------------------------------------------------------- 1 | cd `dirname $0` 2 | chmod +x ./benchmark 3 | ./benchmark "https://cdnspeedtest.club/wp-content/uploads/2021/07/shoeb-1-1024x576.png" "https://cdnspeedtest.xyz/wp-content/uploads/2021/07/test-1024x576.png" "https://www.cdnspeedtest.rest/wp-content/uploads/2021/07/shoeb-1024x576.png" "https://yslravvvpots.cdn.shift8web.com/wp-content/uploads/2021/08/cf-1024x576.png" "https://k7x8t5h4.hostrycdn.com/wp-content/uploads/2021/08/cf-1-1024x576.png" "https://cdnspeeds.club/wp-content/uploads/2021/08/cf-4-1024x576.png" 4 | -------------------------------------------------------------------------------- /benchmark/src/run.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/bash 2 | ./benchmark "https://cdnspeedtest.club/wp-content/uploads/2021/07/shoeb-1-1024x576.png" "https://cdnspeedtest.xyz/wp-content/uploads/2021/07/test-1024x576.png" "https://www.cdnspeedtest.rest/wp-content/uploads/2021/07/shoeb-1024x576.png" "https://yslravvvpots.cdn.shift8web.com/wp-content/uploads/2021/08/cf-1024x576.png" "https://k7x8t5h4.hostrycdn.com/wp-content/uploads/2021/08/cf-1-1024x576.png" "https://cdnspeeds.club/wp-content/uploads/2021/08/cf-4-1024x576.png" 3 | -------------------------------------------------------------------------------- /cf.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/speedtestdemon/speed-tests/5bcf1e83b52cd9085af2dcd79fdca3d069d5918e/cf.png -------------------------------------------------------------------------------- /cf_219kb.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/speedtestdemon/speed-tests/5bcf1e83b52cd9085af2dcd79fdca3d069d5918e/cf_219kb.png -------------------------------------------------------------------------------- /cloudinary_36kb.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/speedtestdemon/speed-tests/5bcf1e83b52cd9085af2dcd79fdca3d069d5918e/cloudinary_36kb.png -------------------------------------------------------------------------------- /curl-format.txt: -------------------------------------------------------------------------------- 1 | time_namelookup: %{time_namelookup}s\n 2 | time_connect: %{time_connect}s\n 3 | time_appconnect: %{time_appconnect}s\n 4 | time_pretransfer: %{time_pretransfer}s\n 5 | time_redirect: %{time_redirect}s\n 6 | time_starttransfer: %{time_starttransfer}s\n 7 | ----------\n 8 | time_total: %{time_total}s\n 9 | -------------------------------------------------------------------------------- /test.py: -------------------------------------------------------------------------------- 1 | import pycurl 2 | import io 3 | import sys 4 | import time 5 | 6 | if len(sys.argv) != 2: 7 | raise ValueError('Please provide a url') 8 | url = sys.argv[1] 9 | 10 | headers = io.BytesIO() 11 | 12 | def curl(url): 13 | global headers 14 | headers = io.BytesIO() 15 | buf = io.BytesIO() # We need to measure download time. 16 | c = pycurl.Curl() 17 | c.setopt(c.URL, url) 18 | c.setopt(c.DNS_CACHE_TIMEOUT,0) # disable dns cache. 19 | c.setopt(c.FORBID_REUSE,1) # disable dns cache. 20 | c.setopt(c.FRESH_CONNECT,1) # disable dns cache. 21 | c.setopt(c.HEADERFUNCTION, headers.write) 22 | c.setopt(c.WRITEFUNCTION, buf.write) 23 | c.perform() 24 | # Sanity check that we got a download. 25 | # print('download size', len(buf.getvalue())) 26 | return c 27 | 28 | def printresults(results): 29 | print('time_namelookup: {:.20f}'.format(results[0])) 30 | print('time_connect: {:.20f}'.format(results[1])) 31 | print('time_appconnect: {:.20f}'.format(results[2])) 32 | print('time_pretransfer: {:.20f}'.format(results[3])) 33 | print('time_redirect: {:.20f}'.format(results[4])) 34 | print('time_starttransfer: {:.20f}'.format(results[5])) 35 | print('time to download: {:.20f}'.format(results[6])) 36 | print('time_total: {:.20f}'.format(results[7])) 37 | 38 | # Turn data from cumulative seconds to individual seconds 39 | def fixdata(D): 40 | # return D # if you want to debug the raw curl numbers. 41 | i = len(D) - 3 42 | cumulativetime = D[ i+1 ] 43 | cur_i = i+1 # we start setting values at 2nd to last num. 44 | while i >= 0: 45 | if D[i] > 0: 46 | D[cur_i] = cumulativetime - D[i] # calculates new value for cur_i 47 | cumulativetime = D[i] # updates the new cumulative time. 48 | cur_i = i 49 | i -= 1 50 | return D 51 | 52 | # This is done for "cold cache test" and "warm cache test". 53 | def singlecurltest(url): 54 | c = curl(url) 55 | print('Got headers:') 56 | print(headers.getvalue().decode("utf-8")) 57 | data = [c.getinfo(c.NAMELOOKUP_TIME), 58 | c.getinfo(c.CONNECT_TIME), 59 | c.getinfo(c.APPCONNECT_TIME), 60 | c.getinfo(c.PRETRANSFER_TIME), 61 | c.getinfo(c.REDIRECT_TIME), 62 | c.getinfo(c.STARTTRANSFER_TIME), 63 | c.getinfo(c.TOTAL_TIME), 64 | c.getinfo(c.TOTAL_TIME) ] 65 | data = fixdata(data) 66 | printresults(data) 67 | 68 | print('-------------------------------------------------------------') 69 | print('Testing "Cold cache speed"') 70 | print('-------------------------------------------------------------') 71 | singlecurltest(url) 72 | 73 | print('-------------------------------------------------------------') 74 | print('Testing "Hot cache speed"') 75 | print('-------------------------------------------------------------') 76 | 77 | # url = "https://d3va53q3li7xt1.cloudfront.net/wp-content/uploads/2021/05/shoeb-1024x576.png" 78 | n = 10 79 | 80 | responses = [] 81 | for i in range(n): 82 | c = curl(url) 83 | data = [c.getinfo(c.NAMELOOKUP_TIME), 84 | c.getinfo(c.CONNECT_TIME), 85 | c.getinfo(c.APPCONNECT_TIME), 86 | c.getinfo(c.PRETRANSFER_TIME), 87 | c.getinfo(c.REDIRECT_TIME), 88 | c.getinfo(c.STARTTRANSFER_TIME), 89 | c.getinfo(c.TOTAL_TIME), 90 | c.getinfo(c.TOTAL_TIME) ] 91 | data = fixdata(data) 92 | 93 | responses.append(data) 94 | c.close() 95 | 96 | 97 | total_sum = [0,0,0,0,0,0,0,0] 98 | for response in responses: 99 | for i in range(len(response)): 100 | total_sum[i] = total_sum[i] + response[i] 101 | 102 | results = [0,0,0,0,0,0,0,0] 103 | for i in range(len(total_sum)): 104 | results[i] = total_sum[i]/n 105 | 106 | print('{0} requests done. Average:'.format(n)) 107 | printresults(results) 108 | 109 | 110 | print('-------------------------------------------------------------') 111 | print('Testing "Warm cache speed"') 112 | print('-------------------------------------------------------------') 113 | print('Sleeping for 0.5 hr to move cache from hot to warm') 114 | time.sleep(1800) # 1800 seconds == 0.5 hr 115 | singlecurltest(url) 116 | -------------------------------------------------------------------------------- /wp.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/speedtestdemon/speed-tests/5bcf1e83b52cd9085af2dcd79fdca3d069d5918e/wp.png --------------------------------------------------------------------------------