@wordpress/env 7.0.0 → 8.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +38 -40
- package/bin/wp-env +18 -2
- package/lib/cli.js +29 -8
- package/lib/commands/clean.js +2 -3
- package/lib/commands/destroy.js +11 -7
- package/lib/commands/run.js +28 -60
- package/lib/commands/start.js +5 -6
- package/lib/config/get-config-from-environment-vars.js +34 -14
- package/lib/config/load-config.js +2 -2
- package/lib/config/merge-configs.js +2 -1
- package/lib/config/parse-config.js +123 -40
- package/lib/config/post-process-config.js +3 -3
- package/lib/config/test/__snapshots__/config-integration.js.snap +28 -4
- package/lib/config/test/config-integration.js +29 -8
- package/lib/config/test/merge-configs.js +10 -0
- package/lib/config/test/parse-config.js +105 -54
- package/lib/config/test/parse-source-string.js +1 -1
- package/lib/config/test/post-process-config.js +6 -2
- package/lib/config/test/validate-config.js +80 -22
- package/lib/config/validate-config.js +34 -8
- package/lib/env.js +2 -2
- package/lib/execute-lifecycle-script.js +86 -0
- package/lib/get-host-user.js +4 -8
- package/lib/init-config.js +11 -6
- package/lib/test/cli.js +1 -1
- package/lib/test/execute-lifecycle-script.js +59 -0
- package/lib/validate-run-container.js +41 -0
- package/package.json +2 -2
- package/lib/execute-after-setup.js +0 -51
- package/lib/test/execute-after-setup.js +0 -66
package/lib/init-config.js
CHANGED
|
@@ -133,8 +133,8 @@ ARG HOST_USERNAME
|
|
|
133
133
|
ARG HOST_UID
|
|
134
134
|
ARG HOST_GID
|
|
135
135
|
# When the IDs are already in use we can still safely move on.
|
|
136
|
-
RUN groupadd -g $HOST_GID $HOST_USERNAME || true
|
|
137
|
-
RUN useradd -
|
|
136
|
+
RUN groupadd -o -g $HOST_GID $HOST_USERNAME || true
|
|
137
|
+
RUN useradd -mlo -u $HOST_UID -g $HOST_GID $HOST_USERNAME || true
|
|
138
138
|
|
|
139
139
|
# Install any dependencies we need in the container.
|
|
140
140
|
${ installDependencies( 'wordpress', env, config ) }`;
|
|
@@ -202,15 +202,20 @@ RUN apt-get -qy install $PHPIZE_DEPS && touch /usr/local/etc/php/php.ini
|
|
|
202
202
|
|
|
203
203
|
# Set up sudo so they can have root access.
|
|
204
204
|
RUN apt-get -qy install sudo
|
|
205
|
-
RUN echo "
|
|
205
|
+
RUN echo "#$HOST_UID ALL=(ALL) NOPASSWD:ALL" >> /etc/sudoers`;
|
|
206
206
|
break;
|
|
207
207
|
}
|
|
208
208
|
case 'cli': {
|
|
209
209
|
dockerFileContent += `
|
|
210
|
+
# Make sure we're working with the latest packages.
|
|
210
211
|
RUN apk update
|
|
212
|
+
|
|
213
|
+
# Install some basic PHP dependencies.
|
|
211
214
|
RUN apk --no-cache add $PHPIZE_DEPS && touch /usr/local/etc/php/php.ini
|
|
215
|
+
|
|
216
|
+
# Set up sudo so they can have root access.
|
|
212
217
|
RUN apk --no-cache add sudo linux-headers
|
|
213
|
-
RUN echo "
|
|
218
|
+
RUN echo "#$HOST_UID ALL=(ALL) NOPASSWD:ALL" >> /etc/sudoers`;
|
|
214
219
|
break;
|
|
215
220
|
}
|
|
216
221
|
default: {
|
|
@@ -238,8 +243,8 @@ RUN rm /tmp/composer-setup.php`;
|
|
|
238
243
|
// Install any Composer packages we might need globally.
|
|
239
244
|
// Make sure to do this as the user and ensure the binaries are available in the $PATH.
|
|
240
245
|
dockerFileContent += `
|
|
241
|
-
USER $
|
|
242
|
-
ENV PATH="\${PATH}
|
|
246
|
+
USER $HOST_UID:$HOST_GID
|
|
247
|
+
ENV PATH="\${PATH}:~/.composer/vendor/bin"
|
|
243
248
|
RUN composer global require --dev yoast/phpunit-polyfills:"^1.0"
|
|
244
249
|
USER root`;
|
|
245
250
|
|
package/lib/test/cli.js
CHANGED
|
@@ -22,7 +22,7 @@ jest.mock( '../env', () => {
|
|
|
22
22
|
clean: jest.fn( Promise.resolve.bind( Promise ) ),
|
|
23
23
|
run: jest.fn( Promise.resolve.bind( Promise ) ),
|
|
24
24
|
ValidationError: actual.ValidationError,
|
|
25
|
-
|
|
25
|
+
LifecycleScriptError: actual.LifecycleScriptError,
|
|
26
26
|
};
|
|
27
27
|
} );
|
|
28
28
|
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
/* eslint-disable jest/no-conditional-expect */
|
|
3
|
+
/**
|
|
4
|
+
* Internal dependencies
|
|
5
|
+
*/
|
|
6
|
+
const {
|
|
7
|
+
LifecycleScriptError,
|
|
8
|
+
executeLifecycleScript,
|
|
9
|
+
} = require( '../execute-lifecycle-script' );
|
|
10
|
+
|
|
11
|
+
describe( 'executeLifecycleScript', () => {
|
|
12
|
+
const spinner = {
|
|
13
|
+
info: jest.fn(),
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
afterEach( () => {
|
|
17
|
+
jest.clearAllMocks();
|
|
18
|
+
} );
|
|
19
|
+
|
|
20
|
+
it( 'should do nothing without event option when debugging', async () => {
|
|
21
|
+
await executeLifecycleScript(
|
|
22
|
+
'test',
|
|
23
|
+
{ lifecycleScripts: { test: null }, debug: true },
|
|
24
|
+
spinner
|
|
25
|
+
);
|
|
26
|
+
|
|
27
|
+
expect( spinner.info ).not.toHaveBeenCalled();
|
|
28
|
+
} );
|
|
29
|
+
|
|
30
|
+
it( 'should run event option and print output when debugging', async () => {
|
|
31
|
+
await executeLifecycleScript(
|
|
32
|
+
'test',
|
|
33
|
+
{ lifecycleScripts: { test: 'node -v' }, debug: true },
|
|
34
|
+
spinner
|
|
35
|
+
);
|
|
36
|
+
|
|
37
|
+
expect( spinner.info ).toHaveBeenCalledWith(
|
|
38
|
+
expect.stringMatching( /test Script:\nv[0-9]/ )
|
|
39
|
+
);
|
|
40
|
+
} );
|
|
41
|
+
|
|
42
|
+
it( 'should throw LifecycleScriptError when process errors', async () => {
|
|
43
|
+
try {
|
|
44
|
+
await executeLifecycleScript(
|
|
45
|
+
'test',
|
|
46
|
+
{
|
|
47
|
+
lifecycleScripts: {
|
|
48
|
+
test: 'node -vvvvvvv',
|
|
49
|
+
},
|
|
50
|
+
},
|
|
51
|
+
spinner
|
|
52
|
+
);
|
|
53
|
+
} catch ( error ) {
|
|
54
|
+
expect( error ).toBeInstanceOf( LifecycleScriptError );
|
|
55
|
+
expect( error.message ).toMatch( /test Error:\n.*bad option/ );
|
|
56
|
+
}
|
|
57
|
+
} );
|
|
58
|
+
} );
|
|
59
|
+
/* eslint-enable jest/no-conditional-expect */
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* A list of the containers that we can use `run` on.
|
|
5
|
+
*/
|
|
6
|
+
const RUN_CONTAINERS = [
|
|
7
|
+
'mysql',
|
|
8
|
+
'tests-mysql',
|
|
9
|
+
'wordpress',
|
|
10
|
+
'tests-wordpress',
|
|
11
|
+
'cli',
|
|
12
|
+
'tests-cli',
|
|
13
|
+
];
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* Custom parsing and validation for the "run" command's container argument.
|
|
17
|
+
*
|
|
18
|
+
* @param {string} value The user-set container.
|
|
19
|
+
*
|
|
20
|
+
* @return {string} The container name to use.
|
|
21
|
+
*/
|
|
22
|
+
function validateRunContainer( value ) {
|
|
23
|
+
// Give special errors for deprecated containers.
|
|
24
|
+
if ( value === 'phpunit' ) {
|
|
25
|
+
throw new Error(
|
|
26
|
+
"The 'phpunit' container has been removed. Please use 'wp-env run tests-cli --env-cwd=wp-content/path/to/plugin phpunit' instead."
|
|
27
|
+
);
|
|
28
|
+
}
|
|
29
|
+
if ( value === 'composer' ) {
|
|
30
|
+
throw new Error(
|
|
31
|
+
"The 'composer' container has been removed. Please use 'wp-env run cli --env-cwd=wp-content/path/to/plugin composer' instead."
|
|
32
|
+
);
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
return value;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
module.exports = {
|
|
39
|
+
RUN_CONTAINERS,
|
|
40
|
+
validateRunContainer,
|
|
41
|
+
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@wordpress/env",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "8.1.0",
|
|
4
4
|
"description": "A zero-config, self contained local WordPress environment for development and testing.",
|
|
5
5
|
"author": "The WordPress Contributors",
|
|
6
6
|
"license": "GPL-2.0-or-later",
|
|
@@ -51,5 +51,5 @@
|
|
|
51
51
|
"scripts": {
|
|
52
52
|
"test": "echo \"Error: run tests from root\" && exit 1"
|
|
53
53
|
},
|
|
54
|
-
"gitHead": "
|
|
54
|
+
"gitHead": "a92f606309b1541b834ff9b0a76ed2a466fc45ed"
|
|
55
55
|
}
|
|
@@ -1,51 +0,0 @@
|
|
|
1
|
-
'use strict';
|
|
2
|
-
/**
|
|
3
|
-
* External dependencies
|
|
4
|
-
*/
|
|
5
|
-
const { execSync } = require( 'child_process' );
|
|
6
|
-
|
|
7
|
-
/**
|
|
8
|
-
* @typedef {import('./config').WPConfig} WPConfig
|
|
9
|
-
*/
|
|
10
|
-
|
|
11
|
-
/**
|
|
12
|
-
* Error subtype which indicates that the afterSetup command failed.
|
|
13
|
-
*/
|
|
14
|
-
class AfterSetupError extends Error {}
|
|
15
|
-
|
|
16
|
-
/**
|
|
17
|
-
* Executes any defined afterSetup command.
|
|
18
|
-
*
|
|
19
|
-
* @param {WPConfig} config The config object to use.
|
|
20
|
-
* @param {Object} spinner A CLI spinner which indciates progress.
|
|
21
|
-
*/
|
|
22
|
-
function executeAfterSetup( config, spinner ) {
|
|
23
|
-
if ( ! config.afterSetup ) {
|
|
24
|
-
return;
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
spinner.text = 'Executing Script: afterSetup';
|
|
28
|
-
|
|
29
|
-
try {
|
|
30
|
-
let output = execSync( config.afterSetup, {
|
|
31
|
-
encoding: 'utf-8',
|
|
32
|
-
stdio: 'pipe',
|
|
33
|
-
env: process.env,
|
|
34
|
-
} );
|
|
35
|
-
|
|
36
|
-
// Remove any trailing whitespace for nicer output.
|
|
37
|
-
output = output.trimRight();
|
|
38
|
-
|
|
39
|
-
// We don't need to bother with any output if there isn't any.
|
|
40
|
-
if ( output ) {
|
|
41
|
-
spinner.info( `After Setup:\n${ output }` );
|
|
42
|
-
}
|
|
43
|
-
} catch ( error ) {
|
|
44
|
-
throw new AfterSetupError( `After Setup:\n${ error.stderr }` );
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
module.exports = {
|
|
49
|
-
AfterSetupError,
|
|
50
|
-
executeAfterSetup,
|
|
51
|
-
};
|
|
@@ -1,66 +0,0 @@
|
|
|
1
|
-
'use strict';
|
|
2
|
-
/**
|
|
3
|
-
* External dependencies
|
|
4
|
-
*/
|
|
5
|
-
const { execSync } = require( 'child_process' );
|
|
6
|
-
|
|
7
|
-
/**
|
|
8
|
-
* Internal dependencies
|
|
9
|
-
*/
|
|
10
|
-
const {
|
|
11
|
-
AfterSetupError,
|
|
12
|
-
executeAfterSetup,
|
|
13
|
-
} = require( '../execute-after-setup' );
|
|
14
|
-
|
|
15
|
-
jest.mock( 'child_process', () => ( {
|
|
16
|
-
execSync: jest.fn(),
|
|
17
|
-
} ) );
|
|
18
|
-
|
|
19
|
-
describe( 'executeAfterSetup', () => {
|
|
20
|
-
const spinner = {
|
|
21
|
-
info: jest.fn(),
|
|
22
|
-
};
|
|
23
|
-
|
|
24
|
-
afterEach( () => {
|
|
25
|
-
jest.clearAllMocks();
|
|
26
|
-
} );
|
|
27
|
-
|
|
28
|
-
it( 'should do nothing without afterSetup option', () => {
|
|
29
|
-
executeAfterSetup( { afterSetup: null }, spinner );
|
|
30
|
-
|
|
31
|
-
expect( spinner.info ).not.toHaveBeenCalled();
|
|
32
|
-
} );
|
|
33
|
-
|
|
34
|
-
it( 'should run afterSetup option and print output without extra whitespace', () => {
|
|
35
|
-
execSync.mockReturnValue( 'Test \n' );
|
|
36
|
-
|
|
37
|
-
executeAfterSetup( { afterSetup: 'Test Setup' }, spinner );
|
|
38
|
-
|
|
39
|
-
expect( execSync ).toHaveBeenCalled();
|
|
40
|
-
expect( execSync.mock.calls[ 0 ][ 0 ] ).toEqual( 'Test Setup' );
|
|
41
|
-
expect( spinner.info ).toHaveBeenCalledWith( 'After Setup:\nTest' );
|
|
42
|
-
} );
|
|
43
|
-
|
|
44
|
-
it( 'should print nothing if afterSetup returns no output', () => {
|
|
45
|
-
execSync.mockReturnValue( '' );
|
|
46
|
-
|
|
47
|
-
executeAfterSetup( { afterSetup: 'Test Setup' }, spinner );
|
|
48
|
-
|
|
49
|
-
expect( execSync ).toHaveBeenCalled();
|
|
50
|
-
expect( execSync.mock.calls[ 0 ][ 0 ] ).toEqual( 'Test Setup' );
|
|
51
|
-
expect( spinner.info ).not.toHaveBeenCalled();
|
|
52
|
-
} );
|
|
53
|
-
|
|
54
|
-
it( 'should throw AfterSetupError when process errors', () => {
|
|
55
|
-
execSync.mockImplementation( ( command ) => {
|
|
56
|
-
expect( command ).toEqual( 'Test Setup' );
|
|
57
|
-
throw { stderr: 'Something bad happened.' };
|
|
58
|
-
} );
|
|
59
|
-
|
|
60
|
-
expect( () =>
|
|
61
|
-
executeAfterSetup( { afterSetup: 'Test Setup' }, spinner )
|
|
62
|
-
).toThrow(
|
|
63
|
-
new AfterSetupError( 'After Setup:\nSomething bad happened.' )
|
|
64
|
-
);
|
|
65
|
-
} );
|
|
66
|
-
} );
|