@scandipwa/magento-scripts 1.16.1 → 2.0.0-alpha.10

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.
Files changed (234) hide show
  1. package/exec.js +71 -0
  2. package/index.js +1 -1
  3. package/lib/commands/cli.js +4 -6
  4. package/lib/commands/execute.js +3 -33
  5. package/lib/commands/import-db.js +1 -1
  6. package/lib/commands/logs.js +1 -1
  7. package/lib/commands/start.js +38 -20
  8. package/lib/commands/status.js +2 -0
  9. package/lib/config/docker.js +103 -85
  10. package/lib/config/get-project-configuration.js +3 -1
  11. package/lib/config/index.js +10 -7
  12. package/lib/config/magento/required-php-extensions/index.js +29 -0
  13. package/lib/config/magento/required-php-extensions/magento-2.3.js +19 -0
  14. package/lib/config/magento/required-php-extensions/magento-2.4.js +29 -0
  15. package/lib/config/php/base-repo.js +3 -0
  16. package/lib/config/php/extensions/apcu.js +12 -0
  17. package/lib/config/php/extensions/bcmath.js +7 -0
  18. package/lib/config/php/extensions/curl.js +11 -0
  19. package/lib/config/php/extensions/gd.js +14 -0
  20. package/lib/config/php/extensions/index.js +18 -2
  21. package/lib/config/php/extensions/intl.js +10 -0
  22. package/lib/config/php/extensions/opcache.js +10 -0
  23. package/lib/config/php/extensions/pdo_mysql.js +7 -0
  24. package/lib/config/php/extensions/soap.js +10 -0
  25. package/lib/config/php/extensions/sodium.js +10 -0
  26. package/lib/config/php/extensions/xdebug.js +8 -5
  27. package/lib/config/php/extensions/xsl.js +10 -0
  28. package/lib/config/php/extensions/zip.js +10 -0
  29. package/lib/config/php/{releases → versions}/index.js +0 -0
  30. package/lib/config/php/versions/php-7.2.js +23 -0
  31. package/lib/config/php/versions/php-7.3.js +23 -0
  32. package/lib/config/php/versions/php-7.4.js +23 -0
  33. package/lib/config/php/versions/php-8.1.js +23 -0
  34. package/lib/config/php-config.js +8 -12
  35. package/lib/config/port-config.js +2 -6
  36. package/lib/config/services/elasticsearch/base-repo.js +3 -0
  37. package/lib/config/services/elasticsearch/default-es-env.js +6 -0
  38. package/lib/config/services/elasticsearch/versions/elasticsearch-6.8.js +19 -0
  39. package/lib/config/services/elasticsearch/versions/index.js +5 -0
  40. package/lib/config/templates/magentorc.template +6 -6
  41. package/lib/config/templates/mariadb.template.cnf +191 -0
  42. package/lib/config/templates/php-fpm.template.conf +3 -3
  43. package/lib/config/templates/php.template.ini +12 -6
  44. package/lib/config/templates/ssl-terminator.template.conf +9 -4
  45. package/lib/config/templates/vscode-launch.template.json +3 -1
  46. package/lib/config/versions/magento-2.3.0.js +10 -5
  47. package/lib/config/versions/magento-2.3.1.js +10 -5
  48. package/lib/config/versions/magento-2.3.2-p1.js +43 -0
  49. package/lib/config/versions/magento-2.3.2-p2.js +10 -5
  50. package/lib/config/versions/magento-2.3.2.js +10 -5
  51. package/lib/config/versions/magento-2.3.3-p1.js +10 -5
  52. package/lib/config/versions/magento-2.3.3.js +10 -5
  53. package/lib/config/versions/magento-2.3.4-p1.js +43 -0
  54. package/lib/config/versions/magento-2.3.4-p2.js +10 -5
  55. package/lib/config/versions/magento-2.3.4.js +10 -5
  56. package/lib/config/versions/magento-2.3.5-p1.js +8 -2
  57. package/lib/config/versions/magento-2.3.5-p2.js +8 -2
  58. package/lib/config/versions/magento-2.3.5.js +8 -2
  59. package/lib/config/versions/magento-2.3.6-p1.js +8 -2
  60. package/lib/config/versions/magento-2.3.6.js +8 -2
  61. package/lib/config/versions/magento-2.3.7-p1.js +8 -2
  62. package/lib/config/versions/magento-2.3.7-p2.js +8 -2
  63. package/lib/config/versions/magento-2.3.7-p3.js +8 -2
  64. package/lib/config/versions/magento-2.3.7-p4.js +44 -0
  65. package/lib/config/versions/magento-2.3.7.js +8 -2
  66. package/lib/config/versions/magento-2.4.0-p1.js +9 -3
  67. package/lib/config/versions/magento-2.4.0.js +9 -3
  68. package/lib/config/versions/magento-2.4.1-p1.js +6 -5
  69. package/lib/config/versions/magento-2.4.1.js +9 -2
  70. package/lib/config/versions/magento-2.4.2-p1.js +6 -5
  71. package/lib/config/versions/magento-2.4.2-p2.js +6 -6
  72. package/lib/config/versions/magento-2.4.2.js +6 -6
  73. package/lib/config/versions/magento-2.4.3-p1.js +7 -7
  74. package/lib/config/versions/magento-2.4.3-p2.js +7 -7
  75. package/lib/config/versions/magento-2.4.3-p3.js +46 -0
  76. package/lib/config/versions/magento-2.4.3.js +7 -7
  77. package/lib/config/versions/magento-2.4.4-p1.js +46 -0
  78. package/lib/config/versions/magento-2.4.4.js +9 -2
  79. package/lib/config/versions/magento-2.4.5.js +46 -0
  80. package/lib/tasks/cleanup.js +3 -3
  81. package/lib/tasks/composer/index.js +14 -104
  82. package/lib/tasks/database/connect-to-database.js +117 -0
  83. package/lib/tasks/database/create-magento-database.js +18 -0
  84. package/lib/tasks/{mysql → database}/dump-theme-config.js +3 -3
  85. package/lib/tasks/{mysql → database}/fix-db.js +2 -2
  86. package/lib/tasks/{mysql/import-dump-to-mysql.js → database/import-dump-to-database.js} +65 -22
  87. package/lib/tasks/{mysql → database}/import-remote-db/index.js +0 -0
  88. package/lib/tasks/{mysql/import-remote-db/ssh/mysqldump-command.js → database/import-remote-db/ssh/database-dump-command.js} +2 -2
  89. package/lib/tasks/{mysql → database}/import-remote-db/ssh/index.js +0 -0
  90. package/lib/tasks/{mysql → database}/import-remote-db/ssh/readymage.js +4 -4
  91. package/lib/tasks/{mysql → database}/import-remote-db/ssh/regular-server.js +2 -2
  92. package/lib/tasks/{mysql → database}/index.js +2 -2
  93. package/lib/tasks/{mysql → database}/magento-tables.js +0 -0
  94. package/lib/tasks/{mysql → database}/restore-theme-config.js +4 -4
  95. package/lib/tasks/docker/api.d.ts +71 -0
  96. package/lib/tasks/docker/api.js +30 -0
  97. package/lib/tasks/docker/containers/container-api.d.ts +132 -0
  98. package/lib/tasks/docker/containers/container-api.js +163 -0
  99. package/lib/tasks/docker/containers/index.js +19 -0
  100. package/lib/tasks/docker/containers/tasks.js +215 -0
  101. package/lib/tasks/docker/convert-legacy-volumes.js +15 -10
  102. package/lib/tasks/docker/convert-mysql-to-mariadb.js +284 -0
  103. package/lib/tasks/docker/image/image-api.d.ts +34 -0
  104. package/lib/tasks/docker/image/image-api.js +49 -0
  105. package/lib/tasks/docker/image/index.js +5 -0
  106. package/lib/tasks/docker/index.js +1 -13
  107. package/lib/tasks/docker/network/index.js +7 -0
  108. package/lib/tasks/docker/network/network-api.d.ts +103 -0
  109. package/lib/tasks/docker/network/network-api.js +99 -0
  110. package/lib/tasks/docker/{network.js → network/tasks.js} +17 -10
  111. package/lib/tasks/docker/project-image-builder.js +167 -0
  112. package/lib/tasks/docker/volume/index.js +8 -0
  113. package/lib/tasks/docker/{volumes.js → volume/tasks.js} +5 -19
  114. package/lib/tasks/docker/volume/volume-api.d.ts +39 -0
  115. package/lib/tasks/docker/volume/volume-api.js +66 -0
  116. package/lib/tasks/execute.js +97 -0
  117. package/lib/tasks/file-system/create-mariadb-config.js +23 -0
  118. package/lib/tasks/file-system/create-nginx-config.js +2 -3
  119. package/lib/tasks/file-system/create-php-config.js +20 -5
  120. package/lib/tasks/file-system/create-php-fpm-config.js +8 -4
  121. package/lib/tasks/file-system/create-phpstorm-config/exclude-folder-config.js +41 -29
  122. package/lib/tasks/file-system/create-phpstorm-config/index.js +2 -0
  123. package/lib/tasks/file-system/create-phpstorm-config/keys.js +15 -1
  124. package/lib/tasks/file-system/create-phpstorm-config/php-config/index.js +4 -1
  125. package/lib/tasks/file-system/create-phpstorm-config/php-config/php-config.js +3 -3
  126. package/lib/tasks/file-system/create-phpstorm-config/php-config/php-interpreters-config.js +81 -0
  127. package/lib/tasks/file-system/create-phpstorm-config/php-docker-settings-config/index.js +42 -0
  128. package/lib/tasks/file-system/create-phpstorm-config/php-docker-settings-config/php-docker-settings-config.js +9 -0
  129. package/lib/tasks/file-system/create-phpstorm-config/php-docker-settings-config/setup-php-docker-container-settings-config.js +66 -0
  130. package/lib/tasks/file-system/create-phpstorm-config/setup-xml-structure.js +11 -9
  131. package/lib/tasks/file-system/create-phpstorm-config/stylelint-config.js +2 -1
  132. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/composer-settings-config.js +15 -30
  133. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/index.js +24 -5
  134. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/mess-detector-project-configuration-config.js +50 -0
  135. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/php-code-sniffer-project-configuration-config.js +50 -0
  136. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/php-cs-fixer-project-configuration-config.js +50 -0
  137. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/php-debug-general-config.js +15 -15
  138. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/php-server-config.js +29 -3
  139. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/php-stan-project-configuration-config.js.js +50 -0
  140. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/php-workspace-project-configuration-config.js +42 -0
  141. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/psalm-project-configuration-config.js.js +50 -0
  142. package/lib/tasks/file-system/create-phpstorm-config/workspace-config/workspace-config.js +0 -2
  143. package/lib/tasks/file-system/create-ssl-terminator-config.js +4 -2
  144. package/lib/tasks/file-system/create-vscode-config.js +57 -42
  145. package/lib/tasks/file-system/index.js +5 -2
  146. package/lib/tasks/import-dump.js +6 -6
  147. package/lib/tasks/link.js +5 -4
  148. package/lib/tasks/magento/enable-magento-composer-plugins.js +85 -30
  149. package/lib/tasks/magento/install-magento-project.js +32 -63
  150. package/lib/tasks/magento/setup-magento/adjust-full-page-cache.js +4 -4
  151. package/lib/tasks/magento/setup-magento/configure-elasticsearch.js +7 -3
  152. package/lib/tasks/magento/setup-magento/create-admin.js +5 -6
  153. package/lib/tasks/magento/setup-magento/delete-admin-users.js +2 -2
  154. package/lib/tasks/magento/setup-magento/delete-customers.js +4 -4
  155. package/lib/tasks/magento/setup-magento/delete-orders.js +4 -4
  156. package/lib/tasks/magento/setup-magento/disable-2fa.js +3 -5
  157. package/lib/tasks/magento/setup-magento/disable-maintenance-mode.js +3 -4
  158. package/lib/tasks/magento/setup-magento/increase-admin-session-lifetime.js +2 -2
  159. package/lib/tasks/magento/setup-magento/index.js +2 -0
  160. package/lib/tasks/magento/setup-magento/install-magento.js +21 -20
  161. package/lib/tasks/magento/setup-magento/migrate-database.js +7 -14
  162. package/lib/tasks/magento/setup-magento/set-base-url.js +3 -3
  163. package/lib/tasks/magento/setup-magento/set-deployment-mode.js +4 -4
  164. package/lib/tasks/magento/setup-magento/set-url-rewrite.js +2 -2
  165. package/lib/tasks/magento/setup-magento/varnish-config.js +10 -8
  166. package/lib/tasks/magento/setup-magento/waiting-for-varnish.js +130 -3
  167. package/lib/tasks/php/php-container.js +112 -0
  168. package/lib/tasks/php/update-env-php.js +39 -21
  169. package/lib/tasks/php/update-env.php +66 -61
  170. package/lib/tasks/php/working_health_check.php +85 -0
  171. package/lib/tasks/requirements/{composer.js → composer-credentials.js} +3 -1
  172. package/lib/tasks/requirements/docker/index.js +18 -13
  173. package/lib/tasks/requirements/docker/performance.js +54 -0
  174. package/lib/tasks/requirements/docker/version.js +8 -8
  175. package/lib/tasks/requirements/index.js +5 -8
  176. package/lib/tasks/requirements/php-version.js +8 -116
  177. package/lib/tasks/requirements/platform.js +12 -25
  178. package/lib/tasks/start.js +21 -50
  179. package/lib/tasks/status/index.js +8 -12
  180. package/lib/tasks/stop.js +0 -2
  181. package/lib/tasks/theme/install-theme.js +1 -1
  182. package/lib/tasks/theme/link-theme.js +2 -2
  183. package/lib/tasks/theme/symlink-theme.js +2 -3
  184. package/lib/util/config-file-validator.js +27 -13
  185. package/lib/util/config-php-json.js +13 -4
  186. package/lib/util/database.js +7 -7
  187. package/lib/util/dockerfile-builder/build-instructions.js +197 -0
  188. package/lib/util/dockerfile-builder/index.js +276 -0
  189. package/lib/util/dockerfile-builder/types.d.ts +123 -0
  190. package/lib/util/env-php-json.js +10 -6
  191. package/lib/util/exec-async-command.js +3 -9
  192. package/lib/util/execute-in-container.js +63 -0
  193. package/lib/util/macos-version.js +20 -0
  194. package/lib/util/magento-task.js +3 -4
  195. package/lib/util/nginx-logs-parser.js +122 -0
  196. package/lib/util/php-task.js +3 -6
  197. package/lib/util/run-composer.js +6 -14
  198. package/lib/util/run-container-image.js +17 -0
  199. package/lib/util/run-magento.js +6 -14
  200. package/lib/util/run-php.js +6 -17
  201. package/package.json +11 -10
  202. package/typings/context.d.ts +7 -13
  203. package/typings/index.d.ts +67 -85
  204. package/lib/config/composer.js +0 -11
  205. package/lib/config/php/extensions/libsodium.js +0 -36
  206. package/lib/config/php/releases/php-7.2.js +0 -25
  207. package/lib/config/php/releases/php-7.3.js +0 -25
  208. package/lib/config/php/releases/php-7.4.js +0 -23
  209. package/lib/config/php/releases/php-8.1.js +0 -25
  210. package/lib/config/phpbrew.js +0 -12
  211. package/lib/tasks/composer/install-prestissimo.js +0 -103
  212. package/lib/tasks/docker/containers.js +0 -231
  213. package/lib/tasks/execute/index.js +0 -23
  214. package/lib/tasks/mysql/connect-to-mysql.js +0 -114
  215. package/lib/tasks/mysql/create-magento-database.js +0 -18
  216. package/lib/tasks/php/bundled-extensions.js +0 -27
  217. package/lib/tasks/php/compile-options.js +0 -56
  218. package/lib/tasks/php/compile.js +0 -55
  219. package/lib/tasks/php/configure.js +0 -89
  220. package/lib/tasks/php/extensions/disable.js +0 -49
  221. package/lib/tasks/php/extensions/enable.js +0 -52
  222. package/lib/tasks/php/extensions/index.js +0 -80
  223. package/lib/tasks/php/extensions/install.js +0 -54
  224. package/lib/tasks/php/index.js +0 -79
  225. package/lib/tasks/php/install-sodium.js +0 -93
  226. package/lib/tasks/php/update-phpbrew.js +0 -45
  227. package/lib/tasks/php/validate-php.js +0 -67
  228. package/lib/tasks/php-fpm/get-process-id.js +0 -14
  229. package/lib/tasks/php-fpm/index.js +0 -4
  230. package/lib/tasks/php-fpm/start-php-fpm.js +0 -49
  231. package/lib/tasks/php-fpm/stop-php-fpm.js +0 -48
  232. package/lib/tasks/requirements/phpbrew/index.js +0 -61
  233. package/lib/tasks/requirements/phpbrew/install.js +0 -159
  234. package/lib/tasks/requirements/phpbrew/version.js +0 -28
@@ -1,6 +1,6 @@
1
1
  module.exports = {
2
- connectToMySQL: require('./connect-to-mysql'),
3
- importDumpToMySQL: require('./import-dump-to-mysql'),
2
+ connectToDatabase: require('./connect-to-database'),
3
+ importDumpToDatabase: require('./import-dump-to-database'),
4
4
  fixDB: require('./fix-db'),
5
5
  dumpThemeConfig: require('./dump-theme-config'),
6
6
  restoreThemeConfig: require('./restore-theme-config')
File without changes
@@ -6,7 +6,7 @@ const { updateTableValues } = require('../../util/database');
6
6
  const restoreThemeConfig = () => ({
7
7
  title: 'Restoring themes and theme configuration',
8
8
  task: async (ctx, task) => {
9
- const { themeDump, mysqlConnection } = ctx;
9
+ const { themeDump, databaseConnection } = ctx;
10
10
 
11
11
  const { themeIdConfig, themes } = themeDump;
12
12
 
@@ -22,7 +22,7 @@ const restoreThemeConfig = () => ({
22
22
  path: themeIdConfig.path,
23
23
  value: themeIdConfig.value
24
24
  }
25
- ], { mysqlConnection, task });
25
+ ], { databaseConnection, task });
26
26
  }
27
27
 
28
28
  if (themes.length === 0) {
@@ -31,10 +31,10 @@ const restoreThemeConfig = () => ({
31
31
 
32
32
  // restore themes
33
33
  const themeKeys = Object.keys(themes[0]);
34
- await mysqlConnection.query('delete from theme;');
34
+ await databaseConnection.query('delete from theme;');
35
35
 
36
36
  for (const theme of themes) {
37
- await mysqlConnection.query(`
37
+ await databaseConnection.query(`
38
38
  insert into theme (${themeKeys.join(', ')})
39
39
  values (${themeKeys.map(() => '?').join(', ')})
40
40
  `, Object.values(theme));
@@ -0,0 +1,71 @@
1
+ import { ExecAsyncSpawnOptions } from '../../util/exec-async-command';
2
+
3
+ export interface DockerVersionOptions<T extends boolean = false> {
4
+ format?: string
5
+ format?: string
6
+ formatToJSON?: T
7
+ }
8
+
9
+ export interface DockerClientDetails {
10
+ Platform: {
11
+ Name: string
12
+ }
13
+ CloudIntegration: string
14
+ Version: string
15
+ ApiVersion: string
16
+ DefaultAPIVersion: string
17
+ GitCommit: string
18
+ GoVersion: string
19
+ Os: string
20
+ Arch: string
21
+ BuildTime: string
22
+ Context: string
23
+ Experimental: boolean
24
+ }
25
+
26
+ export interface DockerServerComponent {
27
+ Name: string
28
+ Version: string
29
+ Details: {
30
+ ApiVersion?: string
31
+ Arch?: string
32
+ BuildTime?: string
33
+ Experimental?: string
34
+ GitCommit: string
35
+ GoVersion?: string
36
+ KernelVersion?: string
37
+ MinApiVersion?: string
38
+ Os?: string
39
+ }
40
+ }
41
+
42
+ export interface DockerServerDetails {
43
+ Platform: {
44
+ Name: string
45
+ }
46
+ Components: DockerServerComponent[]
47
+ Version: string
48
+ ApiVersion: string
49
+ MinAPIVersion: string
50
+ GitCommit: string
51
+ GoVersion: string
52
+ Os: string
53
+ Arch: string
54
+ KernelVersion: string
55
+ BuildTime: string
56
+ }
57
+
58
+ export interface DockerVersionResult {
59
+ Client: DockerClientDetails
60
+ Server: DockerServerDetails
61
+ }
62
+
63
+ export function version(
64
+ options: DockerVersionOptions,
65
+ execOptions?: ExecAsyncSpawnOptions<false>
66
+ ): Promise<string>
67
+
68
+ export function version(
69
+ options: DockerVersionOptions<true>,
70
+ execOptions?: ExecAsyncSpawnOptions<false>
71
+ ): Promise<DockerVersionResult>
@@ -0,0 +1,30 @@
1
+ const { execAsyncSpawn } = require('../../util/exec-async-command');
2
+
3
+ /**
4
+ * @param {import('./api').DockerVersionOptions} options
5
+ * @param {import('../../util/exec-async-command').ExecAsyncSpawnOptions} execOptions
6
+ */
7
+ const version = async (options, execOptions = {}) => {
8
+ const {
9
+ format,
10
+ formatToJSON
11
+ } = options;
12
+
13
+ const formatArg = !formatToJSON && format
14
+ ? `--format=${format}`
15
+ : formatToJSON && '--format=\'{{json .}}\'';
16
+ const args = [
17
+ formatArg
18
+ ].filter(Boolean).join(' ');
19
+
20
+ if (formatToJSON) {
21
+ const result = await execAsyncSpawn(`docker version ${args}`, execOptions);
22
+ return JSON.parse(result);
23
+ }
24
+
25
+ return execAsyncSpawn(`docker version ${args}`, execOptions);
26
+ };
27
+
28
+ module.exports = {
29
+ version
30
+ };
@@ -0,0 +1,132 @@
1
+ /* eslint-disable max-len */
2
+ import { ExecAsyncSpawnOptions } from '../../../util/exec-async-command';
3
+
4
+ export interface ContainerLsOptions<T extends boolean = false> {
5
+ all?: boolean
6
+ filter?: string | string[]
7
+ format?: string
8
+ quiet?: boolean
9
+ noTrunc?: boolean
10
+ formatToJSON?: T
11
+ latest?: boolean
12
+ }
13
+
14
+ export interface ContainerLsResult {
15
+ Command: string
16
+ CreatedAt: string
17
+ ID: string
18
+ Image: string
19
+ Labels: string
20
+ LocalVolumes: string
21
+ Mounts: string
22
+ Names: string
23
+ Networks: string
24
+ Ports: string
25
+ RunningFor: string
26
+ Size: string
27
+ State: string
28
+ Status: string
29
+ }
30
+
31
+ export function ls(options?: ContainerLsOptions, execOptions?: ExecAsyncSpawnOptions<false>): Promise<string>
32
+ export function ls(options?: ContainerLsOptions<true>, execOptions?: ExecAsyncSpawnOptions<false>): Promise<ContainerLsResult[]>
33
+
34
+ export interface ContainerExecOptions {
35
+ /**
36
+ * Set environment variables [docs](https://docs.docker.com/engine/reference/commandline/run/#set-environment-variables--e---env---env-file)
37
+ */
38
+ env?: Record<string, string>
39
+
40
+ /**
41
+ * Working directory inside the container
42
+ */
43
+ workdir?: string
44
+
45
+ /**
46
+ * Username or UID (format: <name|uid>[:<group|gid>])
47
+ */
48
+ user?: string
49
+
50
+ /**
51
+ * Allocate a pseudo-TTY
52
+ */
53
+ tty?: boolean
54
+ }
55
+
56
+ export function exec(command: string, container: string, options?: ContainerExecOptions, execOptions?: ExecAsyncSpawnOptions<false>): Promise<string>
57
+
58
+ export interface ContainerRunOptions {
59
+ /**
60
+ * Add a custom host-to-IP mapping (host:ip)
61
+ */
62
+ addHost?: string
63
+ /**
64
+ * Automatically remove the container when it exits
65
+ */
66
+ rm?: boolean
67
+
68
+ /**
69
+ * Run container in background and print container ID
70
+ */
71
+ detach?: boolean
72
+
73
+ tty?: boolean
74
+ /**
75
+ * Publish or expose port [docs](https://docs.docker.com/engine/reference/commandline/run/#publish-or-expose-port--p---expose)
76
+ */
77
+ ports?: number[]
78
+
79
+ /**
80
+ * Add bind mounts or volumes using the --mount flag [docs](https://docs.docker.com/engine/reference/commandline/run/#add-bind-mounts-or-volumes-using-the---mount-flag)
81
+ */
82
+ mounts?: string[]
83
+
84
+ /**
85
+ * Mount volume [docs](https://docs.docker.com/engine/reference/commandline/run/#mount-volume--v---read-only)
86
+ */
87
+ mountVolumes?: string[]
88
+
89
+ /**
90
+ * Set environment variables [docs](https://docs.docker.com/engine/reference/commandline/run/#set-environment-variables--e---env---env-file)
91
+ */
92
+ env?: Record<string, string>
93
+ image?: string
94
+ /**
95
+ * Restart policies [docs](https://docs.docker.com/engine/reference/commandline/run/#restart-policies---restart)
96
+ */
97
+ restart?: string
98
+
99
+ /**
100
+ * Container name
101
+ */
102
+ name?: string
103
+
104
+ /**
105
+ * Container entrypoint
106
+ */
107
+ entrypoint?: string
108
+
109
+ /**
110
+ * Container command
111
+ */
112
+ command?: string
113
+
114
+ /**
115
+ * Container heathcheck properties
116
+ */
117
+ healthCheck?: Record<'cmd' | 'interval' | 'retries' | 'start-period' | 'timeout', string>
118
+
119
+ /**
120
+ * Security options [docs](https://docs.docker.com/engine/reference/commandline/run/#optional-security-options---security-opt)
121
+ */
122
+ securityOptions?: string[]
123
+ tmpfs?: string[]
124
+ /**
125
+ * Username or UID (format: <name|uid>[:<group|gid>])
126
+ */
127
+ user?: string
128
+ }
129
+
130
+ export function run(containerOptions: ContainerRunOptions, execOptions?: ExecAsyncSpawnOptions<false>): Promise<false>
131
+
132
+ export function runCommand(options: ContainerRunOptions): string[]
@@ -0,0 +1,163 @@
1
+ /* eslint-disable max-len */
2
+ const { execAsyncSpawn } = require('../../../util/exec-async-command');
3
+
4
+ /**
5
+ * @param {import('./container-api').ContainerRunOptions} options
6
+ * @returns {string[]}
7
+ */
8
+ const runCommand = (options) => {
9
+ const {
10
+ addHost,
11
+ ports = [],
12
+ mounts = [],
13
+ mountVolumes = [],
14
+ env,
15
+ image,
16
+ restart,
17
+ network,
18
+ name,
19
+ entrypoint,
20
+ command = '',
21
+ healthCheck,
22
+ securityOptions = [],
23
+ tmpfs = [],
24
+ expose = [],
25
+ detach = true,
26
+ rm = false,
27
+ tty = false,
28
+ user
29
+ } = options;
30
+
31
+ const detachArg = detach && '-d';
32
+ const rmArg = rm && '--rm';
33
+ const ttyArg = tty && '-it';
34
+ const exposeArg = expose && expose.map((e) => `--expose=${ e }`);
35
+ const restartArg = !rm && restart && `--restart=${ restart }`;
36
+ const networkArg = network && `--network=${ network }`;
37
+ const portsArgs = ports && ports.length > 0 && ports.map((port) => `-p=${ port }`).join(' ');
38
+ const mountsArgs = mounts && mounts.map((mount) => `--mount=${ mount }`).join(' ');
39
+ const mountVolumesArgs = mountVolumes && mountVolumes.map((mount) => `-v=${mount}`).join(' ');
40
+ const envArgs = !env ? '' : Object.entries(env).map(([key, value]) => `--env=${ key }='${ value }'`).join(' ');
41
+ const nameArg = name && `--name=${name}`;
42
+ const entrypointArg = entrypoint && `--entrypoint="${entrypoint}"`;
43
+ const healthCheckArg = healthCheck && Object.entries(healthCheck).map(([key, value]) => `--health-${key}='${value}'`).join(' ');
44
+ const securityArg = securityOptions.length > 0 && securityOptions.map((opt) => `--security-opt=${opt}`).join(' ');
45
+ const tmpfsArg = tmpfs.length > 0 && tmpfs.map((t) => `--tmpfs=${t}`).join(' ');
46
+ const userArg = user && `--user=${user}`;
47
+ const addHostArg = addHost && `--add-host=${addHost}`;
48
+
49
+ const dockerCommand = [
50
+ 'docker',
51
+ 'run',
52
+ nameArg,
53
+ ttyArg,
54
+ detachArg,
55
+ rmArg,
56
+ networkArg,
57
+ restartArg,
58
+ portsArgs,
59
+ exposeArg,
60
+ mountsArgs,
61
+ mountVolumesArgs,
62
+ envArgs,
63
+ entrypointArg,
64
+ healthCheckArg,
65
+ securityArg,
66
+ tmpfsArg,
67
+ userArg,
68
+ addHostArg,
69
+ image,
70
+ command
71
+ ].filter(Boolean).filter((arg) => typeof arg === 'string');
72
+
73
+ return dockerCommand;
74
+ };
75
+
76
+ /**
77
+ * @param {import('./container-api').ContainerRunOptions} options
78
+ * @param {import('../../../util/exec-async-command').ExecAsyncSpawnOptions<false>} execOptions
79
+ */
80
+ const run = (options, execOptions = {}) => execAsyncSpawn(runCommand(options).join(' '), execOptions);
81
+
82
+ /**
83
+ * @param {string} command
84
+ * @param {string} container container id or name
85
+ * @param {import('./container-api').ContainerExecOptions} options
86
+ * @param {import('../../../util/exec-async-command').ExecAsyncSpawnOptions<false>} execOptions
87
+ */
88
+ const exec = (command, container, options = {}, execOptions = {}) => {
89
+ const {
90
+ env,
91
+ tty,
92
+ user,
93
+ workdir
94
+ } = options;
95
+ const envArgs = !env ? '' : Object.entries(env).map(([key, value]) => `--env ${ key }='${ value }'`).join(' ');
96
+ const ttyArg = tty ? '--tty' : '';
97
+ const userArg = user ? `--user=${user}` : '';
98
+ const workdirArg = workdir ? `--workdir=${workdir}` : '';
99
+
100
+ const execCommand = [
101
+ 'docker',
102
+ 'container',
103
+ 'exec',
104
+ envArgs,
105
+ ttyArg,
106
+ userArg,
107
+ workdirArg,
108
+ container,
109
+ command
110
+ ].filter(Boolean).join(' ');
111
+
112
+ return execAsyncSpawn(execCommand, execOptions);
113
+ };
114
+
115
+ /**
116
+ * @param {import('./container-api').ContainerLsOptions} options
117
+ * @param {import('../../../util/exec-async-command').ExecAsyncSpawnOptions<false>} execOptions
118
+ */
119
+ const ls = async (options = {}, execOptions = {}) => {
120
+ const {
121
+ all,
122
+ filter,
123
+ format,
124
+ formatToJSON = false,
125
+ latest,
126
+ noTrunc,
127
+ quiet
128
+ } = options;
129
+
130
+ const allArg = all && '--all';
131
+ const filterArg = filter && typeof filter === 'string'
132
+ ? `--filter=${filter}`
133
+ : filter && Array.isArray(filter) && filter.every((f) => typeof f === 'string') && filter.map((f) => `--filter=${f}`).join(' ');
134
+ const formatArg = !formatToJSON && format
135
+ ? `--format=${format}`
136
+ : formatToJSON && '--format=\'{{json .}}\'';
137
+ const latestArg = latest && '--latest';
138
+ const noTruncArg = noTrunc && '--no-trunc';
139
+ const quietArg = quiet && '--quiet';
140
+
141
+ const args = [
142
+ allArg,
143
+ filterArg,
144
+ formatArg,
145
+ latestArg,
146
+ noTruncArg,
147
+ quietArg
148
+ ].filter(Boolean).join(' ');
149
+
150
+ if (formatToJSON) {
151
+ const result = await execAsyncSpawn(`docker container ls ${args}`, execOptions);
152
+ return JSON.parse(`[${result.split('\n').join(', ')}]`);
153
+ }
154
+
155
+ return execAsyncSpawn(`docker container ls ${args}`, execOptions);
156
+ };
157
+
158
+ module.exports = {
159
+ run,
160
+ runCommand,
161
+ exec,
162
+ ls
163
+ };
@@ -0,0 +1,19 @@
1
+ const {
2
+ startContainers,
3
+ stopContainers,
4
+ pullImages,
5
+ statusContainers,
6
+ checkContainersAreRunning,
7
+ getContainerStatus
8
+ } = require('./tasks');
9
+ const containerApi = require('./container-api');
10
+
11
+ module.exports = {
12
+ startContainers,
13
+ stopContainers,
14
+ pullImages,
15
+ statusContainers,
16
+ checkContainersAreRunning,
17
+ getContainerStatus,
18
+ containerApi
19
+ };
@@ -0,0 +1,215 @@
1
+ /* eslint-disable max-len */
2
+ const sleep = require('../../../util/sleep');
3
+ const logger = require('@scandipwa/scandipwa-dev-utils/logger');
4
+ const KnownError = require('../../../errors/known-error');
5
+ const containerApi = require('./container-api');
6
+ const { imageApi } = require('../image');
7
+ const { execAsyncSpawn } = require('../../../util/exec-async-command');
8
+
9
+ const stop = async (containers) => {
10
+ await execAsyncSpawn(`docker container stop ${containers.join(' ')}`);
11
+ await execAsyncSpawn(`docker container rm ${containers.join(' ')}`);
12
+ };
13
+
14
+ const pull = async (image) => execAsyncSpawn(`docker pull ${image}`);
15
+
16
+ const remoteImageReducer = (acc, val) => {
17
+ if (Array.isArray(val.remoteImages) && val.remoteImages.every((image) => typeof image === 'string')) {
18
+ return acc.concat(val.remoteImages);
19
+ }
20
+
21
+ return acc.concat([val.image]);
22
+ };
23
+
24
+ /**
25
+ * @type {() => import('listr2').ListrTask<import('../../../../typings/context').ListrContext>}
26
+ */
27
+ const pullImages = () => ({
28
+ title: 'Pulling container images',
29
+ task: async ({ config: { docker } }, task) => {
30
+ const containers = Object.values(docker.getContainers());
31
+ const imagesFilter = containers
32
+ .reduce(remoteImageReducer, [])
33
+ .map((image) => `reference='${image}'`);
34
+
35
+ const existingImages = await imageApi.ls({
36
+ formatToJSON: true,
37
+ filter: imagesFilter
38
+ });
39
+
40
+ const missingContainerImages = containers
41
+ .reduce(remoteImageReducer, [])
42
+ .map((image) => {
43
+ const [repo, tag = 'latest'] = image.split(':');
44
+
45
+ return { repo, tag };
46
+ })
47
+ .filter(
48
+ ({ repo, tag }) => !existingImages.some(
49
+ (image) => image.Repository === repo
50
+ && image.Tag === tag
51
+ )
52
+ )
53
+ .reduce(
54
+ (acc, val) => acc.concat(
55
+ acc.some(
56
+ (c) => c.repo === val.repo
57
+ && c.tag === val.tag
58
+ )
59
+ ? []
60
+ : val
61
+ ),
62
+ []
63
+ );
64
+
65
+ if (missingContainerImages.length === 0) {
66
+ task.skip();
67
+ return;
68
+ }
69
+
70
+ return task.newListr(
71
+ missingContainerImages.map(({ repo, tag }) => ({
72
+ title: `Pulling ${ logger.style.file(`${repo}:${tag}`) } image`,
73
+ task: () => pull(`${repo}:${tag}`)
74
+ })), {
75
+ concurrent: true,
76
+ exitOnError: true
77
+ }
78
+ );
79
+ }
80
+ });
81
+
82
+ /**
83
+ * @type {() => import('listr2').ListrTask<import('../../../typings/context').ListrContext>}
84
+ */
85
+ const startContainers = () => ({
86
+ title: 'Starting containers',
87
+ task: async ({ ports, config: { docker }, debug }, task) => {
88
+ const containerList = (await execAsyncSpawn('docker container ls --all --format="{{.Names}}"')).split('\n');
89
+
90
+ const missingContainers = Object.values(docker.getContainers(ports)).filter(
91
+ ({ name }) => !containerList.includes(name)
92
+ );
93
+
94
+ if (missingContainers.length === 0) {
95
+ task.skip();
96
+ return;
97
+ }
98
+
99
+ if (debug) {
100
+ await Promise.all(
101
+ missingContainers
102
+ .map((container) => {
103
+ if (container.debugImage) {
104
+ container.image = container.debugImage;
105
+ }
106
+
107
+ return container;
108
+ }).map((container) => containerApi.run(container).then((out) => {
109
+ task.output = `From ${container._}: ${out}`;
110
+ }))
111
+ );
112
+
113
+ return;
114
+ }
115
+
116
+ // TODO: we might stop containers here ?
117
+ await Promise.all(missingContainers.map((container) => containerApi.run(container).then((out) => {
118
+ task.output = `From ${container._}: ${out}`;
119
+ })));
120
+ },
121
+ options: {
122
+ bottomBar: 10
123
+ }
124
+ });
125
+
126
+ /**
127
+ * @type {() => import('listr2').ListrTask<import('../../../typings/context').ListrContext>}
128
+ */
129
+ const stopContainers = () => ({
130
+ title: 'Stopping Docker containers',
131
+ task: async ({ config: { baseConfig: { prefix } } }, task) => {
132
+ const containerList = (await execAsyncSpawn('docker container ls --all --format="{{.Names}}"')).split('\n');
133
+
134
+ const runningContainers = containerList.filter((containerName) => containerName.startsWith(prefix));
135
+
136
+ if (runningContainers.length === 0) {
137
+ task.skip();
138
+ return;
139
+ }
140
+
141
+ await stop(runningContainers);
142
+ }
143
+ });
144
+
145
+ const getContainerStatus = async (containerName) => {
146
+ try {
147
+ return JSON.parse(await execAsyncSpawn(`docker inspect --format='{{json .State}}' ${containerName}`));
148
+ } catch {
149
+ return null;
150
+ }
151
+ };
152
+
153
+ /**
154
+ * @type {() => import('listr2').ListrTask<import('../../../typings/context').ListrContext>}
155
+ */
156
+ const checkContainersAreRunning = () => ({
157
+ title: 'Checking container statuses',
158
+ task: async (ctx, task) => {
159
+ const { config: { docker }, ports } = ctx;
160
+ const containers = Object.values(docker.getContainers(ports));
161
+ let tries = 0;
162
+ while (tries < 3) {
163
+ const containersWithStatus = await Promise.all(
164
+ containers.map(async (container) => ({
165
+ ...container,
166
+ status: await getContainerStatus(container.name)
167
+ }))
168
+ );
169
+
170
+ if (containersWithStatus.some((c) => c.status.Status !== 'running')) {
171
+ if (tries === 2) {
172
+ throw new KnownError(`${containersWithStatus.filter((c) => c.status.Status !== 'running').map((c) => c._).join(', ')} containers are not running! Please check container logs for more details!`);
173
+ } else {
174
+ task.output = `${containersWithStatus.filter((c) => c.status.Status !== 'running').map((c) => c._).join(', ')} are not running, waiting if something will change...`;
175
+ await sleep(2000);
176
+ tries++;
177
+ }
178
+ } else {
179
+ break;
180
+ }
181
+ }
182
+ },
183
+ options: {
184
+ bottomBar: 10
185
+ }
186
+ });
187
+
188
+ /**
189
+ * @type {() => import('listr2').ListrTask<import('../../../typings/context').ListrContext>}
190
+ */
191
+ const statusContainers = () => ({
192
+ task: async (ctx) => {
193
+ const { config: { docker }, ports } = ctx;
194
+ const containers = Object.values(docker.getContainers(ports));
195
+
196
+ ctx.containers = await Promise.all(
197
+ containers.map(async (container) => ({
198
+ ...container,
199
+ status: await getContainerStatus(container.name)
200
+ }))
201
+ );
202
+ },
203
+ options: {
204
+ bottomBar: 10
205
+ }
206
+ });
207
+
208
+ module.exports = {
209
+ startContainers,
210
+ stopContainers,
211
+ pullImages,
212
+ statusContainers,
213
+ checkContainersAreRunning,
214
+ getContainerStatus
215
+ };