libdragon 10.8.2 → 10.9.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 +24 -1
- package/modules/actions/destroy.js +7 -1
- package/modules/actions/exec.js +18 -0
- package/modules/actions/init.js +27 -23
- package/modules/actions/install.js +18 -15
- package/modules/actions/start.js +22 -1
- package/modules/actions/stop.js +7 -1
- package/modules/actions/update-and-start.js +8 -1
- package/modules/actions/utils.js +36 -2
- package/modules/helpers.js +36 -9
- package/modules/project-info.js +11 -2
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -184,7 +184,7 @@ For a quick development loop it really helps linking the code in this repository
|
|
|
184
184
|
|
|
185
185
|
npm link
|
|
186
186
|
|
|
187
|
-
in the root of the repository. Once you do this, running `libdragon` will use the code here rather than the actual npm installation. Then you can test your changes in the libdragon project here or elsewhere on your computer.
|
|
187
|
+
in the root of the repository. Once you do this, running `libdragon` will use the code here rather than the actual npm installation. Then you can test your changes in the libdragon project here or elsewhere on your computer. This setup is automatically done if you use the [devcontainer](#experimental-devcontainer-support).
|
|
188
188
|
|
|
189
189
|
When you are happy with your changes, you can verify you conform to the coding standards via:
|
|
190
190
|
|
|
@@ -201,6 +201,29 @@ This repository uses [`semantic-release`](https://github.com/semantic-release/se
|
|
|
201
201
|
|
|
202
202
|
It will create a `semantic-release` compatible commit from your current staged changes.
|
|
203
203
|
|
|
204
|
+
### Experimental devcontainer support
|
|
205
|
+
|
|
206
|
+
The repository provides a configuration (in `.devcontainer`) so that IDEs that support it can create and run the Docker container for you. Then, you can start working on it as if you are working on a machine with libdragon installed.
|
|
207
|
+
|
|
208
|
+
With the provided setup, you can continue using the cli in the container and it will work for non-container specific actions like `install`, `disasm` etc. You don't have to use the cli in the container, but you can. In general it will be easier and faster to just run `make` in the container but this setup is included to ease developing the cli as well.
|
|
209
|
+
|
|
210
|
+
To create your own dev container backed project, you can use the contents of the `.devcontainer` folder as reference. You don't need to include nodejs or the cli and you can just run `build.sh` as `postCreateCommand`. See the `devcontainer.json` for more details. As long as your container have the `DOCKER_CONTAINER` environment variable, the tool can work inside a container.
|
|
211
|
+
|
|
212
|
+
#### Caveats
|
|
213
|
+
|
|
214
|
+
- In the devcontainer, uploading via USB will not work.
|
|
215
|
+
- Error matching is not yet tested.
|
|
216
|
+
- Ideally the necessary extensions should be automatically installed. This is not configured yet.
|
|
217
|
+
|
|
218
|
+
<details>
|
|
219
|
+
<summary>vscode instructions</summary>
|
|
220
|
+
|
|
221
|
+
- Make sure you have the [Dev container extension](https://marketplace.visualstudio.com/items?itemName=ms-vscode-remote.remote-containers) installed and you fulfill its [requirements](https://code.visualstudio.com/docs/devcontainers/containers).
|
|
222
|
+
- Clone this repository with `--recurse-submodules` or run `git submodule update --init`.
|
|
223
|
+
- Open command palette and run `Dev Containers: Reopen in container`.
|
|
224
|
+
- It will prepare the container and open it in the editor.
|
|
225
|
+
</details>
|
|
226
|
+
|
|
204
227
|
## As an NPM dependency
|
|
205
228
|
|
|
206
229
|
You can install libdragon as an NPM dependency by `npm install libdragon --save` in order to use docker in your N64 projects. A `libdragon` command similar to global intallation is provided that can be used in your NPM scripts as follows;
|
|
@@ -3,13 +3,19 @@ const path = require('path');
|
|
|
3
3
|
|
|
4
4
|
const { destroyContainer } = require('./utils');
|
|
5
5
|
const { CONFIG_FILE, LIBDRAGON_PROJECT_MANIFEST } = require('../constants');
|
|
6
|
-
const { fileExists, dirExists, log } = require('../helpers');
|
|
6
|
+
const { fileExists, dirExists, log, ValidationError } = require('../helpers');
|
|
7
7
|
const chalk = require('chalk');
|
|
8
8
|
|
|
9
9
|
/**
|
|
10
10
|
* @param {import('../project-info').LibdragonInfo} libdragonInfo
|
|
11
11
|
*/
|
|
12
12
|
const destroy = async (libdragonInfo) => {
|
|
13
|
+
if (process.env.DOCKER_CONTAINER) {
|
|
14
|
+
throw new ValidationError(
|
|
15
|
+
`Not possible to destroy the container from inside.`
|
|
16
|
+
);
|
|
17
|
+
}
|
|
18
|
+
|
|
13
19
|
await destroyContainer(libdragonInfo);
|
|
14
20
|
|
|
15
21
|
const projectPath = path.join(libdragonInfo.root, LIBDRAGON_PROJECT_MANIFEST);
|
package/modules/actions/exec.js
CHANGED
|
@@ -9,6 +9,7 @@ const {
|
|
|
9
9
|
fileExists,
|
|
10
10
|
dirExists,
|
|
11
11
|
CommandError,
|
|
12
|
+
spawnProcess,
|
|
12
13
|
} = require('../helpers');
|
|
13
14
|
|
|
14
15
|
const { start } = require('./start');
|
|
@@ -45,6 +46,23 @@ const exec = async (info) => {
|
|
|
45
46
|
true
|
|
46
47
|
);
|
|
47
48
|
|
|
49
|
+
// Don't even bother here, we are already in a container.
|
|
50
|
+
if (process.env.DOCKER_CONTAINER) {
|
|
51
|
+
const enableTTY = Boolean(process.stdout.isTTY && process.stdin.isTTY);
|
|
52
|
+
await spawnProcess(info.options.EXTRA_PARAMS[0], parameters, {
|
|
53
|
+
userCommand: true,
|
|
54
|
+
// Inherit stdin/out in tandem if we are going to disable TTY o/w the input
|
|
55
|
+
// stream remains inherited by the node process while the output pipe is
|
|
56
|
+
// waiting data from stdout and it behaves like we are still controlling
|
|
57
|
+
// the spawned process while the terminal is actually displaying say for
|
|
58
|
+
// example `less`.
|
|
59
|
+
inheritStdout: enableTTY,
|
|
60
|
+
inheritStdin: enableTTY,
|
|
61
|
+
inheritStderr: true,
|
|
62
|
+
});
|
|
63
|
+
return info;
|
|
64
|
+
}
|
|
65
|
+
|
|
48
66
|
const stdin = new PassThrough();
|
|
49
67
|
|
|
50
68
|
/** @type {string[]} */
|
package/modules/actions/init.js
CHANGED
|
@@ -108,7 +108,11 @@ const autoVendor = async (info) => {
|
|
|
108
108
|
return info;
|
|
109
109
|
}
|
|
110
110
|
|
|
111
|
-
|
|
111
|
+
// Container re-init breaks file modes assume there is git for this case.
|
|
112
|
+
// TODO: we should remove the unnecessary inits in the future.
|
|
113
|
+
if (!process.env.DOCKER_CONTAINER) {
|
|
114
|
+
await runGitMaybeHost(info, ['init']);
|
|
115
|
+
}
|
|
112
116
|
|
|
113
117
|
// TODO: TS thinks this is already defined
|
|
114
118
|
const detectedStrategy = await autoDetect(info);
|
|
@@ -220,33 +224,33 @@ async function init(info) {
|
|
|
220
224
|
LIBDRAGON_PROJECT_MANIFEST
|
|
221
225
|
)} exists. This is already a libdragon project, starting it...`
|
|
222
226
|
);
|
|
223
|
-
if (
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
...info,
|
|
233
|
-
containerId: await start(info),
|
|
234
|
-
};
|
|
227
|
+
if (!process.env.DOCKER_CONTAINER) {
|
|
228
|
+
if (info.options.DOCKER_IMAGE) {
|
|
229
|
+
info = await syncImageAndStart(info);
|
|
230
|
+
} else {
|
|
231
|
+
info = {
|
|
232
|
+
...info,
|
|
233
|
+
containerId: await start(info),
|
|
234
|
+
};
|
|
235
|
+
}
|
|
235
236
|
}
|
|
237
|
+
|
|
236
238
|
info = await autoVendor(info);
|
|
237
239
|
await installDependencies(info);
|
|
238
240
|
return info;
|
|
239
241
|
}
|
|
240
242
|
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
243
|
+
if (!process.env.DOCKER_CONTAINER) {
|
|
244
|
+
// Download image and start it
|
|
245
|
+
await updateImage(info, info.imageName);
|
|
246
|
+
info.containerId = await start(info);
|
|
247
|
+
// We have created a new container, save the new info ASAP
|
|
248
|
+
// When in a container, we should already have git
|
|
249
|
+
// Re-initing breaks file modes anyways
|
|
250
|
+
await initGitAndCacheContainerId(
|
|
251
|
+
/** @type Parameters<initGitAndCacheContainerId>[0] */ (info)
|
|
252
|
+
);
|
|
253
|
+
}
|
|
250
254
|
|
|
251
255
|
info = await autoVendor(info);
|
|
252
256
|
|
|
@@ -274,7 +278,7 @@ module.exports = /** @type {const} */ ({
|
|
|
274
278
|
|
|
275
279
|
By default, a git repository and a submodule at \`./libdragon\` will be created to automatically update the vendored libdragon files on subsequent \`update\`s. If you intend to opt-out from this feature, see the \`--strategy manual\` flag to provide your self-managed libdragon copy. The default behaviour is intended for users who primarily want to consume libdragon as is.
|
|
276
280
|
|
|
277
|
-
If this is the first time you are creating a libdragon project at that location, this action will also create skeleton project files to kickstart things with the given image, if provided. For subsequent runs, it will act like \`start\` thus can be used to revive an existing project without modifying it.
|
|
281
|
+
If this is the first time you are creating a libdragon project at that location, this action will also create skeleton project files to kickstart things with the given image, if provided. For subsequent runs without any parameter, it will act like \`start\` thus can be used to revive an existing project without modifying it.
|
|
278
282
|
|
|
279
283
|
If you have an existing project with an already vendored submodule or subtree libdragon copy, \`init\` will automatically detect it at the provided \`--directory\`.`,
|
|
280
284
|
group: ['docker', 'vendoring'],
|
|
@@ -13,21 +13,24 @@ const { log } = require('../helpers');
|
|
|
13
13
|
*/
|
|
14
14
|
const install = async (libdragonInfo) => {
|
|
15
15
|
let updatedInfo = libdragonInfo;
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
16
|
+
|
|
17
|
+
if (!process.env.DOCKER_CONTAINER) {
|
|
18
|
+
const imageName = libdragonInfo.options.DOCKER_IMAGE;
|
|
19
|
+
// If an image is provided, attempt to install
|
|
20
|
+
if (imageName) {
|
|
21
|
+
log(
|
|
22
|
+
chalk.yellow(
|
|
23
|
+
'Using `install` action to update the docker image is deprecated. Use the `update` action instead.'
|
|
24
|
+
)
|
|
25
|
+
);
|
|
26
|
+
updatedInfo = await syncImageAndStart(libdragonInfo);
|
|
27
|
+
} else {
|
|
28
|
+
// Make sure existing one is running
|
|
29
|
+
updatedInfo = {
|
|
30
|
+
...updatedInfo,
|
|
31
|
+
containerId: await start(libdragonInfo),
|
|
32
|
+
};
|
|
33
|
+
}
|
|
31
34
|
}
|
|
32
35
|
|
|
33
36
|
// Re-install vendors on new image
|
package/modules/actions/start.js
CHANGED
|
@@ -1,7 +1,14 @@
|
|
|
1
1
|
const chalk = require('chalk').stderr;
|
|
2
2
|
|
|
3
3
|
const { CONTAINER_TARGET_PATH } = require('../constants');
|
|
4
|
-
const {
|
|
4
|
+
const {
|
|
5
|
+
spawnProcess,
|
|
6
|
+
log,
|
|
7
|
+
print,
|
|
8
|
+
dockerExec,
|
|
9
|
+
assert,
|
|
10
|
+
ValidationError,
|
|
11
|
+
} = require('../helpers');
|
|
5
12
|
|
|
6
13
|
const {
|
|
7
14
|
checkContainerAndClean,
|
|
@@ -14,6 +21,11 @@ const {
|
|
|
14
21
|
* @param {import('../project-info').LibdragonInfo} libdragonInfo
|
|
15
22
|
*/
|
|
16
23
|
const initContainer = async (libdragonInfo) => {
|
|
24
|
+
assert(
|
|
25
|
+
!process.env.DOCKER_CONTAINER,
|
|
26
|
+
new Error('initContainer does not make sense in a container')
|
|
27
|
+
);
|
|
28
|
+
|
|
17
29
|
let newId;
|
|
18
30
|
try {
|
|
19
31
|
log('Creating new container...');
|
|
@@ -79,6 +91,11 @@ const initContainer = async (libdragonInfo) => {
|
|
|
79
91
|
* @param {import('../project-info').LibdragonInfo} libdragonInfo
|
|
80
92
|
*/
|
|
81
93
|
const start = async (libdragonInfo) => {
|
|
94
|
+
assert(
|
|
95
|
+
!process.env.DOCKER_CONTAINER,
|
|
96
|
+
new Error('Cannot start a container when we are already in a container.')
|
|
97
|
+
);
|
|
98
|
+
|
|
82
99
|
const running =
|
|
83
100
|
libdragonInfo.containerId &&
|
|
84
101
|
(await checkContainerRunning(libdragonInfo.containerId));
|
|
@@ -108,6 +125,10 @@ module.exports = /** @type {const} */ ({
|
|
|
108
125
|
* @param {import('../project-info').LibdragonInfo} libdragonInfo
|
|
109
126
|
*/
|
|
110
127
|
fn: async (libdragonInfo) => {
|
|
128
|
+
if (process.env.DOCKER_CONTAINER) {
|
|
129
|
+
throw new ValidationError(`We are already in a container.`);
|
|
130
|
+
}
|
|
131
|
+
|
|
111
132
|
const containerId = await start(libdragonInfo);
|
|
112
133
|
print(containerId);
|
|
113
134
|
return { ...libdragonInfo, containerId };
|
package/modules/actions/stop.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
const { spawnProcess } = require('../helpers');
|
|
1
|
+
const { spawnProcess, ValidationError } = require('../helpers');
|
|
2
2
|
|
|
3
3
|
const { checkContainerRunning } = require('./utils');
|
|
4
4
|
|
|
@@ -7,6 +7,12 @@ const { checkContainerRunning } = require('./utils');
|
|
|
7
7
|
* @returns {Promise<import('../project-info').LibdragonInfo | void>}
|
|
8
8
|
*/
|
|
9
9
|
const stop = async (libdragonInfo) => {
|
|
10
|
+
if (process.env.DOCKER_CONTAINER) {
|
|
11
|
+
throw new ValidationError(
|
|
12
|
+
`Not possible to stop the container from inside.`
|
|
13
|
+
);
|
|
14
|
+
}
|
|
15
|
+
|
|
10
16
|
const running =
|
|
11
17
|
libdragonInfo.containerId &&
|
|
12
18
|
(await checkContainerRunning(libdragonInfo.containerId));
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
const { log } = require('../helpers');
|
|
1
|
+
const { log, assert } = require('../helpers');
|
|
2
2
|
const { updateImage, destroyContainer } = require('./utils');
|
|
3
3
|
const { start } = require('./start');
|
|
4
4
|
|
|
@@ -6,6 +6,13 @@ const { start } = require('./start');
|
|
|
6
6
|
* @param {import('../project-info').LibdragonInfo} libdragonInfo
|
|
7
7
|
*/
|
|
8
8
|
async function syncImageAndStart(libdragonInfo) {
|
|
9
|
+
assert(
|
|
10
|
+
!process.env.DOCKER_CONTAINER,
|
|
11
|
+
new Error(
|
|
12
|
+
'[syncImageAndStart] We should already know we are in a container.'
|
|
13
|
+
)
|
|
14
|
+
);
|
|
15
|
+
|
|
9
16
|
const oldImageName = libdragonInfo.imageName;
|
|
10
17
|
const imageName = libdragonInfo.options.DOCKER_IMAGE ?? oldImageName;
|
|
11
18
|
// If an image is provided, always attempt to install it
|
package/modules/actions/utils.js
CHANGED
|
@@ -53,11 +53,16 @@ const installDependencies = async (libdragonInfo) => {
|
|
|
53
53
|
|
|
54
54
|
/**
|
|
55
55
|
* Downloads the given docker image. Returns false if the local image is the
|
|
56
|
-
* same,
|
|
56
|
+
* same, true otherwise.
|
|
57
57
|
* @param {import('../project-info').LibdragonInfo} libdragonInfo
|
|
58
58
|
* @param {string} newImageName
|
|
59
59
|
*/
|
|
60
60
|
const updateImage = async (libdragonInfo, newImageName) => {
|
|
61
|
+
assert(
|
|
62
|
+
!process.env.DOCKER_CONTAINER,
|
|
63
|
+
new Error('[updateImage] should not be called in a container')
|
|
64
|
+
);
|
|
65
|
+
|
|
61
66
|
// Will not take too much time if already have the same
|
|
62
67
|
const download = async () => {
|
|
63
68
|
log(`Downloading docker image: ${newImageName}`);
|
|
@@ -89,13 +94,18 @@ const updateImage = async (libdragonInfo, newImageName) => {
|
|
|
89
94
|
}
|
|
90
95
|
|
|
91
96
|
log(`Image is different: ${newImageName}`, true);
|
|
92
|
-
return
|
|
97
|
+
return true;
|
|
93
98
|
};
|
|
94
99
|
|
|
95
100
|
/**
|
|
96
101
|
* @param {import('../project-info').LibdragonInfo} libdragonInfo
|
|
97
102
|
*/
|
|
98
103
|
const destroyContainer = async (libdragonInfo) => {
|
|
104
|
+
assert(
|
|
105
|
+
!process.env.DOCKER_CONTAINER,
|
|
106
|
+
new Error('[destroyContainer] should not be called in a container')
|
|
107
|
+
);
|
|
108
|
+
|
|
99
109
|
if (libdragonInfo.containerId) {
|
|
100
110
|
await spawnProcess('docker', [
|
|
101
111
|
'container',
|
|
@@ -144,6 +154,11 @@ async function runGitMaybeHost(libdragonInfo, params, options = {}) {
|
|
|
144
154
|
throw e;
|
|
145
155
|
}
|
|
146
156
|
|
|
157
|
+
assert(
|
|
158
|
+
!process.env.DOCKER_CONTAINER,
|
|
159
|
+
new Error('[runGitMaybeHost] Native git should exist in a container.')
|
|
160
|
+
);
|
|
161
|
+
|
|
147
162
|
return await dockerExec(
|
|
148
163
|
libdragonInfo,
|
|
149
164
|
// Use the host user when initializing git as we will need access
|
|
@@ -159,6 +174,13 @@ async function runGitMaybeHost(libdragonInfo, params, options = {}) {
|
|
|
159
174
|
* @param {import('../project-info').LibdragonInfo} libdragonInfo
|
|
160
175
|
*/
|
|
161
176
|
async function checkContainerAndClean(libdragonInfo) {
|
|
177
|
+
assert(
|
|
178
|
+
!process.env.DOCKER_CONTAINER,
|
|
179
|
+
new Error(
|
|
180
|
+
'[checkContainerAndClean] We should already know we are in a container.'
|
|
181
|
+
)
|
|
182
|
+
);
|
|
183
|
+
|
|
162
184
|
const id =
|
|
163
185
|
libdragonInfo.containerId &&
|
|
164
186
|
(
|
|
@@ -188,6 +210,13 @@ async function checkContainerAndClean(libdragonInfo) {
|
|
|
188
210
|
* @param {string} containerId
|
|
189
211
|
*/
|
|
190
212
|
async function checkContainerRunning(containerId) {
|
|
213
|
+
assert(
|
|
214
|
+
!process.env.DOCKER_CONTAINER,
|
|
215
|
+
new Error(
|
|
216
|
+
'[checkContainerRunning] We should already know we are in a container.'
|
|
217
|
+
)
|
|
218
|
+
);
|
|
219
|
+
|
|
191
220
|
const running = (
|
|
192
221
|
await spawnProcess('docker', [
|
|
193
222
|
'container',
|
|
@@ -203,11 +232,16 @@ async function checkContainerRunning(containerId) {
|
|
|
203
232
|
* @param {import('../project-info').LibdragonInfo & {containerId: string}} libdragonInfo
|
|
204
233
|
*/
|
|
205
234
|
async function initGitAndCacheContainerId(libdragonInfo) {
|
|
235
|
+
if (!libdragonInfo.containerId) {
|
|
236
|
+
return;
|
|
237
|
+
}
|
|
238
|
+
|
|
206
239
|
// If there is managed vendoring, make sure we have a git repo. `git init` is
|
|
207
240
|
// safe anyways...
|
|
208
241
|
if (libdragonInfo.vendorStrategy !== 'manual') {
|
|
209
242
|
await runGitMaybeHost(libdragonInfo, ['init']);
|
|
210
243
|
}
|
|
244
|
+
|
|
211
245
|
const gitFolder = path.join(libdragonInfo.root, '.git');
|
|
212
246
|
if (await dirExists(gitFolder)) {
|
|
213
247
|
await fs.writeFile(
|
package/modules/helpers.js
CHANGED
|
@@ -157,6 +157,10 @@ function spawnProcess(
|
|
|
157
157
|
spawnOptions: {},
|
|
158
158
|
}
|
|
159
159
|
) {
|
|
160
|
+
assert(
|
|
161
|
+
cmd !== 'docker' || !process.env.DOCKER_CONTAINER,
|
|
162
|
+
new Error('Trying to invoke docker inside a container.')
|
|
163
|
+
);
|
|
160
164
|
return new Promise((resolve, reject) => {
|
|
161
165
|
/** @type {Buffer[]} */
|
|
162
166
|
const stdout = [];
|
|
@@ -273,11 +277,6 @@ const dockerExec = /** @type {DockerExec} */ (
|
|
|
273
277
|
/** @type {SpawnOptions | undefined} */
|
|
274
278
|
options
|
|
275
279
|
) {
|
|
276
|
-
assert(
|
|
277
|
-
!!libdragonInfo.containerId,
|
|
278
|
-
new Error('Trying to invoke dockerExec without a containerId.')
|
|
279
|
-
);
|
|
280
|
-
|
|
281
280
|
// TODO: assert for invalid args
|
|
282
281
|
const haveDockerParams =
|
|
283
282
|
Array.isArray(dockerParams) && Array.isArray(cmdWithParams);
|
|
@@ -286,6 +285,35 @@ const dockerExec = /** @type {DockerExec} */ (
|
|
|
286
285
|
options = /** @type {SpawnOptions} */ (cmdWithParams);
|
|
287
286
|
}
|
|
288
287
|
|
|
288
|
+
const finalCmdWithParams = haveDockerParams ? cmdWithParams : dockerParams;
|
|
289
|
+
const finalDockerParams = haveDockerParams ? dockerParams : [];
|
|
290
|
+
|
|
291
|
+
assert(
|
|
292
|
+
finalDockerParams.findIndex(
|
|
293
|
+
(val) => val === '--workdir=' || val === '-w='
|
|
294
|
+
) === -1,
|
|
295
|
+
new Error('Do not use `=` syntax when setting working dir')
|
|
296
|
+
);
|
|
297
|
+
|
|
298
|
+
// Convert docker execs into regular commands in the correct cwd
|
|
299
|
+
if (process.env.DOCKER_CONTAINER) {
|
|
300
|
+
const workDirIndex = finalDockerParams.findIndex(
|
|
301
|
+
(val) => val === '--workdir' || val === '-w'
|
|
302
|
+
);
|
|
303
|
+
const workDir =
|
|
304
|
+
workDirIndex >= 0 ? finalDockerParams[workDirIndex + 1] : undefined;
|
|
305
|
+
return spawnProcess(finalCmdWithParams[0], finalCmdWithParams.slice(1), {
|
|
306
|
+
...options,
|
|
307
|
+
spawnOptions: { cwd: workDir, ...options?.spawnOptions },
|
|
308
|
+
});
|
|
309
|
+
}
|
|
310
|
+
|
|
311
|
+
assert(
|
|
312
|
+
!!libdragonInfo.containerId,
|
|
313
|
+
new Error('Trying to invoke dockerExec without a containerId.')
|
|
314
|
+
);
|
|
315
|
+
|
|
316
|
+
/** @type string[] */
|
|
289
317
|
const additionalParams = [];
|
|
290
318
|
|
|
291
319
|
// Docker TTY wants in & out streams both to be a TTY
|
|
@@ -309,11 +337,10 @@ const dockerExec = /** @type {DockerExec} */ (
|
|
|
309
337
|
'docker',
|
|
310
338
|
[
|
|
311
339
|
'exec',
|
|
312
|
-
...
|
|
313
|
-
|
|
314
|
-
: additionalParams),
|
|
340
|
+
...finalDockerParams,
|
|
341
|
+
...additionalParams,
|
|
315
342
|
libdragonInfo.containerId,
|
|
316
|
-
...
|
|
343
|
+
...finalCmdWithParams,
|
|
317
344
|
],
|
|
318
345
|
options
|
|
319
346
|
);
|
package/modules/project-info.js
CHANGED
|
@@ -64,6 +64,11 @@ const {
|
|
|
64
64
|
* @param {LibdragonInfo} libdragonInfo
|
|
65
65
|
*/
|
|
66
66
|
async function findContainerId(libdragonInfo) {
|
|
67
|
+
assert(
|
|
68
|
+
!process.env.DOCKER_CONTAINER,
|
|
69
|
+
new Error('[findContainerId] We should already know we are in a container.')
|
|
70
|
+
);
|
|
71
|
+
|
|
67
72
|
const idFile = path.join(libdragonInfo.root, '.git', CACHED_CONTAINER_FILE);
|
|
68
73
|
if (await fileExists(idFile)) {
|
|
69
74
|
const id = (await fs.readFile(idFile, { encoding: 'utf8' })).trim();
|
|
@@ -225,15 +230,19 @@ const readProjectInfo = async function (optionInfo) {
|
|
|
225
230
|
}
|
|
226
231
|
}
|
|
227
232
|
|
|
228
|
-
|
|
229
|
-
|
|
233
|
+
if (!process.env.DOCKER_CONTAINER) {
|
|
234
|
+
info.containerId = await findContainerId(info);
|
|
235
|
+
log(`Active container id: ${info.containerId}`, true);
|
|
236
|
+
}
|
|
230
237
|
|
|
231
238
|
// For imageName, flag has the highest priority followed by the one read from
|
|
232
239
|
// the file and then if there is any matching container, name is read from it.
|
|
233
240
|
// As last option fallback to default value.
|
|
234
241
|
|
|
235
242
|
// If still have the container, read the image name from it
|
|
243
|
+
// No need to do anything if we are in a container
|
|
236
244
|
if (
|
|
245
|
+
!process.env.DOCKER_CONTAINER &&
|
|
237
246
|
!info.imageName &&
|
|
238
247
|
info.containerId &&
|
|
239
248
|
(await checkContainerAndClean(info))
|