Repository: saucelabs/node-saucelabs
Pull request #260 (2024-08-15 14:27:28)

updating sauce connect api
# One-line summary

> Related to Issue: #240 

Adding an API to get available Sauce Connect versions

## Description

- Getting available Sauce Connect versions is the first step for adding SC5 support

- Another supporting change added in this MR is allowing query parameters containing an underscore `my_param=value`. Before, the code assumed that query parameters are camel-cased `myParam=value`
- regenerated `interface.md` file

Output example

```
$ bin/sl scVersions 5.0.1 darwin-arm64
{
    "downloads": {
        "linux": {
            "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.x86_64.tar.gz",
            "sha256": "6247e61e39ff054cf524341a681f4045c557be79bcf63c8c501e634ef2d54a41"
        },
        "linux-arm64": {
            "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.aarch64.tar.gz",
            "sha256": "b4951cf64a724ceb03cf0ae676a35a0ca721210c0e42426384dcec23159f1fe5"
        },
        "osx": {
            "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_darwin.all.zip",
            "sha256": "d0a29f2df3277e8468c55810ef99685bed632ec6d2eed9fdbd941f2f8faf2354"
        },
        "win32": {
            "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_windows.x86_64.zip",
            "sha256": "d3e692cca8b9311a4822e8a6f8715e787319e70dc5551cbb212f5be68d36f7bb"
        },
        "windows-arm64": {
            "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_windows.aarch64.zip",
            "sha256": "fbb1b15c9a5ae6435cba0dc43f195df32764e5c7b1fcc6a2e625df58ea05642d"
        }
    },
    "info_url": "https://docs.saucelabs.com/secure-connections/sauce-connect-5/installation/",
    "latest_version": "5.1.1",
    "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_darwin.all.zip",
    "sha256": "d0a29f2df3277e8468c55810ef99685bed632ec6d2eed9fdbd941f2f8faf2354",
    "status": "UPGRADE",
    "client_version": "5.0.1"
}
```

## Types of Changes

- New feature (non-breaking change which adds functionality)
- Refactor/improvements

## Review
_List of tasks the reviewer must do to review the PR_
- [ ] Tests
- [ ] Documentation


Patch:
diff --git a/apis/sauce.json b/apis/sauce.json
index 3b78792..1bda613 100644
--- a/apis/sauce.json
+++ b/apis/sauce.json
@@ -458,6 +458,84 @@
       },
       "type": "object"
     },
+    "SauceConnectDownloadInfo": {
+      "type": "object",
+      "properties": {
+        "download_url": {
+          "type": "string"
+        },
+        "sha1": {
+          "type": "string",
+          "nullable": true
+        },
+        "sha256": {
+          "type": "string",
+          "nullable": true
+        },
+        "version": {
+          "type": "string",
+          "nullable": true
+        }
+      }
+    },
+    "SauceConnectByPlatform": {
+      "type": "object",
+      "properties": {
+        "linux": {
+          "$ref": "#/definitions/SauceConnectDownloadInfo",
+          "nullable": true
+        },
+        "linux-arm64": {
+          "$ref": "#/definitions/SauceConnectDownloadInfo",
+          "nullable": true
+        },
+        "win32": {
+          "$ref": "#/definitions/SauceConnectDownloadInfo",
+          "nullable": true
+        },
+        "osx": {
+          "$ref": "#/definitions/SauceConnectDownloadInfo"
+        }
+      }
+    },
+    "SauceConnectVersions": {
+      "type": "object",
+      "properties": {
+        "latest_version": {
+          "type": "string"
+        },
+        "client_version": {
+          "type": "string"
+        },
+        "status": {
+          "type": "string",
+          "enum": ["LATEST", "UPGRADE", "PRERELEASE", "UNKNOWN", "EOL"]
+        },
+        "info_url": {
+          "type": "string"
+        },
+        "download_url": {
+          "type": "string"
+        },
+        "sha1": {
+          "type": "string",
+          "nullable": true
+        },
+        "sha256": {
+          "type": "string",
+          "nullable": true
+        }
+      },
+      "downloads": {
+        "$ref": "#/definitions/SauceConnectByPlatform"
+      },
+      "all_downloads": {
+        "type": "array",
+        "items": {
+          "$ref": "#/definitions/SauceConnectByPlatform"
+        }
+      }
+    },
     "SauceStatus": {
       "properties": {
         "service_operational": {
@@ -742,6 +820,20 @@
       "required": true,
       "type": "string"
     },
+    "clientHost": {
+      "description": "SC client host OS and CPU arch",
+      "in": "query",
+      "name": "client_host",
+      "required": false,
+      "type": "string"
+    },
+    "clientVersion": {
+      "description": "SC client version",
+      "in": "query",
+      "name": "client_version",
+      "required": false,
+      "type": "string"
+    },
     "filepath": {
       "description": "file path to store the asset at",
       "in": "path",
@@ -756,6 +848,14 @@
       "required": true,
       "type": "string"
     },
+    "filter": {
+      "description": "Filter expression to apply before returning query results",
+      "in": "query",
+      "name": "filter",
+      "enum": ["v2alpha", "one_per_pool"],
+      "required": false,
+      "type": "string"
+    },
     "full": {
       "description": "Should the response result contain everything or just the basics",
       "in": "query",
@@ -811,6 +911,21 @@
         "type": "object"
       }
     },
+    "protocol": {
+      "description": "Sauce Connect Protocol",
+      "in": "query",
+      "name": "protocol",
+      "required": false,
+      "enum": ["kgp", "h2c"],
+      "type": "string"
+    },
+    "reason": {
+      "description": "Reason for stopping a tunnel",
+      "in": "query",
+      "name": "reason",
+      "required": true,
+      "type": "string"
+    },
     "subaccounts": {
       "default": false,
       "description": "Include subaccounts in list of jobs",
@@ -825,6 +940,13 @@
       "required": true,
       "type": "string"
     },
+    "wait_for_jobs": {
+      "default": true,
+      "description": "Wait for jobs to finish",
+      "in": "query",
+      "name": "wait_for_jobs",
+      "type": "boolean"
+    },
     "jobIds": {
       "description": "list of jobIds",
       "in": "query",
@@ -1539,6 +1661,12 @@
           },
           {
             "$ref": "#/parameters/full"
+          },
+          {
+            "$ref": "#/parameters/filter"
+          },
+          {
+            "$ref": "#/parameters/protocol"
           }
         ],
         "responses": {
@@ -1577,6 +1705,12 @@
           },
           {
             "$ref": "#/parameters/id"
+          },
+          {
+            "$ref": "#/parameters/reason"
+          },
+          {
+            "$ref": "#/parameters/wait_for_jobs"
           }
         ],
         "responses": {
@@ -1633,6 +1767,38 @@
         "tags": ["Tunnel"]
       }
     },
+    "/v1/public/tunnels/info/versions": {
+      "get": {
+        "operationId": "sc_versions",
+        "parameters": [
+          {
+            "$ref": "#/parameters/clientVersion"
+          },
+          {
+            "$ref": "#/parameters/clientHost"
+          },
+          {
+            "$ref": "#/parameters/all"
+          }
+        ],
+        "responses": {
+          "200": {
+            "description": "Tunnels",
+            "schema": {
+              "$ref": "#/definitions/SauceConnectVersions"
+            }
+          },
+          "default": {
+            "description": "Unexpected error",
+            "schema": {
+              "$ref": "#/definitions/Error"
+            }
+          }
+        },
+        "summary": "Get tunnels for the user or all the users in the team",
+        "tags": ["Tunnel"]
+      }
+    },
     "/v1/jobs/{id}/{assetName}": {
       "get": {
         "operationId": "download_job_asset",
diff --git a/docs/interface.md b/docs/interface.md
index e99ba6c..c3cc7d4 100644
--- a/docs/interface.md
+++ b/docs/interface.md
@@ -61,46 +61,6 @@ The following commands are available via package or cli tool:
         <code>api.getStatus()</code>
       </td>
     </tr>
-    <tr>
-      <td>
-        <b>DELETE</b> <code>/v1/manual</code><br>
-        complete manual task
-        <h3>Example:</h3>
-        <code>api.deleteManualJob(ids)</code>
-      </td>
-    </tr>
-    <tr>
-      <td>
-        <b>POST</b> <code>/v1/manual</code><br>
-        Creates a manual job
-        <h3>Example:</h3>
-        <code>api.createManualJob(capabilities)</code>
-      </td>
-    </tr>
-    <tr>
-      <td>
-        <b>GET</b> <code>/v1/manual/options/</code><br>
-        returns a list of supported platforms in the Sauce cloud
-        <h3>Example:</h3>
-        <code>api.listManualPlatforms()</code>
-      </td>
-    </tr>
-    <tr>
-      <td>
-        <b>GET</b> <code>/v1/manual/{taskId}</code><br>
-        get manual task
-        <h3>Example:</h3>
-        <code>api.getManualJob(taskId)</code>
-      </td>
-    </tr>
-    <tr>
-      <td>
-        <b>POST</b> <code>/v1/manual/{taskId}/screenshot</code><br>
-        Take screenshot in manual session
-        <h3>Example:</h3>
-        <code>api.createManualJobScreenshot(taskId)</code>
-      </td>
-    </tr>
     <tr>
       <td>
         <b>GET</b> <code>/v1/me</code><br>
@@ -109,22 +69,6 @@ The following commands are available via package or cli tool:
         <code>api.getCurrentUser()</code>
       </td>
     </tr>
-    <tr>
-      <td>
-        <b>DELETE</b> <code>/v1/tasks</code><br>
-        complete manual task
-        <h3>Example:</h3>
-        <code>api.deleteManualJobLegacy(ids)</code>
-      </td>
-    </tr>
-    <tr>
-      <td>
-        <b>POST</b> <code>/v1/tasks</code><br>
-        Creates a manual job
-        <h3>Example:</h3>
-        <code>api.createManualJobLegacy(capabilities)</code>
-      </td>
-    </tr>
     <tr>
       <td>
         <b>GET</b> <code>/v1/users/{username}</code><br>
@@ -220,15 +164,16 @@ The following commands are available via package or cli tool:
         <h3>Example:</h3>
         <code>api.listTunnels(username, { ...options })</code>
         <br><h4>Options</h4>
-        <ul>          <li><b>all</b>: Should the response contain the same team user data</li>          <li><b>full</b>: Should the response result contain everything or just the basics</li>        </ul>      </td>
+        <ul>          <li><b>all</b>: Should the response contain the same team user data</li>          <li><b>full</b>: Should the response result contain everything or just the basics</li>          <li><b>filter</b>: Filter expression to apply before returning query results</li>          <li><b>protocol</b>: Sauce Connect Protocol</li>        </ul>      </td>
     </tr>
     <tr>
       <td>
         <b>DELETE</b> <code>/v1/{username}/tunnels/{id}</code><br>
         Delete a Tunnel
         <h3>Example:</h3>
-        <code>api.deleteTunnel(username, id)</code>
-      </td>
+        <code>api.deleteTunnel(username, id, reason, { ...options })</code>
+        <br><h4>Options</h4>
+        <ul>          <li><b>wait_for_jobs</b>: Wait for jobs to finish</li>        </ul>      </td>
     </tr>
     <tr>
       <td>
@@ -238,6 +183,15 @@ The following commands are available via package or cli tool:
         <code>api.getTunnel(username, id)</code>
       </td>
     </tr>
+    <tr>
+      <td>
+        <b>GET</b> <code>/v1/public/tunnels/info/versions</code><br>
+        Get tunnels for the user or all the users in the team
+        <h3>Example:</h3>
+        <code>api.scVersions({ ...options })</code>
+        <br><h4>Options</h4>
+        <ul>          <li><b>client_version</b>: SC client version</li>          <li><b>client_host</b>: SC client host OS and CPU arch</li>          <li><b>all</b>: Should the response contain the same team user data</li>        </ul>      </td>
+    </tr>
     <tr>
       <td>
         <b>GET</b> <code>/v1/jobs/{id}/{assetName}</code><br>
@@ -256,15 +210,6 @@ The following commands are available via package or cli tool:
         <br><h4>Options</h4>
         <ul>          <li><b>full</b>: Should the response result contain everything or just the basics</li>        </ul>      </td>
     </tr>
-    <tr>
-      <td>
-        <b>POST</b> <code>/storage/upload</code><br>
-        Returns new application id after the upload.
-        <h3>Example:</h3>
-        <code>api.uploadApp({ ...options })</code>
-        <br><h4>Options</h4>
-        <ul>          <li><b>App-Type</b>: Application type</li>          <li><b>App-Identifier</b>: Your custom unique identifier for your app</li>          <li><b>App-DisplayName</b>: Your custom display name</li>          <li><b>App-Active</b>: If true makes uploaded application active one</li>          <li><b>body</b>: No description available.</li>        </ul>      </td>
-    </tr>
     <tr>
       <td>
         <b>GET</b> <code>/metrics/</code><br>
@@ -584,7 +529,7 @@ The following commands are available via package or cli tool:
         <h3>Example:</h3>
         <code>api.getBuildsV2(build_source, { ...options })</code>
         <br><h4>Options</h4>
-        <ul>          <li><b>user_id</b>: user_id</li>          <li><b>org_id</b>: org_id</li>          <li><b>group_id</b>: group_id</li>          <li><b>team_id</b>: team_id</li>          <li><b>status</b>: status</li>          <li><b>name</b>: start</li>          <li><b>end</b>: end</li>          <li><b>limit</b>: Number of results to return</li>          <li><b>offset</b>: Starting number</li>          <li><b>sort</b>: sort</li>        </ul>      </td>
+        <ul>          <li><b>user_id</b>: user_id</li>          <li><b>org_id</b>: org_id</li>          <li><b>group_id</b>: group_id</li>          <li><b>team_id</b>: team_id</li>          <li><b>status</b>: status</li>          <li><b>start_time</b>: start_time</li>          <li><b>end_time</b>: end_time</li>          <li><b>limit</b>: Number of results to return</li>          <li><b>offset</b>: Starting number</li>          <li><b>sort</b>: sort</li>        </ul>      </td>
     </tr>
     <tr>
       <td>
diff --git a/src/index.js b/src/index.js
index 3e2ffda..058f946 100644
--- a/src/index.js
+++ b/src/index.js
@@ -529,20 +529,24 @@ export default class SauceLabs {
     const options = args.slice(pathParams.length)[0] || {};
     for (const optionParam of params.filter((p) => p.in === 'query')) {
       const expectedType = optionParam.type.replace('integer', 'number');
+      // I'm not sure why query param name is camel-cased here, underscore params do exist in Sauce Labs.
       const optionName = camelCase(optionParam.name);
-      const option = options[optionName];
+      const optionValue = options[optionName] || options[optionParam.name];
       const isRequired =
         Boolean(optionParam.required) ||
         (typeof optionParam.required === 'undefined' &&
           typeof optionParam.default === 'undefined');
-      if ((isRequired || option) && !isValidType(option, expectedType)) {
+      if (
+        (isRequired || optionValue) &&
+        !isValidType(optionValue, expectedType)
+      ) {
         throw new Error(
-          `Expected parameter for option '${optionName}' from type '${expectedType}', found '${typeof option}'`
+          `Expected parameter for option '${optionName}' from type '${expectedType}', found '${typeof optionValue}'`
         );
       }
 
-      if (typeof option !== 'undefined') {
-        bodyMap.set(optionParam.name, option);
+      if (typeof optionValue !== 'undefined') {
+        bodyMap.set(optionParam.name, optionValue);
       }
     }
 


Test patch:
diff --git a/tests/__responses__/all_versions.json b/tests/__responses__/all_versions.json
new file mode 100644
index 0000000..59c2fde
--- /dev/null
+++ b/tests/__responses__/all_versions.json
@@ -0,0 +1,270 @@
+{
+  "downloads": {
+    "linux": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.x86_64.tar.gz",
+      "sha256": "6247e61e39ff054cf524341a681f4045c557be79bcf63c8c501e634ef2d54a41"
+    },
+    "linux-arm64": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.aarch64.tar.gz",
+      "sha256": "b4951cf64a724ceb03cf0ae676a35a0ca721210c0e42426384dcec23159f1fe5"
+    },
+    "osx": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_darwin.all.zip",
+      "sha256": "d0a29f2df3277e8468c55810ef99685bed632ec6d2eed9fdbd941f2f8faf2354"
+    },
+    "win32": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_windows.x86_64.zip",
+      "sha256": "d3e692cca8b9311a4822e8a6f8715e787319e70dc5551cbb212f5be68d36f7bb"
+    },
+    "windows-arm64": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_windows.aarch64.zip",
+      "sha256": "fbb1b15c9a5ae6435cba0dc43f195df32764e5c7b1fcc6a2e625df58ea05642d"
+    }
+  },
+  "info_url": "https://docs.saucelabs.com/secure-connections/sauce-connect-5/installation/",
+  "latest_version": "5.1.1",
+  "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_darwin.all.zip",
+  "sha256": "d0a29f2df3277e8468c55810ef99685bed632ec6d2eed9fdbd941f2f8faf2354",
+  "status": "LATEST",
+  "client_version": "5.1.1",
+  "all_downloads": {
+    "4.7.0": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.7.0-linux.tar.gz",
+        "sha1": "f0bf8e35894e9b35bf9fae8f4f34e83845b4bb6b"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.7.0-osx.zip",
+        "sha1": "8e41a471bdf4cfeed7cd06d6af9dd081b9aa028d"
+      }
+    },
+    "4.7.1": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.7.1-linux.tar.gz",
+        "sha1": "e5d7f82ad98251a653d1b0537f1103e49eda5e11"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.7.1-linux-arm64.tar.gz",
+        "sha1": "d07c8f62ec64168f9cc80d73a59976764f2c62b4"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.7.1-osx.zip",
+        "sha1": "1f18defa14a5cc4b663bf07213411f6bdd535b6d"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.7.1-win32.zip",
+        "sha1": "9c91e5adbd023973efe0eb14d2d427d2c0ef3c25"
+      }
+    },
+    "4.8.0": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.0-linux.tar.gz",
+        "sha1": "a6bcfeab41b245e503c1f2aad382bfa8956893a1"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.0-linux-arm64.tar.gz",
+        "sha1": "8ce9b5a740710e6eef1be70b1b1d347df938d46a"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.0-osx.zip",
+        "sha1": "8c4c7de20c68b704cffddcaddea44a6773b05746"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.0-win32.zip",
+        "sha1": "48382adec66130d96148ccaff46894088366ed90"
+      }
+    },
+    "4.8.1": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.1-linux.tar.gz",
+        "sha1": "9c16682e4c9716734432789884f868212f95f563"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.1-linux-arm64.tar.gz",
+        "sha1": "2a6a5fd0ad90c1d776048e4f9fd60a1a8a26c3a2"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.1-osx.zip",
+        "sha1": "4c5b8b570994a76396c75858455032bfdbb83589"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.1-win32.zip",
+        "sha1": "f3df33f01bf8d9585cfcda084b54300089266159"
+      }
+    },
+    "4.8.2": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.2-linux.tar.gz",
+        "sha1": "e65e77e849a80d1eb1de03ba56abf5a4d51cf1c5"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.2-linux-arm64.tar.gz",
+        "sha1": "fd782a658f4d28b9792edaf9df730a87ae797cba"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.2-osx.zip",
+        "sha1": "5c2f81f6b0f246a641384d33df5c091ca0174730"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.2-win32.zip",
+        "sha1": "1c81cbe9d1b25b8f8483cc1163d54d94191f7665"
+      }
+    },
+    "4.8.3": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.3-linux.tar.gz",
+        "sha1": "1af0d45ce48e3f0707164dbf0577adad2e6b7853"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.3-linux-arm64.tar.gz",
+        "sha1": "de6c894d018a1dd1f38c3c90bd4b8084c2e9fd4d"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.3-osx.zip",
+        "sha1": "c6edb040d3c7398c0f2be41957846b85a8d1e6e6"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.8.3-win32.zip",
+        "sha1": "6df7d8114954b09d61e54ac8c642137fa98d342f"
+      }
+    },
+    "4.9.0": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.0-linux.tar.gz",
+        "sha1": "f263177c700ebc29a0c5772a04e9b04bc1487c91"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.0-linux-arm64.tar.gz",
+        "sha1": "04f697d585bdc7d95d7663dea52f5b895628b0ba"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.0-osx.zip",
+        "sha1": "f3080fbd76a3847c9c19dae6131f93a1c3abb008"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.0-win32.zip",
+        "sha1": "fe35f66126ddd6e8d043790906206c2999d69f1a"
+      }
+    },
+    "4.9.1": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.1-linux.tar.gz",
+        "sha1": "9310bc860f7870a1f872b11c4dc6073a1ad34e5e"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.1-linux-arm64.tar.gz",
+        "sha1": "535e6c9edcc0ca94cac7c9f800f910dcea808cbf"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.1-osx.zip",
+        "sha1": "64f9c1bac5d4f5b9acb6fbb629b6df0f5671b4c8"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.1-win32.zip",
+        "sha1": "63858695eb6840306921607a97af0083c0697bf3"
+      }
+    },
+    "4.9.2": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.2-linux.tar.gz",
+        "sha1": "5589571bdc186f3f1b05fe6ce68529501a42fb43"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.2-linux-arm64.tar.gz",
+        "sha1": "8b02c4343b74c36c575817ea4a6eae5fb5718f6c"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sc-4.9.2-win32.zip",
+        "sha1": "47c19feda3fb684f88acd816e9c8f2e3d4a1e3c0"
+      }
+    },
+    "5.0.0": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.0/sauce-connect-5.0.0_linux.x86_64.tar.gz",
+        "sha1": "1dfcae164bf28dc5071d496777f23187285f7578"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.0/sauce-connect-5.0.0_linux.aarch64.tar.gz",
+        "sha1": "9861f28c8703a8d4a0f7824684e467974e202350"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.0/sauce-connect-5.0.0_darwin.all.zip",
+        "sha1": "19d56467d90a98cafd85ed1f2b7647c95d8fe27b"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.0/sauce-connect-5.0.0_windows.x86_64.zip",
+        "sha1": "40f1375d0d28e8c704f8b829fb842bedd11ea6c9"
+      },
+      "windows-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.0/sauce-connect-5.0.0_windows.aarch64.zip",
+        "sha1": "a7be976a39a72e0c1c931f7b981649a93c0a4b36"
+      }
+    },
+    "5.0.1": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.1/sauce-connect-5.0.1_linux.x86_64.tar.gz",
+        "sha1": "23fe2956742c1244757e249e5e05a59e96039482"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.1/sauce-connect-5.0.1_linux.aarch64.tar.gz",
+        "sha1": "962c1cd7884ad703e213d86ba9df8d7b5d58dbe7"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.1/sauce-connect-5.0.1_darwin.all.zip",
+        "sha1": "5eaa165b5eae2c57c8fc07f7272404c09a56cb89"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.1/sauce-connect-5.0.1_windows.x86_64.zip",
+        "sha1": "f6afc12802581922fdff2ee7472f1b3a1d259ec9"
+      },
+      "windows-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.0.1/sauce-connect-5.0.1_windows.aarch64.zip",
+        "sha1": "c92ae859e212fc83221b92486886e741bb6f336c"
+      }
+    },
+    "5.1.0": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.0/sauce-connect-5.1.0_linux.x86_64.tar.gz",
+        "sha256": "69ef7830b8ea3fc2bd9129cbf3f5ff04a22c6a7cd8a3c9e1e1ff0ee411b0ca20"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.0/sauce-connect-5.1.0_linux.aarch64.tar.gz",
+        "sha256": "679b940e6e7e99ded716fd22e0a4229be012c85aaad9d0ca9242e2bbcf8f50ed"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.0/sauce-connect-5.1.0_darwin.all.zip",
+        "sha256": "e587d5a9b5e5c928600d9e5e35d74ae9926218c7e13ab1da90f26da411d360cd"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.0/sauce-connect-5.1.0_windows.x86_64.zip",
+        "sha256": "291f149685fa20015f78423a5650438978aa38ba3c72671fe834d80c706e32c4"
+      },
+      "windows-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.0/sauce-connect-5.1.0_windows.aarch64.zip",
+        "sha256": "a6b1e61f93eb8afb4bf461d7df43724ae1cafdb9553ca7f7cc59905ed431d7f7"
+      }
+    },
+    "5.1.1": {
+      "linux": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.x86_64.tar.gz",
+        "sha256": "6247e61e39ff054cf524341a681f4045c557be79bcf63c8c501e634ef2d54a41"
+      },
+      "linux-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.aarch64.tar.gz",
+        "sha256": "b4951cf64a724ceb03cf0ae676a35a0ca721210c0e42426384dcec23159f1fe5"
+      },
+      "osx": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_darwin.all.zip",
+        "sha256": "d0a29f2df3277e8468c55810ef99685bed632ec6d2eed9fdbd941f2f8faf2354"
+      },
+      "win32": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_windows.x86_64.zip",
+        "sha256": "d3e692cca8b9311a4822e8a6f8715e787319e70dc5551cbb212f5be68d36f7bb"
+      },
+      "windows-arm64": {
+        "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_windows.aarch64.zip",
+        "sha256": "fbb1b15c9a5ae6435cba0dc43f195df32764e5c7b1fcc6a2e625df58ea05642d"
+      }
+    }
+  }
+}
diff --git a/tests/__responses__/latest_versions.json b/tests/__responses__/latest_versions.json
new file mode 100644
index 0000000..0547945
--- /dev/null
+++ b/tests/__responses__/latest_versions.json
@@ -0,0 +1,30 @@
+{
+  "downloads": {
+    "linux": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.x86_64.tar.gz",
+      "sha256": "6247e61e39ff054cf524341a681f4045c557be79bcf63c8c501e634ef2d54a41"
+    },
+    "linux-arm64": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.aarch64.tar.gz",
+      "sha256": "b4951cf64a724ceb03cf0ae676a35a0ca721210c0e42426384dcec23159f1fe5"
+    },
+    "osx": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_darwin.all.zip",
+      "sha256": "d0a29f2df3277e8468c55810ef99685bed632ec6d2eed9fdbd941f2f8faf2354"
+    },
+    "win32": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_windows.x86_64.zip",
+      "sha256": "d3e692cca8b9311a4822e8a6f8715e787319e70dc5551cbb212f5be68d36f7bb"
+    },
+    "windows-arm64": {
+      "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_windows.aarch64.zip",
+      "sha256": "fbb1b15c9a5ae6435cba0dc43f195df32764e5c7b1fcc6a2e625df58ea05642d"
+    }
+  },
+  "info_url": "https://docs.saucelabs.com/secure-connections/sauce-connect-5/installation/",
+  "latest_version": "5.1.1",
+  "download_url": "https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_darwin.all.zip",
+  "sha256": "d0a29f2df3277e8468c55810ef99685bed632ec6d2eed9fdbd941f2f8faf2354",
+  "status": "LATEST",
+  "client_version": "5.1.1"
+}
diff --git a/tests/__responses__/versions.json b/tests/__responses__/versions.json
index 9ba2c6f..dab9b3c 100644
--- a/tests/__responses__/versions.json
+++ b/tests/__responses__/versions.json
@@ -1,30 +1,26 @@
 {
   "Sauce Connect": {
-    "download_url": "https://wiki.saucelabs.com/display/DOCS/Setting+Up+Sauce+Connect",
+    "download_url": "https://docs.saucelabs.com/secure-connections/sauce-connect/installation/",
     "linux": {
-      "build": 5183,
-      "download_url": "https://saucelabs.com/downloads/sc-4.6.2-linux.tar.gz",
-      "sha1": "7b7f35433af9c3380758e048894d7b9aecf3754e"
+      "build": "b491a8aaea43d70ef6cb1f37a11191de01fa8446",
+      "download_url": "https://saucelabs.com/downloads/sc-4.9.2-linux.tar.gz",
+      "sha1": "5589571bdc186f3f1b05fe6ce68529501a42fb43"
     },
-    "linux32": {
-      "build": 5183,
-      "download_url": "https://saucelabs.com/downloads/sc-4.6.2-linux32.tar.gz",
-      "sha1": "ce96d8543f013e0112a678aa9980e95331421cb1"
+    "linux-arm64": {
+      "build": "b491a8aaea43d70ef6cb1f37a11191de01fa8446",
+      "download_url": "https://saucelabs.com/downloads/sc-4.9.2-linux-arm64.tar.gz",
+      "sha1": "8b02c4343b74c36c575817ea4a6eae5fb5718f6c"
     },
     "osx": {
-      "build": 5183,
-      "download_url": "https://saucelabs.com/downloads/sc-4.6.2-osx.zip",
-      "sha1": "51c6c152eb54c20d8969a9d5917ebecc3ac868e1"
+      "build": "55cc68ffd9a2891e9b717ed459b1d0e970555f9c",
+      "download_url": "https://saucelabs.com/downloads/sc-4.9.1-osx.zip",
+      "sha1": "64f9c1bac5d4f5b9acb6fbb629b6df0f5671b4c8"
     },
-    "version": "1.2.4",
+    "version": "4.9.2",
     "win32": {
-      "build": 5183,
-      "download_url": "https://saucelabs.com/downloads/sc-4.6.2-win32.zip",
-      "sha1": "4b8955c806998226ed41592cbe45c929c0f88a87"
+      "build": "b491a8aaea43d70ef6cb1f37a11191de01fa8446",
+      "download_url": "https://saucelabs.com/downloads/sc-4.9.2-win32.zip",
+      "sha1": "47c19feda3fb684f88acd816e9c8f2e3d4a1e3c0"
     }
-  },
-  "Sauce Connect 2": {
-    "download_url": "https://docs.saucelabs.com/reference/sauce-connect/",
-    "version": "4.3.13-r999"
   }
 }
diff --git a/tests/__snapshots__/index.test.js.snap b/tests/__snapshots__/index.test.js.snap
index 63ae680..481a63c 100644
--- a/tests/__snapshots__/index.test.js.snap
+++ b/tests/__snapshots__/index.test.js.snap
@@ -1,5 +1,21 @@
 // Jest Snapshot v1, https://goo.gl/fbAQLP
 
+exports[`should contain all download links 1`] = `
+[
+  [
+    "https://api.us-west-1.saucelabs.com/rest/v1/public/tunnels/info/versions",
+    {
+      "responseType": "json",
+      "searchParams": {
+        "all": true,
+        "client_host": "darwin-arm64",
+        "client_version": "5.1.1",
+      },
+    },
+  ],
+]
+`;
+
 exports[`should get builds failed jobs 1`] = `
 [
   [
@@ -122,6 +138,21 @@ exports[`should get user by username 1`] = `
 ]
 `;
 
+exports[`should have status latest 1`] = `
+[
+  [
+    "https://api.us-west-1.saucelabs.com/rest/v1/public/tunnels/info/versions",
+    {
+      "responseType": "json",
+      "searchParams": {
+        "client_host": "darwin-arm64",
+        "client_version": "5.1.1",
+      },
+    },
+  ],
+]
+`;
+
 exports[`startSauceConnect should start sauce connect with fallback default version in case the call to the API failed 1`] = `
 [
   [
diff --git a/tests/index.test.js b/tests/index.test.js
index ccb1336..52dd019 100644
--- a/tests/index.test.js
+++ b/tests/index.test.js
@@ -8,6 +8,8 @@ import FormData from 'form-data';
 import SauceLabs from '../src';
 
 import versions from './__responses__/versions.json';
+import allVersions from './__responses__/all_versions.json';
+import latestVersions from './__responses__/latest_versions.json';
 
 const instances = [];
 
@@ -421,6 +423,45 @@ test('should fail if file parameter is invalid', async () => {
   expect(result.message).toContain('Invalid file parameter');
 });
 
+test('should contain all download links', async () => {
+  const api = new SauceLabs({user: 'foo', key: 'bar'});
+  got.mockReturnValue(
+    Promise.resolve({
+      body: {
+        ...allVersions,
+      },
+    })
+  );
+  const scVersions = await api.scVersions({
+    clientVersion: '5.1.1',
+    clientHost: 'darwin-arm64',
+    all: true,
+  });
+  expect(got.mock.calls).toMatchSnapshot();
+  expect(scVersions.all_downloads['5.1.1'].linux).toMatchObject({
+    download_url:
+      'https://saucelabs.com/downloads/sauce-connect/5.1.1/sauce-connect-5.1.1_linux.x86_64.tar.gz',
+    sha256: '6247e61e39ff054cf524341a681f4045c557be79bcf63c8c501e634ef2d54a41',
+  });
+});
+
+test('should have status latest', async () => {
+  const api = new SauceLabs({user: 'foo', key: 'bar'});
+  got.mockReturnValue(
+    Promise.resolve({
+      body: {
+        ...latestVersions,
+      },
+    })
+  );
+  const scVersions = await api.scVersions({
+    clientVersion: '5.1.1',
+    clientHost: 'darwin-arm64',
+  });
+  expect(got.mock.calls).toMatchSnapshot();
+  expect(scVersions.status).toEqual('LATEST');
+});
+
 describe('startSauceConnect', () => {
   it('should start sauce connect with proper parsed args', async () => {
     const logs = [];