Skip to content

Commit 938b8ea

Browse files
authoredMay 17, 2023
Merge pull request #115 from webdriverio-community/cb-project-rewrite
Project Update
2 parents 64aaced + e806d1e commit 938b8ea

37 files changed

+11514
-2510
lines changed
 

‎.editorconfig

+15
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
# EditorConfig helps developers define and maintain consistent
2+
# coding styles between different editors and IDEs
3+
# editorconfig.org
4+
5+
root = true
6+
7+
[*]
8+
9+
indent_style = space
10+
indent_size = 2
11+
12+
end_of_line = lf
13+
charset = utf-8
14+
trim_trailing_whitespace = true
15+
insert_final_newline = true

‎.eslintrc.cjs

+75
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
/** @type {import('eslint').Linter.Config} */
2+
const config = {
3+
root: true,
4+
parser: '@typescript-eslint/parser',
5+
plugins: ['@typescript-eslint', 'unicorn', 'import'],
6+
extends: ['eslint:recommended'],
7+
env: {
8+
node: true,
9+
es6: true,
10+
},
11+
parserOptions: {
12+
ecmaVersion: 2020,
13+
sourceType: 'module',
14+
},
15+
rules: {
16+
quotes: ['error', 'single', { avoidEscape: true }],
17+
camelcase: ['error', { properties: 'never' }],
18+
semi: ['error', 'never'],
19+
indent: [2, 2],
20+
eqeqeq: ['error', 'always'],
21+
22+
'prefer-const': 'error',
23+
'no-multiple-empty-lines': [2, { max: 1, maxEOF: 1 }],
24+
'array-bracket-spacing': ['error', 'never'],
25+
'brace-style': ['error', '1tbs', { allowSingleLine: true }],
26+
'comma-spacing': ['error', { before: false, after: true }],
27+
'no-lonely-if': 'error',
28+
'dot-notation': 'error',
29+
'no-else-return': 'error',
30+
'no-tabs': 'error',
31+
'no-trailing-spaces': [
32+
'error',
33+
{
34+
skipBlankLines: false,
35+
ignoreComments: false,
36+
},
37+
],
38+
'no-var': 'error',
39+
'unicode-bom': ['error', 'never'],
40+
curly: ['error', 'all'],
41+
'object-curly-spacing': ['error', 'always'],
42+
'keyword-spacing': ['error'],
43+
'require-atomic-updates': 0,
44+
'linebreak-style': ['error', 'unix'],
45+
'unicorn/prefer-node-protocol': ['error'],
46+
'import/extensions': ['error', 'ignorePackages'],
47+
'no-restricted-syntax': [
48+
'error',
49+
'IfStatement > ExpressionStatement > AssignmentExpression',
50+
],
51+
'unicorn/prefer-ternary': 'error',
52+
},
53+
overrides: [
54+
{
55+
files: ['*.ts'],
56+
rules: {
57+
// see https://stackoverflow.com/questions/55280555/typescript-eslint-eslint-plugin-error-route-is-defined-but-never-used-no-un
58+
'no-unused-vars': 'off',
59+
'@typescript-eslint/no-unused-vars': 'error',
60+
'@typescript-eslint/consistent-type-imports': 'error',
61+
'no-undef': 'off',
62+
// allow overloads
63+
'no-redeclare': 'off',
64+
},
65+
},
66+
{
67+
files: ['*.test.ts'],
68+
rules: {
69+
'dot-notation': 'off',
70+
},
71+
},
72+
],
73+
}
74+
75+
module.exports = config

‎.github/dependabot.yml

+7
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
version: 2
2+
updates:
3+
- package-ecosystem: npm
4+
directory: "/"
5+
schedule:
6+
interval: weekly
7+
open-pull-requests-limit: 10

‎.github/workflows/audit.yml

+35
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
name: Audit
2+
on:
3+
push:
4+
branches:
5+
- main
6+
paths-ignore:
7+
- '**.md'
8+
pull_request:
9+
paths-ignore:
10+
- '**.md'
11+
12+
jobs:
13+
14+
build:
15+
name: Audit
16+
17+
runs-on: ubuntu-latest
18+
19+
steps:
20+
- name: Checkout
21+
uses: actions/checkout@v3
22+
23+
- name: Set Node.js 20.x
24+
uses: actions/setup-node@v3
25+
with:
26+
node-version: 20.x
27+
28+
- name: npm install
29+
run: npm install
30+
31+
- name: Build
32+
run: npm run build
33+
34+
- name: Audit
35+
run: npm audit --audit-level=moderate

‎.github/workflows/ci.yml

+30
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
name: CI
2+
3+
on:
4+
push:
5+
branches:
6+
- main
7+
tags:
8+
- v[0-9]+.[0-9]+.[0-9]+*
9+
pull_request:
10+
11+
jobs:
12+
build:
13+
strategy:
14+
matrix:
15+
os: [macos-latest, ubuntu-latest, windows-latest]
16+
runs-on: ${{ matrix.os }}
17+
steps:
18+
- uses: actions/checkout@v3
19+
- name: 💚 Use Node.js
20+
uses: actions/setup-node@v3
21+
with:
22+
node-version: 20
23+
- name: 🚧 Install Dependencies
24+
run: npm ci
25+
- name: 📦 Build
26+
run: npm run build
27+
- name: 🧪 Run Tests
28+
uses: GabrielBB/xvfb-action@v1
29+
with:
30+
run: npm test

‎.github/workflows/release.yml

+66
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
name: Manual NPM Publish
2+
3+
on:
4+
workflow_dispatch:
5+
inputs:
6+
releaseType:
7+
description: "Release type - major, minor or patch"
8+
required: true
9+
type: choice
10+
default: "patch"
11+
options:
12+
- patch
13+
- minor
14+
- major
15+
distTag:
16+
description: 'NPM tag (e.g. use "next" to release a test version)'
17+
required: true
18+
default: 'latest'
19+
preRelease:
20+
description: If latest release was a pre-release (e.g. X.X.X-alpha.0) and you want to push another one, pick "yes"
21+
required: true
22+
type: choice
23+
default: "no"
24+
options:
25+
- "yes"
26+
- "no"
27+
28+
env:
29+
NPM_TOKEN: ${{ secrets.NPM_TOKEN }}
30+
31+
jobs:
32+
release:
33+
runs-on: ubuntu-latest
34+
steps:
35+
- uses: actions/checkout@v3
36+
with:
37+
ref: 'main'
38+
fetch-depth: 0
39+
- uses: actions/setup-node@v3
40+
with:
41+
node-version: 20
42+
- name: NPM Setup
43+
run: |
44+
npm set registry "https://registry.npmjs.org/"
45+
npm set //registry.npmjs.org/:_authToken $NPM_TOKEN
46+
npm whoami
47+
- name: Git Setup
48+
run: |
49+
git config --global user.email "bot@webdriver.io"
50+
git config --global user.name "WebdriverIO Release Bot"
51+
- name: Install Dependencies
52+
run: npm ci
53+
- name: Build
54+
run: npm run build
55+
- name: Release
56+
run: npx release-it ${{github.event.inputs.releaseType}} --github.release --ci --npm.skipChecks --no-git.requireCleanWorkingDir --npm.tag=${{github.event.inputs.distTag}}
57+
env:
58+
NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
59+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
60+
if: ${{ github.event.inputs.preRelease == 'no' }}
61+
- name: Pre-Release
62+
run: npx release-it ${{github.event.inputs.releaseType}} --github.release --ci --npm.skipChecks --no-git.requireCleanWorkingDir --preRelease=alpha --github.preRelease --npm.tag=next
63+
env:
64+
NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
65+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
66+
if: ${{ github.event.inputs.preRelease == 'yes' }}

‎.github/workflows/test.yml

-39
This file was deleted.

‎.github/workflows/update.yml

+47
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
# this workflow merges requests from Dependabot if tests are passing
2+
# ref https://docs.github.com/en/code-security/dependabot/working-with-dependabot/automating-dependabot-with-github-actions
3+
# and https://github.com/dependabot/fetch-metadata
4+
name: Auto-merge
5+
6+
# `pull_request_target` means this uses code in the base branch, not the PR.
7+
on: pull_request_target
8+
9+
# Dependabot PRs' tokens have read permissions by default and thus we must enable write permissions.
10+
permissions:
11+
contents: write
12+
pull-requests: write
13+
14+
jobs:
15+
dependencies:
16+
runs-on: ubuntu-latest
17+
if: github.actor == 'dependabot[bot]'
18+
19+
steps:
20+
- name: Fetch PR metadata
21+
id: metadata
22+
uses: dependabot/fetch-metadata@v1.3.5
23+
with:
24+
github-token: ${{ secrets.GITHUB_TOKEN }}
25+
26+
- name: Wait for PR CI
27+
# Don't merge updates to GitHub Actions versions automatically.
28+
# (Some repos may wish to limit by version range (major/minor/patch), or scope (dep vs dev-dep), too.)
29+
if: contains(steps.metadata.outputs.package-ecosystem, 'npm')
30+
uses: lewagon/wait-on-check-action@v1.2.0
31+
with:
32+
ref: ${{ github.event.pull_request.head.sha }}
33+
repo-token: ${{ secrets.GITHUB_TOKEN }}
34+
wait-interval: 30 # seconds
35+
running-workflow-name: dependencies # wait for all checks except this one
36+
allowed-conclusions: success # all other checks must pass, being skipped or cancelled is not sufficient
37+
38+
- name: Auto-merge dependabot PRs
39+
# Don't merge updates to GitHub Actions versions automatically.
40+
# (Some repos may wish to limit by version range (major/minor/patch), or scope (dep vs dev-dep), too.)
41+
if: contains(steps.metadata.outputs.package-ecosystem, 'npm')
42+
env:
43+
PR_URL: ${{ github.event.pull_request.html_url }}
44+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
45+
# The "auto" flag will only merge once all of the target branch's required checks
46+
# are met. Configure those in the "branch protection" settings for each repo.
47+
run: gh pr merge --auto --squash "$PR_URL"

‎.gitignore

+2
Original file line numberDiff line numberDiff line change
@@ -3,3 +3,5 @@ node_modules
33
!/*/geckodriver
44
*.tar.gz
55
*.log
6+
dist
7+
.bin/

‎.husky/pre-push

+4
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
#!/bin/sh
2+
. "$(dirname "$0")/_/husky.sh"
3+
4+
npm run test:lint

‎.npmignore

+9-6
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
1-
.git
2-
geckodriver
3-
geckodriver.tar.gz
4-
.idea
5-
!bin/geckodriver
6-
.github
1+
src
2+
tests
3+
coverage
4+
*.tgz
5+
/.*
6+
/*.mjs
7+
/tsconfig.json
8+
vitest.config.ts
9+
CHANGELOG.md

‎.nvmrc

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
v20.1.0

‎AUTHORS

+1
Original file line numberDiff line numberDiff line change
@@ -24,3 +24,4 @@ pillsilly
2424
vladikoff
2525
w-ku
2626
Марат Абдулин
27+
Christian Bromann

‎CHANGELOG.md

+39
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
# Changelog
2+
3+
For updates and changelogs on v4.0.0 and above, go to https://github.com/webdriverio-community/node-geckodriver/releases.
4+
5+
* 3.2.0 - geckodriver 0.32.0, arm64 support for Mac, Linux and Windows, added `GECKODRIVER_ARCH` for custom arch downloads.
6+
* 3.1.0 - geckodriver 0.31.0
7+
* 2.0.1 - fixed proxy download behaviour.
8+
* 1.20.0 - geckodriver 27. Requires node 8 and higher. Support `HTTPS_PROXY` env and npm_config_geckodriver_version variables.
9+
* 1.19.0 - geckodriver 26. Dependency updates.
10+
* 1.18.0 - geckodriver 26.
11+
* 1.17.0 - geckodriver 25.
12+
* 1.16.2 - fix issue with 'tar' dependency.
13+
* 1.16.1 - added support for `GECKODRIVER_FILEPATH` env variable.
14+
* 1.16.0 - added support for `GECKODRIVER_VERSION` env variable. Set it to `'0.24.0'` to fetch that version.
15+
* 1.15.1 - fix for the new `.npmignore` pattern matching
16+
* 1.15.0 - geckodriver 0.24.0
17+
* 1.14.0 - geckodriver 0.23.0
18+
* 1.13.0 - geckodriver 0.22.0
19+
* 1.12.2 - add proxy settings
20+
* 1.12.1 - adm-zip security fix
21+
* 1.12.0 - geckodriver 0.21.0
22+
* 1.11.0 - geckodriver 0.20.0
23+
* 1.10.0 - geckodriver 0.19.1, switch tar package, enable Win32 builds again, process.env.npm_config_geckodriver_cdnurl support
24+
* 1.9.0 - updated to geckodriver 0.19.0 32-bit windows support removed.
25+
* 1.8.1 - added geckodriver.exe bin for Windows
26+
* 1.8.0 - updated to geckodriver 0.18.0
27+
* 1.7.1 - 'GECKODRIVER_CDNURL' support added.
28+
* 1.7.0 - updated to geckodriver 0.17.0 32-bit linux support added.
29+
* 1.6.1 - updated to geckodriver 0.16.1
30+
* 1.6.0 - updated to geckodriver 0.16.0. 32-bit linux support removed.
31+
* 1.5.0 - updated to geckodriver 0.15.0.
32+
* 1.4.0 - updated to geckodriver 0.14.0.
33+
* 1.3.0 - updated to geckodriver 0.13.0.
34+
* 1.2.1 - added support for Linux 32-bit.
35+
* 1.2.0 - updated to geckodriver 0.11.1.
36+
* 1.1.3 - adds Windows support, fixes Windows tests.
37+
* 1.1.2 - fixed `require` by pointing `package.json main` property to the `lib` file.
38+
* 1.1.0 - programmatic usage, added `bin` support.
39+
* 1.0.0 - init release

‎README.md

+185-114
Original file line numberDiff line numberDiff line change
@@ -1,153 +1,224 @@
1-
## node-geckodriver [![Build Status](https://github.com/vladikoff/node-geckodriver/workflows/Tests/badge.svg)](https://github.com/vladikoff/node-geckodriver/actions?workflow=Tests) [![npm package](https://img.shields.io/npm/v/geckodriver.svg)](https://www.npmjs.com/package/geckodriver)
1+
Geckodriver [![CI](https://github.com/webdriverio-community/node-geckodriver/actions/workflows/ci.yml/badge.svg)](https://github.com/webdriverio-community/node-geckodriver/actions/workflows/ci.yml) [![Audit](https://github.com/webdriverio-community/node-geckodriver/actions/workflows/audit.yml/badge.svg)](https://github.com/webdriverio-community/node-geckodriver/actions/workflows/audit.yml)
2+
==========
23

3-
> Downloader for [github.com/mozilla/geckodriver/releases](https://github.com/mozilla/geckodriver/releases)
4+
An NPM wrapper for Mozilla's [Geckodriver](https://github.com/mozilla/geckodriver). It manages to download various (or the latest) Geckodriver versions and provides a programmatic interface to start and stop it within Node.js. __Note:__ this is a wrapper module. If you discover any bugs with Geckodriver, please report them in the [official repository](https://github.com/mozilla/geckodriver).
45

5-
This puts `geckodriver` or `geckodriver.exe` into root of this module.
6+
# Installing
67

7-
## Install
8+
You can install this package via:
89

9-
```
10+
```sh
1011
npm install geckodriver
1112
```
1213

13-
## Usage
14+
Or install it globally:
1415

15-
There are several ways to use this module:
16+
```sh
17+
npm install -g geckodriver
18+
```
1619

17-
### Use the provided `geckodriver` from `bin` directory.
20+
__Note:__ This installs a `geckodriver` shell script that runs the executable, but on Windows, [`selenium-webdriver`](https://www.npmjs.com/package/selenium-webdriver) looks for `geckodriver.exe`. To use a global installation of this package with [`selenium-webdriver`](https://www.npmjs.com/package/selenium-webdriver) on Windows, copy or link `geckodriver.exe` to a location on your `PATH` (such as the NPM bin directory) after installing this package:
1821

19-
```
20-
bin/geckodriver [args]
22+
```sh
23+
mklink %USERPROFILE%\AppData\Roaming\npm\geckodriver.exe %USERPROFILE%\AppData\Roaming\npm\node_modules\geckodriver\geckodriver.exe
2124
```
2225

23-
### Use it by requiring:
26+
Once installed you can start Geckodriver via:
2427

25-
```
26-
require('geckodriver');
28+
```sh
29+
npx geckodriver --port=4444
2730
```
2831

29-
### Use it by setting WebDriver capabilities:
32+
By default, this package downloads Geckodriver when used for the first time through the CLI or the programmatical interface. If you like to download it as part of the NPM install process, set the `GECKODRIVER_AUTO_INSTALL` environment flag, e.g.:
3033

31-
```
32-
profile.setPreference('marionette', true);
33-
// Add log level if needed:
34-
// profile.setPreference('marionette.logging', 'TRACE');
34+
```sh
35+
GECKODRIVER_AUTO_INSTALL=1 npm i
3536
```
3637

37-
### Use it globally:
38+
To get a list of available CLI options run `npx geckodriver --help`. By default this package downloads the latest version of the driver. If you prefer to have it install a custom Geckodriver version you can define the environment variable `GECKODRIVER_VERSION` when running in CLI, e.g.:
3839

39-
```
40-
npm install -g geckodriver
41-
geckodriver [args]
42-
```
40+
```sh
41+
$ npm i geckodriver
42+
$ GECKODRIVER_VERSION="0.33.0" npx geckodriver --version
43+
geckodriver 0.31.0 (b617178ef491 2022-04-06 11:57 +0000)
4344

44-
Note: This installs a `geckodriver` shell script that runs the executable, but on Windows, selenium-webdriver looks for `geckodriver.exe`. To use a global installation of this package with selenium-webdriver on Windows, copy or link `geckodriver.exe` to a location on your PATH (such as the NPM bin directory) after installing this package:
45+
The source code of this program is available from
46+
testing/geckodriver in https://hg.mozilla.org/mozilla-central.
4547

46-
```
47-
mklink %USERPROFILE%\AppData\Roaming\npm\geckodriver.exe %USERPROFILE%\AppData\Roaming\npm\node_modules\geckodriver\geckodriver.exe
48+
This program is subject to the terms of the Mozilla Public License 2.0.
49+
You can obtain a copy of the license at https://mozilla.org/MPL/2.0/.
4850
```
4951

5052
## Setting a CDN URL for binary download
5153

5254
To set an alternate CDN location for geckodriver binaries, set the `GECKODRIVER_CDNURL` like this:
5355

54-
```
56+
```sh
5557
GECKODRIVER_CDNURL=https://INTERNAL_CDN/geckodriver/download
5658
```
5759

5860
Binaries on your CDN should be located in a subdirectory of the above base URL. For example, `/vxx.xx.xx/*.tar.gz` should be located under `/geckodriver/download` above.
5961

60-
Alternatively, you can add the same property to your `.npmrc` file.
62+
Alternatively, you can add the same property to your .npmrc file.
6163

6264
Default location is set to https://github.com/mozilla/geckodriver/releases/download
6365

6466
## Setting a PROXY URL
6567

6668
Use `HTTPS_PROXY` or `HTTP_PROXY` to set your proxy url.
6769

68-
## Setting a specific version
69-
70-
Use `GECKODRIVER_VERSION` if you require a specific version of gecko driver for your browser version.
71-
72-
## Using a cached download
73-
74-
Use `GECKODRIVER_FILEPATH` to point to a pre-downloaded geckodriver archive that should be extracted during installation.
75-
76-
## Skipping geckodriver download
77-
78-
Use `GECKODRIVER_SKIP_DOWNLOAD` to skip the download of the geckodriver file.
79-
80-
81-
## Related Projects
82-
83-
* [node-chromedriver](https://github.com/giggio/node-chromedriver)
84-
85-
## Versions
86-
87-
* [npm module version] - [geckodriver version]
88-
* 4.0.0 - geckodriver 0.32.0.
89-
* 3.2.0 - geckodriver 0.32.0, arm64 support.
90-
* 3.1.0 - geckodriver 0.31.0
91-
* 3.0.x - geckodriver 0.30.0, refactored logic, dependency updates.
92-
* 2.00.x - geckodriver 0.29.1, support changed to node v12+
93-
* 1.22.x - geckodriver 0.29.0
94-
* 1.21.x - geckodriver 0.28.0
95-
* 1.20.x - geckodriver 0.27.0
96-
* 1.19.x - geckodriver 0.26.0
97-
* 1.18.x - geckodriver 0.26.0
98-
* 1.17.x - geckodriver 0.25.0
99-
* 1.16.x - geckodriver 0.24.0 and `GECKODRIVER_VERSION` env support
100-
* 1.15.x - geckodriver 0.24.0
101-
* 1.14.x - geckodriver 0.23.0
102-
* 1.13.x - geckodriver 0.22.0
103-
* 1.12.x - geckodriver 0.21.0
104-
* 1.11.x - geckodriver 0.20.0
105-
* 1.10.x - geckodriver 0.19.1
106-
* 1.9.x - geckodriver 0.19.0
107-
* 1.8.x - geckodriver 0.18.0
108-
* 1.7.x - geckodriver 0.17.0
109-
* 1.6.x - geckodriver 0.16.1
110-
* 1.5.x - geckodriver 0.15.0
111-
* 1.4.x - geckodriver 0.14.0
112-
* 1.3.x - geckodriver 0.13.0
113-
* 1.2.x - geckodriver 0.11.1
114-
* 1.1.x - geckodriver 0.10
115-
116-
## Changelog
117-
118-
* 4.0.0 - requires node 14+, drops support for node 12.
119-
* 3.2.0 - geckodriver 0.32.0, arm64 support for Mac, Linux and Windows, added `GECKODRIVER_ARCH` for custom arch downloads.
120-
* 3.1.0 - geckodriver 0.31.0
121-
* 2.0.1 - fixed proxy download behaviour.
122-
* 1.20.0 - geckodriver 27. Requires node 8 and higher. Support `HTTPS_PROXY` env and npm_config_geckodriver_version variables.
123-
* 1.19.0 - geckodriver 26. Dependency updates.
124-
* 1.18.0 - geckodriver 26.
125-
* 1.17.0 - geckodriver 25.
126-
* 1.16.2 - fix issue with 'tar' dependency.
127-
* 1.16.1 - added support for `GECKODRIVER_FILEPATH` env variable.
128-
* 1.16.0 - added support for `GECKODRIVER_VERSION` env variable. Set it to `'0.24.0'` to fetch that version.
129-
* 1.15.1 - fix for the new `.npmignore` pattern matching
130-
* 1.15.0 - geckodriver 0.24.0
131-
* 1.14.0 - geckodriver 0.23.0
132-
* 1.13.0 - geckodriver 0.22.0
133-
* 1.12.2 - add proxy settings
134-
* 1.12.1 - adm-zip security fix
135-
* 1.12.0 - geckodriver 0.21.0
136-
* 1.11.0 - geckodriver 0.20.0
137-
* 1.10.0 - geckodriver 0.19.1, switch tar package, enable Win32 builds again, process.env.npm_config_geckodriver_cdnurl support
138-
* 1.9.0 - updated to geckodriver 0.19.0 32-bit windows support removed.
139-
* 1.8.1 - added geckodriver.exe bin for Windows
140-
* 1.8.0 - updated to geckodriver 0.18.0
141-
* 1.7.1 - 'GECKODRIVER_CDNURL' support added.
142-
* 1.7.0 - updated to geckodriver 0.17.0 32-bit linux support added.
143-
* 1.6.1 - updated to geckodriver 0.16.1
144-
* 1.6.0 - updated to geckodriver 0.16.0. 32-bit linux support removed.
145-
* 1.5.0 - updated to geckodriver 0.15.0.
146-
* 1.4.0 - updated to geckodriver 0.14.0.
147-
* 1.3.0 - updated to geckodriver 0.13.0.
148-
* 1.2.1 - added support for Linux 32-bit.
149-
* 1.2.0 - updated to geckodriver 0.11.1.
150-
* 1.1.3 - adds Windows support, fixes Windows tests.
151-
* 1.1.2 - fixed `require` by pointing `package.json main` property to the `lib` file.
152-
* 1.1.0 - programmatic usage, added `bin` support.
153-
* 1.0.0 - init release
70+
# Programmatic Interface
71+
72+
You can import this package with Node.js and start the driver as part of your script and use it e.g. with [WebdriverIO](https://webdriver.io).
73+
74+
## Exported Methods
75+
76+
The package exports a `start` and `download` method.
77+
78+
### `start`
79+
80+
Starts an Geckodriver instance and returns a [`ChildProcess`](https://nodejs.org/api/child_process.html#class-childprocess). If Geckodriver is not downloaded it will download it for you.
81+
82+
__Params:__ `GeckodriverParameters` - options to pass into Geckodriver (see below)
83+
84+
__Example:__
85+
86+
```js
87+
import { start } from 'geckodriver';
88+
import { remote } from 'webdriverio';
89+
import waitPort from 'wait-port';
90+
91+
/**
92+
* first start Geckodriver
93+
*/
94+
const cp = await start({ port: 4444 });
95+
96+
/**
97+
* wait for Geckodriver to be up
98+
*/
99+
await waitPort({ port: 4444 });
100+
101+
/**
102+
* then start WebdriverIO session
103+
*/
104+
const browser = await remote({ capabilities: { browserName: 'firefox' } });
105+
await browser.url('https://webdriver.io');
106+
console.log(await browser.getTitle()); // prints "WebdriverIO · Next-gen browser and mobile automation test framework for Node.js | WebdriverIO"
107+
108+
/**
109+
* kill Geckodriver process
110+
*/
111+
cp.kill();
112+
```
113+
114+
__Note:__ as you can see in the example above this package does not wait for the driver to be up, you have to manage this yourself through packages like [`wait-on`](https://github.com/jeffbski/wait-on).
115+
116+
### `download`
117+
118+
Method to download an Geckodriver with a particular version. If version parameter is omitted it tries to download the latest available version of the driver.
119+
120+
__Params:__ `string` - version of Geckodriver to download (optional)
121+
122+
## CJS Support
123+
124+
In case your module uses CJS you can use this package as follows:
125+
126+
```js
127+
const { start } = require('geckodriver')
128+
// see example above
129+
```
130+
131+
## Options
132+
133+
The `start` method offers the following options to be passed on to the actual Geckodriver CLI.
134+
135+
### allowHosts
136+
137+
List of hostnames to allow. By default the value of --host is allowed, and in addition if that's a well known local address, other variations on well known local addresses are allowed. If --allow-hosts is provided only exactly those hosts are allowed.
138+
139+
Type: `string[]`<br />
140+
Default: `[]`
141+
142+
### allowOrigins
143+
List of request origins to allow. These must be formatted as scheme://host:port. By default any request with an origin header is rejected. If `--allow-origins` is provided then only exactly those origins are allowed.
144+
145+
Type: `string[]`<br />
146+
Default: `[]`
147+
148+
### binary
149+
Path to the Firefox binary.
150+
151+
Type: `string`
152+
153+
### connectExisting
154+
Connect to an existing Firefox instance.
155+
156+
Type: `boolean`<br />
157+
Default: `false`
158+
159+
### host
160+
Host IP to use for WebDriver server.
161+
162+
Type: `string`<br />
163+
Default: `127.0.0.1`
164+
165+
### jsdebugger
166+
Attach browser toolbox debugger for Firefox.
167+
168+
Type: `boolean`<br />
169+
Default: `false`
170+
171+
### log
172+
Set Gecko log level [possible values: `fatal`, `error`, `warn`, `info`, `config`, `debug`, `trace`].
173+
174+
Type: `string`
175+
176+
### logNoTruncated
177+
Write server log to file instead of stderr, increases log level to `INFO`.
178+
179+
Type: `boolean`
180+
181+
### marionetteHost
182+
Host to use to connect to Gecko.
183+
184+
Type: `boolean`<br />
185+
Default: `127.0.0.1`
186+
187+
### marionettePort
188+
Port to use to connect to Gecko.
189+
190+
Type: `number`<br />
191+
Default: `0`
192+
193+
### port
194+
Port to listen on.
195+
196+
Type: `number`
197+
198+
### profileRoot
199+
Directory in which to create profiles. Defaults to the system temporary directory.
200+
201+
Type: `string`
202+
203+
### geckoDriverVersion
204+
Version of Geckodriver to start. See https://github.com/mozilla/geckodriver/releases for all available versions, platforms and architecture.
205+
206+
Type: `string`
207+
208+
### customGeckoDriverPath
209+
Don't download Geckodriver, instead use a custom path to it, e.g. a cached binary.
210+
211+
Type: `string`<br />
212+
Default: `process.env.GECKODRIVER_FILEPATH`
213+
214+
# Other Browser Driver
215+
216+
If you also look for other browser driver NPM wrapper, you can find them here:
217+
218+
- Chrome: [giggio/node-chromedriver](https://github.com/giggio/node-chromedriver)
219+
- Microsoft Edge: [webdriverio-community/node-edgedriver](https://github.com/webdriverio-community/node-edgedriver)
220+
- Safari: [webdriverio-community/node-safaridriver](https://github.com/webdriverio-community/node-safaridriver)
221+
222+
---
223+
224+
For more information on WebdriverIO see the [homepage](https://webdriver.io).

‎bin/geckodriver

-10
This file was deleted.

‎bin/geckodriver.js

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
#!/usr/bin/env node
2+
3+
import run from '../dist/cli.js'
4+
5+
run()

‎index.js

-130
This file was deleted.

‎lib/geckodriver.d.ts

-12
This file was deleted.

‎lib/geckodriver.js

-21
This file was deleted.

‎package-lock.json

+10,505-2,118
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

‎package.json

+66-23
Original file line numberDiff line numberDiff line change
@@ -1,40 +1,83 @@
11
{
22
"name": "geckodriver",
3-
"version": "4.0.0",
4-
"description": "Downloader for https://github.com/mozilla/geckodriver/releases",
5-
"scripts": {
6-
"test": "ava",
7-
"postinstall": "node index.js"
8-
},
9-
"repository": {
10-
"type": "git",
11-
"url": "git+https://github.com/vladikoff/node-geckodriver.git"
12-
},
3+
"version": "3.2.0",
4+
"description": "Mozilla's Geckodriver for Node.js",
5+
"homepage": "https://github.com/webdriverio-community/node-geckodriver#readme",
136
"author": {
147
"name": "vladikoff",
158
"email": "vlad.filippov@gmail.com",
169
"url": "http://vf.io"
1710
},
11+
"license": "MPL-2.0",
12+
"keywords": [
13+
"geckodriver",
14+
"webdriver"
15+
],
16+
"repository": {
17+
"type": "git",
18+
"url": "git+https://github.com/webdriverio-community/node-geckodriver.git"
19+
},
20+
"scripts": {
21+
"build": "tsc -b .",
22+
"clean": "rimraf ./node_modules package-lock.yaml ./dist",
23+
"prepare": "husky install",
24+
"postinstall": "test -f ./dist/install.js && node ./dist/install.js || echo \"Skipping install, project not build!\"",
25+
"test": "run-s test:*",
26+
"test:lint": "eslint",
27+
"test:unit": "vitest --run",
28+
"test:e2e": "node ./tests/test.e2e.js",
29+
"watch": "npm run build -- --watch"
30+
},
1831
"engines": {
19-
"node": ">=14.0.0"
32+
"node": "^16.13 || >=18 || >=20"
33+
},
34+
"type": "module",
35+
"types": "./dist/index.d.ts",
36+
"main": "./dist/cjs/index.js",
37+
"exports": {
38+
".": [
39+
{
40+
"types": "./dist/index.d.ts",
41+
"import": "./dist/index.js",
42+
"require": "./dist/cjs/index.js"
43+
},
44+
"./dist/cjs/index.js"
45+
]
2046
},
21-
"main": "lib/geckodriver",
2247
"bin": {
2348
"geckodriver": "./bin/geckodriver"
2449
},
25-
"license": "MPL-2.0",
2650
"bugs": {
27-
"url": "https://github.com/vladikoff/node-geckodriver/issues"
28-
},
29-
"homepage": "https://github.com/vladikoff/node-geckodriver#readme",
30-
"dependencies": {
31-
"adm-zip": "0.5.9",
32-
"bluebird": "3.7.2",
33-
"got": "11.8.5",
34-
"tar": "6.1.11",
35-
"https-proxy-agent": "5.0.1"
51+
"url": "https://github.com/webdriverio-community/node-geckodriver/issues"
3652
},
3753
"devDependencies": {
38-
"ava": "3.15.0"
54+
"@types/node": "^20.1.5",
55+
"@types/tar-fs": "^2.0.1",
56+
"@types/unzipper": "^0.10.6",
57+
"@typescript-eslint/eslint-plugin": "^5.59.6",
58+
"@typescript-eslint/parser": "^5.59.6",
59+
"@vitest/coverage-c8": "^0.31.0",
60+
"eslint": "^8.40.0",
61+
"eslint-plugin-import": "^2.27.5",
62+
"eslint-plugin-unicorn": "^47.0.0",
63+
"husky": "^8.0.3",
64+
"npm-run-all": "^4.1.5",
65+
"octokit": "^2.0.14",
66+
"release-it": "^15.10.3",
67+
"ts-node": "^10.9.1",
68+
"typescript": "^5.0.4",
69+
"vitest": "^0.31.0",
70+
"wait-port": "^1.0.4",
71+
"webdriverio": "^8.10.2"
72+
},
73+
"dependencies": {
74+
"@wdio/logger": "^8.6.6",
75+
"decamelize": "^6.0.0",
76+
"http-proxy-agent": "^6.0.1",
77+
"https-proxy-agent": "^6.1.0",
78+
"node-fetch": "^3.3.1",
79+
"tar-fs": "^2.1.1",
80+
"unzipper": "^0.10.14",
81+
"which": "^3.0.1"
3982
}
4083
}

‎src/cjs/index.ts

+9
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
exports.start = async function start (params: unknown) {
2+
const esmPkg = await import('../index.js')
3+
return esmPkg.start(params)
4+
}
5+
6+
exports.download = async function download (params?: string) {
7+
const esmPkg = await import('../index.js')
8+
return esmPkg.download(params)
9+
}

‎src/cjs/package.json

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{
2+
"type": "commonjs"
3+
}

‎src/cli.ts

+28
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
import url from 'node:url'
2+
import path from 'node:path'
3+
import cp from 'node:child_process'
4+
5+
import { download } from './install.js'
6+
import { hasAccess } from './utils.js'
7+
import { BINARY_FILE } from './constants.js'
8+
9+
const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
10+
11+
export default async function run () {
12+
await download()
13+
const targetDir = path.resolve(__dirname, '..', '.bin')
14+
const binaryFilePath = path.resolve(targetDir, BINARY_FILE)
15+
16+
if (!(await hasAccess(binaryFilePath))) {
17+
throw new Error('Failed to download Geckodriver')
18+
}
19+
20+
const child = cp.spawn(binaryFilePath, process.argv.slice(2))
21+
child.stdout.pipe(process.stdout)
22+
child.stderr.pipe(process.stderr)
23+
child.on('exit', process.exit)
24+
process.on('SIGTERM', function() {
25+
child.kill('SIGTERM')
26+
process.exit(1)
27+
})
28+
}

‎src/constants.ts

+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
import os from 'node:os'
2+
3+
export const MOZ_CENTRAL_CARGO_TOML = 'https://hg.mozilla.org/mozilla-central/raw-file/tip/testing/geckodriver/Cargo.toml'
4+
export const BASE_CDN_URL = process.env.GECKODRIVER_CDNURL || process.env.npm_config_geckodriver_cdnurl || 'https://github.com/mozilla/geckodriver/releases/download'
5+
// e.g. https://github.com/mozilla/geckodriver/releases/download/v0.33.0/geckodriver-v0.33.0-macos-aarch64.tar.gz
6+
export const GECKODRIVER_DOWNLOAD_PATH = `${BASE_CDN_URL}/v%s/geckodriver-v%s-%s%s%s`
7+
8+
export const BINARY_FILE = 'geckodriver' + (os.platform() === 'win32' ? '.exe' : '')

‎src/index.ts

+28
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
import url from 'node:url'
2+
import path from 'node:path'
3+
import cp from 'node:child_process'
4+
5+
import { download as downloadDriver } from './install.js'
6+
import { hasAccess, parseParams } from './utils.js'
7+
import { BINARY_FILE } from './constants.js'
8+
import type { GeckodriverParameters } from 'types.js'
9+
10+
const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
11+
12+
export async function start (params: GeckodriverParameters) {
13+
const customGeckoDriverPath = process.env.GECKODRIVER_FILEPATH || params.customGeckoDriverPath
14+
if (!customGeckoDriverPath) {
15+
await downloadDriver(params.geckoDriverVersion)
16+
}
17+
const targetDir = path.resolve(__dirname, '..', '.bin')
18+
const binaryFilePath = customGeckoDriverPath || path.resolve(targetDir, BINARY_FILE)
19+
20+
if (!(await hasAccess(binaryFilePath))) {
21+
throw new Error('Failed to access Geckodriver, was it installed successfully?')
22+
}
23+
24+
return cp.spawn(binaryFilePath, parseParams(params))
25+
}
26+
27+
export const download = downloadDriver
28+
export * from './types.js'

‎src/install.ts

+107
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
import url from 'node:url'
2+
import path from 'node:path'
3+
import util from 'node:util'
4+
import stream from 'node:stream'
5+
import fs from 'node:fs'
6+
import fsp from 'node:fs/promises'
7+
import zlib from 'node:zlib'
8+
import { Readable } from 'node:stream'
9+
10+
import tar from 'tar-fs'
11+
import fetch, { type RequestInit } from 'node-fetch'
12+
import { HttpsProxyAgent } from 'https-proxy-agent'
13+
import { HttpProxyAgent } from 'http-proxy-agent'
14+
import unzipper, { type Entry } from 'unzipper'
15+
import logger from '@wdio/logger'
16+
17+
import { BINARY_FILE, MOZ_CENTRAL_CARGO_TOML } from './constants.js'
18+
import { hasAccess, getDownloadUrl } from './utils.js'
19+
20+
const streamPipeline = util.promisify(stream.pipeline)
21+
const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
22+
const log = logger('geckodriver')
23+
24+
const fetchOpts: RequestInit = {}
25+
if (process.env.HTTPS_PROXY) {
26+
fetchOpts.agent = new HttpsProxyAgent(process.env.HTTPS_PROXY)
27+
} else if (process.env.HTTP_PROXY) {
28+
fetchOpts.agent = new HttpProxyAgent(process.env.HTTP_PROXY)
29+
}
30+
31+
export async function download (geckodriverVersion: string = process.env.GECKODRIVER_VERSION) {
32+
const targetDir = path.resolve(__dirname, '..', '.bin')
33+
const binaryFilePath = path.resolve(targetDir, BINARY_FILE)
34+
35+
if (await hasAccess(binaryFilePath)) {
36+
return binaryFilePath
37+
}
38+
39+
/**
40+
* get latest version of Geckodriver
41+
*/
42+
if (!geckodriverVersion) {
43+
const res = await fetch(MOZ_CENTRAL_CARGO_TOML, fetchOpts)
44+
const toml = await res.text()
45+
const version = toml.split('\n').find((l) => l.startsWith('version = '))
46+
if (!version) {
47+
throw new Error(`Couldn't find version property in Cargo.toml file: ${toml}`)
48+
}
49+
geckodriverVersion = version.split(' = ').pop().slice(1, -1)
50+
log.info(`Detected Geckodriver v${geckodriverVersion} to be latest`)
51+
}
52+
53+
const url = getDownloadUrl(geckodriverVersion)
54+
log.info(`Downloading Geckodriver from ${url}`)
55+
const res = await fetch(url, fetchOpts)
56+
57+
if (res.status !== 200) {
58+
throw new Error(`Failed to download binary (statusCode ${res.status}): ${res.statusText}`)
59+
}
60+
61+
await fsp.mkdir(targetDir, { recursive: true })
62+
await (url.endsWith('.zip')
63+
? downloadZip(res.body, targetDir)
64+
: streamPipeline(res.body, zlib.createGunzip(), tar.extract(targetDir)))
65+
66+
await fsp.chmod(binaryFilePath, '755')
67+
return binaryFilePath
68+
}
69+
70+
function downloadZip(body: NodeJS.ReadableStream, targetDir: string) {
71+
const stream = Readable.from(body).pipe(unzipper.Parse())
72+
const promiseChain: Promise<string | void>[] = [
73+
new Promise((resolve, reject) => {
74+
stream.on('close', () => resolve())
75+
stream.on('error', () => reject())
76+
})
77+
]
78+
79+
stream.on('entry', async (entry: Entry) => {
80+
const unzippedFilePath = path.join(targetDir, entry.path)
81+
if (entry.type === 'Directory') {
82+
return
83+
}
84+
85+
if (!await hasAccess(path.dirname(unzippedFilePath))) {
86+
await fsp.mkdir(path.dirname(unzippedFilePath), { recursive: true })
87+
}
88+
89+
const execStream = entry.pipe(fs.createWriteStream(unzippedFilePath))
90+
promiseChain.push(new Promise((resolve, reject) => {
91+
execStream.on('close', () => resolve(unzippedFilePath))
92+
execStream.on('error', reject)
93+
}))
94+
})
95+
96+
return Promise.all(promiseChain)
97+
}
98+
99+
/**
100+
* download on install
101+
*/
102+
if (process.argv[1] && process.argv[1].endsWith('/dist/install.js') && Boolean(process.env.GECKODRIVER_AUTO_INSTALL || '1')) {
103+
await download().then(
104+
() => log.info('Success!'),
105+
(err) => log.error(`Failed to install Geckodriver: ${err.stack}`)
106+
)
107+
}

‎src/types.ts

+71
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
export type LogLevel = 'fatal' | 'error' | 'warn' | 'info' | 'config' | 'debug' | 'trace'
2+
3+
export interface GeckodriverParameters {
4+
/**
5+
* List of hostnames to allow. By default the value of --host is allowed, and in addition if that's a well
6+
* known local address, other variations on well known local addresses are allowed. If --allow-hosts is
7+
* provided only exactly those hosts are allowed
8+
* @default []
9+
*/
10+
allowHosts?: string[]
11+
/**
12+
* List of request origins to allow. These must be formatted as scheme://host:port. By default any request
13+
* with an origin header is rejected. If --allow-origins is provided then only exactly those origins
14+
* are allowed.
15+
* @default []
16+
*/
17+
allowOrigins?: string[]
18+
/**
19+
* Path to the Firefox binary
20+
*/
21+
binary?: string
22+
/**
23+
* Connect to an existing Firefox instance
24+
* @default false
25+
*/
26+
connectExisting?: boolean
27+
/**
28+
* Host IP to use for WebDriver server
29+
* @default 127.0.0.1
30+
*/
31+
host?: string
32+
/**
33+
* Attach browser toolbox debugger for Firefox
34+
* @default false
35+
*/
36+
jsdebugger?: boolean
37+
/**
38+
* Set Gecko log level [possible values: fatal, error, warn, info, config, debug, trace]
39+
*/
40+
log?: LogLevel
41+
/**
42+
* write server log to file instead of stderr, increases log level to INFO
43+
*/
44+
logNoTruncated?: boolean
45+
/**
46+
* Host to use to connect to Gecko
47+
* @default 127.0.0.1
48+
*/
49+
marionetteHost?: string
50+
/**
51+
* Port to use to connect to Gecko
52+
* @default 0
53+
*/
54+
marionettePort?: number
55+
/**
56+
* port to listen on
57+
*/
58+
port?: number
59+
/**
60+
* Directory in which to create profiles. Defaults to the system temporary directory.
61+
*/
62+
profileRoot?: string
63+
/**
64+
* Version of Geckodriver to start. See https://github.com/mozilla/geckodriver/releases for all available versions, platforms and architecture.
65+
*/
66+
geckoDriverVersion?: string
67+
/**
68+
* Don't download Geckodriver, instead use a custom path to it, e.g. a cached binary.
69+
*/
70+
customGeckoDriverPath?: string
71+
}

‎src/utils.ts

+44
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
import os from 'node:os'
2+
import util from 'node:util'
3+
import fs from 'node:fs/promises'
4+
5+
import decamelize from 'decamelize'
6+
7+
import { GECKODRIVER_DOWNLOAD_PATH } from './constants.js'
8+
import type { GeckodriverParameters } from './types.js'
9+
10+
export async function hasAccess(filePath: string) {
11+
return fs.access(filePath).then(() => true, () => false)
12+
}
13+
14+
export function getDownloadUrl (version: string) {
15+
const platformIdentifier = os.platform() === 'win32'
16+
? 'win'
17+
: os.platform() === 'darwin'
18+
? 'macos'
19+
: 'linux'
20+
const arch = os.arch() === 'arm64'
21+
? '-aarch64'
22+
: platformIdentifier === 'macos'
23+
? ''
24+
: os.arch() === 'x64'
25+
? '64'
26+
: '32'
27+
const ext = os.platform() === 'win32' ? '.zip' : '.tar.gz'
28+
return util.format(GECKODRIVER_DOWNLOAD_PATH, version, version, platformIdentifier, arch, ext)
29+
}
30+
31+
const EXCLUDED_PARAMS = ['version', 'help']
32+
export function parseParams (params: GeckodriverParameters) {
33+
return Object.entries(params)
34+
.filter(([key,]) => !EXCLUDED_PARAMS.includes(key))
35+
.map(([key, val]) => {
36+
if (typeof val === 'boolean' && !val) {
37+
return ''
38+
}
39+
const vals = Array.isArray(val) ? val : [val]
40+
return vals.map((v) => `--${decamelize(key, { separator: '-' })}${typeof v === 'boolean' ? '' : `=${v}`}`)
41+
})
42+
.flat()
43+
.filter(Boolean)
44+
}

‎test/index.js

-37
This file was deleted.

‎tests/__snapshots__/unit.test.ts.snap

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
2+
3+
exports[`getDownloadUrl 1`] = `"https://github.com/mozilla/geckodriver/releases/download/v0.33.0/geckodriver-v0.33.0-linux32.tar.gz"`;
4+
5+
exports[`getDownloadUrl 2`] = `"https://github.com/mozilla/geckodriver/releases/download/v0.33.0/geckodriver-v0.33.0-linux-aarch64.tar.gz"`;
6+
7+
exports[`getDownloadUrl 3`] = `"https://github.com/mozilla/geckodriver/releases/download/v0.33.0/geckodriver-v0.33.0-win32.zip"`;
8+
9+
exports[`getDownloadUrl 4`] = `"https://github.com/mozilla/geckodriver/releases/download/v0.33.0/geckodriver-v0.33.0-win-aarch64.zip"`;
10+
11+
exports[`getDownloadUrl 5`] = `"https://github.com/mozilla/geckodriver/releases/download/v0.33.0/geckodriver-v0.33.0-macos.tar.gz"`;
12+
13+
exports[`getDownloadUrl 6`] = `"https://github.com/mozilla/geckodriver/releases/download/v0.33.0/geckodriver-v0.33.0-macos-aarch64.tar.gz"`;
14+
15+
exports[`parseParams 1`] = `
16+
[
17+
"--base-url=foobar",
18+
"--silent",
19+
"--allowed-ips=123",
20+
"--allowed-ips=321",
21+
]
22+
`;

‎tests/interop/cjs.test.ts

+9
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
import { test, expect } from 'vitest'
2+
3+
// eslint-disable-next-line import/extensions
4+
const { start, download } = require('../..')
5+
6+
test('should work in CJS context', () => {
7+
expect(typeof start).toBe('function')
8+
expect(typeof download).toBe('function')
9+
})

‎tests/interop/package.json

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{
2+
"type": "commonjs"
3+
}

‎tests/test.e2e.js

+27
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
import waitPort from 'wait-port'
2+
import { remote } from 'webdriverio'
3+
4+
import { start } from '../dist/index.js'
5+
6+
const port = 4444
7+
const cp = await start({ port })
8+
9+
try {
10+
await waitPort({ port: 4444 })
11+
const browser = await remote({
12+
automationProtocol: 'webdriver',
13+
capabilities: {
14+
browserName: 'firefox',
15+
'moz:firefoxOptions': {
16+
args: ['-headless']
17+
}
18+
}
19+
})
20+
await browser.url('https://webdriver.io')
21+
await browser.deleteSession()
22+
} catch (err) {
23+
console.error(err)
24+
process.exit(1)
25+
} finally {
26+
cp.kill()
27+
}

‎tests/unit.test.ts

+37
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
import os from 'node:os'
2+
import { vi, test, expect } from 'vitest'
3+
4+
import { getDownloadUrl, parseParams } from '../src/utils.js'
5+
6+
vi.mock('node:os', () => ({
7+
default: {
8+
arch: vi.fn(),
9+
platform: vi.fn()
10+
}
11+
}))
12+
13+
test('getDownloadUrl', () => {
14+
vi.mocked(os.arch).mockReturnValue('arm')
15+
vi.mocked(os.platform).mockReturnValue('linux')
16+
expect(getDownloadUrl('0.33.0')).toMatchSnapshot()
17+
vi.mocked(os.arch).mockReturnValue('arm64')
18+
vi.mocked(os.platform).mockReturnValue('linux')
19+
expect(getDownloadUrl('0.33.0')).toMatchSnapshot()
20+
vi.mocked(os.arch).mockReturnValue('arm')
21+
vi.mocked(os.platform).mockReturnValue('win32')
22+
expect(getDownloadUrl('0.33.0')).toMatchSnapshot()
23+
vi.mocked(os.arch).mockReturnValue('arm64')
24+
vi.mocked(os.platform).mockReturnValue('win32')
25+
expect(getDownloadUrl('0.33.0')).toMatchSnapshot()
26+
vi.mocked(os.arch).mockReturnValue('x64')
27+
vi.mocked(os.platform).mockReturnValue('darwin')
28+
expect(getDownloadUrl('0.33.0')).toMatchSnapshot()
29+
vi.mocked(os.arch).mockReturnValue('arm64')
30+
vi.mocked(os.platform).mockReturnValue('darwin')
31+
expect(getDownloadUrl('0.33.0')).toMatchSnapshot()
32+
})
33+
34+
test('parseParams', () => {
35+
expect(parseParams({ baseUrl: 'foobar', silent: true, verbose: false, allowedIps: ['123', '321'] }))
36+
.toMatchSnapshot()
37+
})

‎tsconfig.json

+26
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
{
2+
"compilerOptions": {
3+
"module": "ESNext",
4+
"target": "ES2020",
5+
"baseUrl": "src",
6+
"outDir": "./dist",
7+
"moduleResolution": "node",
8+
"declaration": true,
9+
"declarationMap": true,
10+
"noUnusedLocals": true,
11+
"skipLibCheck": true,
12+
"sourceMap": true,
13+
"allowSyntheticDefaultImports": true,
14+
"newLine": "lf",
15+
"noEmitOnError": true,
16+
"lib": ["ES2020"],
17+
"noImplicitAny": true,
18+
"resolveJsonModule": true,
19+
"experimentalDecorators": true,
20+
"checkJs": true,
21+
"types": ["node"]
22+
},
23+
"include": ["src/**/*", "src/cjs/package.json"],
24+
"ignore": ["node_modules", "dist"]
25+
}
26+

0 commit comments

Comments
 (0)
Please sign in to comment.