synapse-mcp 1.0.0 → 1.0.2
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 +1820 -147
- package/dist/constants.d.ts +10 -4
- package/dist/constants.d.ts.map +1 -1
- package/dist/constants.js +18 -8
- package/dist/constants.js.map +1 -1
- package/dist/events/emitter.d.ts +63 -0
- package/dist/events/emitter.d.ts.map +1 -0
- package/dist/events/emitter.js +112 -0
- package/dist/events/emitter.js.map +1 -0
- package/dist/events/index.d.ts +3 -0
- package/dist/events/index.d.ts.map +1 -0
- package/dist/events/index.js +3 -0
- package/dist/events/index.js.map +1 -0
- package/dist/events/types.d.ts +51 -0
- package/dist/events/types.d.ts.map +1 -0
- package/dist/events/types.js +3 -0
- package/dist/events/types.js.map +1 -0
- package/dist/formatters/compose.d.ts +185 -0
- package/dist/formatters/compose.d.ts.map +1 -0
- package/dist/formatters/compose.js +397 -0
- package/dist/formatters/compose.js.map +1 -0
- package/dist/formatters/container.d.ts +84 -0
- package/dist/formatters/container.d.ts.map +1 -0
- package/dist/formatters/container.js +323 -0
- package/dist/formatters/container.js.map +1 -0
- package/dist/formatters/diagnostics.d.ts +20 -0
- package/dist/formatters/diagnostics.d.ts.map +1 -0
- package/dist/formatters/diagnostics.js +73 -0
- package/dist/formatters/diagnostics.js.map +1 -0
- package/dist/formatters/docker.d.ts +139 -0
- package/dist/formatters/docker.d.ts.map +1 -0
- package/dist/formatters/docker.js +216 -0
- package/dist/formatters/docker.js.map +1 -0
- package/dist/formatters/host.d.ts +137 -0
- package/dist/formatters/host.d.ts.map +1 -0
- package/dist/formatters/host.js +198 -0
- package/dist/formatters/host.js.map +1 -0
- package/dist/formatters/index.d.ts +17 -270
- package/dist/formatters/index.d.ts.map +1 -1
- package/dist/formatters/index.js +21 -456
- package/dist/formatters/index.js.map +1 -1
- package/dist/formatters/scout.d.ts +424 -0
- package/dist/formatters/scout.d.ts.map +1 -0
- package/dist/formatters/scout.js +687 -0
- package/dist/formatters/scout.js.map +1 -0
- package/dist/formatters/strategy.d.ts +105 -0
- package/dist/formatters/strategy.d.ts.map +1 -0
- package/dist/formatters/strategy.js +120 -0
- package/dist/formatters/strategy.js.map +1 -0
- package/dist/formatters/utils.d.ts +84 -0
- package/dist/formatters/utils.d.ts.map +1 -0
- package/dist/formatters/utils.js +129 -0
- package/dist/formatters/utils.js.map +1 -0
- package/dist/health-rate-limiter.d.ts +59 -0
- package/dist/health-rate-limiter.d.ts.map +1 -0
- package/dist/health-rate-limiter.js +159 -0
- package/dist/health-rate-limiter.js.map +1 -0
- package/dist/index.js +61 -100
- package/dist/index.js.map +1 -1
- package/dist/middleware/async-handler.d.ts +62 -0
- package/dist/middleware/async-handler.d.ts.map +1 -0
- package/dist/middleware/async-handler.js +58 -0
- package/dist/middleware/async-handler.js.map +1 -0
- package/dist/middleware/auth.d.ts +32 -0
- package/dist/middleware/auth.d.ts.map +1 -0
- package/dist/middleware/auth.js +63 -0
- package/dist/middleware/auth.js.map +1 -0
- package/dist/middleware/csrf-protection.d.ts +58 -0
- package/dist/middleware/csrf-protection.d.ts.map +1 -0
- package/dist/middleware/csrf-protection.js +123 -0
- package/dist/middleware/csrf-protection.js.map +1 -0
- package/dist/middleware/error-handler.d.ts +49 -0
- package/dist/middleware/error-handler.d.ts.map +1 -0
- package/dist/middleware/error-handler.js +90 -0
- package/dist/middleware/error-handler.js.map +1 -0
- package/dist/middleware/error-mapper.d.ts +44 -0
- package/dist/middleware/error-mapper.d.ts.map +1 -0
- package/dist/middleware/error-mapper.js +127 -0
- package/dist/middleware/error-mapper.js.map +1 -0
- package/dist/middleware/index.d.ts +13 -0
- package/dist/middleware/index.d.ts.map +1 -0
- package/dist/middleware/index.js +13 -0
- package/dist/middleware/index.js.map +1 -0
- package/dist/middleware/request-id.d.ts +22 -0
- package/dist/middleware/request-id.d.ts.map +1 -0
- package/dist/middleware/request-id.js +31 -0
- package/dist/middleware/request-id.js.map +1 -0
- package/dist/middleware/types.d.ts +33 -0
- package/dist/middleware/types.d.ts.map +1 -0
- package/dist/middleware/types.js +2 -0
- package/dist/middleware/types.js.map +1 -0
- package/dist/schemas/common.d.ts +205 -8
- package/dist/schemas/common.d.ts.map +1 -1
- package/dist/schemas/common.js +290 -17
- package/dist/schemas/common.js.map +1 -1
- package/dist/schemas/flux/compose.d.ts +307 -44
- package/dist/schemas/flux/compose.d.ts.map +1 -1
- package/dist/schemas/flux/compose.js +74 -48
- package/dist/schemas/flux/compose.js.map +1 -1
- package/dist/schemas/flux/container.d.ts +423 -56
- package/dist/schemas/flux/container.d.ts.map +1 -1
- package/dist/schemas/flux/container.js +83 -61
- package/dist/schemas/flux/container.js.map +1 -1
- package/dist/schemas/flux/docker.d.ts +254 -37
- package/dist/schemas/flux/docker.d.ts.map +1 -1
- package/dist/schemas/flux/docker.js +69 -39
- package/dist/schemas/flux/docker.js.map +1 -1
- package/dist/schemas/flux/host.d.ts +312 -29
- package/dist/schemas/flux/host.d.ts.map +1 -1
- package/dist/schemas/flux/host.js +74 -31
- package/dist/schemas/flux/host.js.map +1 -1
- package/dist/schemas/flux/index.d.ts +503 -11
- package/dist/schemas/flux/index.d.ts.map +1 -1
- package/dist/schemas/flux/index.js +34 -70
- package/dist/schemas/flux/index.js.map +1 -1
- package/dist/schemas/host-config.d.ts +76 -0
- package/dist/schemas/host-config.d.ts.map +1 -0
- package/dist/schemas/host-config.js +105 -0
- package/dist/schemas/host-config.js.map +1 -0
- package/dist/schemas/scout/index.d.ts +80 -23
- package/dist/schemas/scout/index.d.ts.map +1 -1
- package/dist/schemas/scout/index.js +26 -11
- package/dist/schemas/scout/index.js.map +1 -1
- package/dist/schemas/scout/logs.d.ts +17 -5
- package/dist/schemas/scout/logs.d.ts.map +1 -1
- package/dist/schemas/scout/logs.js +41 -31
- package/dist/schemas/scout/logs.js.map +1 -1
- package/dist/schemas/scout/simple.d.ts +126 -11
- package/dist/schemas/scout/simple.d.ts.map +1 -1
- package/dist/schemas/scout/simple.js +112 -57
- package/dist/schemas/scout/simple.js.map +1 -1
- package/dist/schemas/scout/zfs.d.ts +17 -5
- package/dist/schemas/scout/zfs.d.ts.map +1 -1
- package/dist/schemas/scout/zfs.js +34 -25
- package/dist/schemas/scout/zfs.js.map +1 -1
- package/dist/services/cache-layer.d.ts +160 -0
- package/dist/services/cache-layer.d.ts.map +1 -0
- package/dist/services/cache-layer.js +138 -0
- package/dist/services/cache-layer.js.map +1 -0
- package/dist/services/compose-cache.d.ts +75 -0
- package/dist/services/compose-cache.d.ts.map +1 -0
- package/dist/services/compose-cache.js +178 -0
- package/dist/services/compose-cache.js.map +1 -0
- package/dist/services/compose-discovery.d.ts +46 -0
- package/dist/services/compose-discovery.d.ts.map +1 -0
- package/dist/services/compose-discovery.js +219 -0
- package/dist/services/compose-discovery.js.map +1 -0
- package/dist/services/compose-project-lister.d.ts +27 -0
- package/dist/services/compose-project-lister.d.ts.map +1 -0
- package/dist/services/compose-project-lister.js +71 -0
- package/dist/services/compose-project-lister.js.map +1 -0
- package/dist/services/compose-scanner.d.ts +63 -0
- package/dist/services/compose-scanner.d.ts.map +1 -0
- package/dist/services/compose-scanner.js +253 -0
- package/dist/services/compose-scanner.js.map +1 -0
- package/dist/services/compose.d.ts +64 -28
- package/dist/services/compose.d.ts.map +1 -1
- package/dist/services/compose.js +220 -98
- package/dist/services/compose.js.map +1 -1
- package/dist/services/config-loader.d.ts +23 -0
- package/dist/services/config-loader.d.ts.map +1 -0
- package/dist/services/config-loader.js +124 -0
- package/dist/services/config-loader.js.map +1 -0
- package/dist/services/config-service.d.ts +38 -0
- package/dist/services/config-service.d.ts.map +1 -0
- package/dist/services/config-service.js +225 -0
- package/dist/services/config-service.js.map +1 -0
- package/dist/services/container-host-map-cache.d.ts +121 -0
- package/dist/services/container-host-map-cache.d.ts.map +1 -0
- package/dist/services/container-host-map-cache.js +188 -0
- package/dist/services/container-host-map-cache.js.map +1 -0
- package/dist/services/container.d.ts +194 -6
- package/dist/services/container.d.ts.map +1 -1
- package/dist/services/container.js +386 -11
- package/dist/services/container.js.map +1 -1
- package/dist/services/diagnostics.d.ts +57 -0
- package/dist/services/diagnostics.d.ts.map +1 -0
- package/dist/services/diagnostics.js +271 -0
- package/dist/services/diagnostics.js.map +1 -0
- package/dist/services/docker/container-service.d.ts +123 -0
- package/dist/services/docker/container-service.d.ts.map +1 -0
- package/dist/services/docker/container-service.js +347 -0
- package/dist/services/docker/container-service.js.map +1 -0
- package/dist/services/docker/image-service.d.ts +82 -0
- package/dist/services/docker/image-service.d.ts.map +1 -0
- package/dist/services/docker/image-service.js +193 -0
- package/dist/services/docker/image-service.js.map +1 -0
- package/dist/services/docker/index.d.ts +80 -0
- package/dist/services/docker/index.d.ts.map +1 -0
- package/dist/services/docker/index.js +103 -0
- package/dist/services/docker/index.js.map +1 -0
- package/dist/services/docker/network-service.d.ts +22 -0
- package/dist/services/docker/network-service.d.ts.map +1 -0
- package/dist/services/docker/network-service.js +43 -0
- package/dist/services/docker/network-service.js.map +1 -0
- package/dist/services/docker/system-service.d.ts +49 -0
- package/dist/services/docker/system-service.d.ts.map +1 -0
- package/dist/services/docker/system-service.js +215 -0
- package/dist/services/docker/system-service.js.map +1 -0
- package/dist/services/docker/utils/client-factory.d.ts +56 -0
- package/dist/services/docker/utils/client-factory.d.ts.map +1 -0
- package/dist/services/docker/utils/client-factory.js +139 -0
- package/dist/services/docker/utils/client-factory.js.map +1 -0
- package/dist/services/docker/utils/client-manager.d.ts +88 -0
- package/dist/services/docker/utils/client-manager.d.ts.map +1 -0
- package/dist/services/docker/utils/client-manager.js +124 -0
- package/dist/services/docker/utils/client-manager.js.map +1 -0
- package/dist/services/docker/utils/exec-handler.d.ts +94 -0
- package/dist/services/docker/utils/exec-handler.d.ts.map +1 -0
- package/dist/services/docker/utils/exec-handler.js +197 -0
- package/dist/services/docker/utils/exec-handler.js.map +1 -0
- package/dist/services/docker/utils/formatters.d.ts +13 -0
- package/dist/services/docker/utils/formatters.d.ts.map +1 -0
- package/dist/services/docker/utils/formatters.js +33 -0
- package/dist/services/docker/utils/formatters.js.map +1 -0
- package/dist/services/docker/utils/log-parser.d.ts +10 -0
- package/dist/services/docker/utils/log-parser.d.ts.map +1 -0
- package/dist/services/docker/utils/log-parser.js +48 -0
- package/dist/services/docker/utils/log-parser.js.map +1 -0
- package/dist/services/docker/utils/stats-calculator.d.ts +68 -0
- package/dist/services/docker/utils/stats-calculator.d.ts.map +1 -0
- package/dist/services/docker/utils/stats-calculator.js +61 -0
- package/dist/services/docker/utils/stats-calculator.js.map +1 -0
- package/dist/services/docker/volume-service.d.ts +22 -0
- package/dist/services/docker/volume-service.d.ts.map +1 -0
- package/dist/services/docker/volume-service.js +48 -0
- package/dist/services/docker/volume-service.js.map +1 -0
- package/dist/services/docker-interfaces.d.ts +283 -0
- package/dist/services/docker-interfaces.d.ts.map +1 -0
- package/dist/services/docker-interfaces.js +13 -0
- package/dist/services/docker-interfaces.js.map +1 -0
- package/dist/services/docker.d.ts +42 -5
- package/dist/services/docker.d.ts.map +1 -1
- package/dist/services/docker.js +335 -127
- package/dist/services/docker.js.map +1 -1
- package/dist/services/file-service.d.ts +6 -2
- package/dist/services/file-service.d.ts.map +1 -1
- package/dist/services/file-service.js +156 -52
- package/dist/services/file-service.js.map +1 -1
- package/dist/services/host-config-repository.d.ts +133 -0
- package/dist/services/host-config-repository.d.ts.map +1 -0
- package/dist/services/host-config-repository.js +323 -0
- package/dist/services/host-config-repository.js.map +1 -0
- package/dist/services/host-resolver.d.ts +49 -0
- package/dist/services/host-resolver.d.ts.map +1 -0
- package/dist/services/host-resolver.js +176 -0
- package/dist/services/host-resolver.js.map +1 -0
- package/dist/services/interfaces.d.ts +61 -194
- package/dist/services/interfaces.d.ts.map +1 -1
- package/dist/services/local-executor.d.ts +31 -0
- package/dist/services/local-executor.d.ts.map +1 -0
- package/dist/services/local-executor.js +71 -0
- package/dist/services/local-executor.js.map +1 -0
- package/dist/services/ssh-config-loader.d.ts +35 -0
- package/dist/services/ssh-config-loader.d.ts.map +1 -0
- package/dist/services/ssh-config-loader.js +218 -0
- package/dist/services/ssh-config-loader.js.map +1 -0
- package/dist/services/ssh-pool.d.ts +26 -1
- package/dist/services/ssh-pool.d.ts.map +1 -1
- package/dist/services/ssh-pool.js +166 -25
- package/dist/services/ssh-pool.js.map +1 -1
- package/dist/services/ssh-service.d.ts +3 -0
- package/dist/services/ssh-service.d.ts.map +1 -1
- package/dist/services/ssh-service.js +53 -31
- package/dist/services/ssh-service.js.map +1 -1
- package/dist/services/ssh.d.ts +2 -6
- package/dist/services/ssh.d.ts.map +1 -1
- package/dist/services/ssh.js +9 -40
- package/dist/services/ssh.js.map +1 -1
- package/dist/tools/definitions/flux.d.ts +13 -0
- package/dist/tools/definitions/flux.d.ts.map +1 -0
- package/dist/tools/definitions/flux.js +101 -0
- package/dist/tools/definitions/flux.js.map +1 -0
- package/dist/tools/definitions/index.d.ts +8 -0
- package/dist/tools/definitions/index.d.ts.map +1 -0
- package/dist/tools/definitions/index.js +8 -0
- package/dist/tools/definitions/index.js.map +1 -0
- package/dist/tools/definitions/scout.d.ts +13 -0
- package/dist/tools/definitions/scout.d.ts.map +1 -0
- package/dist/tools/definitions/scout.js +78 -0
- package/dist/tools/definitions/scout.js.map +1 -0
- package/dist/tools/flux.d.ts +16 -8
- package/dist/tools/flux.d.ts.map +1 -1
- package/dist/tools/flux.js +27 -66
- package/dist/tools/flux.js.map +1 -1
- package/dist/tools/handlers/base-handler.d.ts +172 -0
- package/dist/tools/handlers/base-handler.d.ts.map +1 -0
- package/dist/tools/handlers/base-handler.js +234 -0
- package/dist/tools/handlers/base-handler.js.map +1 -0
- package/dist/tools/handlers/compose-handlers.d.ts +108 -0
- package/dist/tools/handlers/compose-handlers.d.ts.map +1 -0
- package/dist/tools/handlers/compose-handlers.js +293 -0
- package/dist/tools/handlers/compose-handlers.js.map +1 -0
- package/dist/tools/handlers/compose-utils.d.ts +35 -0
- package/dist/tools/handlers/compose-utils.d.ts.map +1 -0
- package/dist/tools/handlers/compose-utils.js +76 -0
- package/dist/tools/handlers/compose-utils.js.map +1 -0
- package/dist/tools/handlers/compose.d.ts +23 -0
- package/dist/tools/handlers/compose.d.ts.map +1 -0
- package/dist/tools/handlers/compose.js +125 -0
- package/dist/tools/handlers/compose.js.map +1 -0
- package/dist/tools/handlers/container.d.ts +23 -0
- package/dist/tools/handlers/container.d.ts.map +1 -0
- package/dist/tools/handlers/container.js +333 -0
- package/dist/tools/handlers/container.js.map +1 -0
- package/dist/tools/handlers/docker.d.ts +24 -0
- package/dist/tools/handlers/docker.d.ts.map +1 -0
- package/dist/tools/handlers/docker.js +155 -0
- package/dist/tools/handlers/docker.js.map +1 -0
- package/dist/tools/handlers/host.d.ts +23 -0
- package/dist/tools/handlers/host.d.ts.map +1 -0
- package/dist/tools/handlers/host.js +196 -0
- package/dist/tools/handlers/host.js.map +1 -0
- package/dist/tools/handlers/scout-logs.d.ts +24 -0
- package/dist/tools/handlers/scout-logs.d.ts.map +1 -0
- package/dist/tools/handlers/scout-logs.js +119 -0
- package/dist/tools/handlers/scout-logs.js.map +1 -0
- package/dist/tools/handlers/scout-simple.d.ts +23 -0
- package/dist/tools/handlers/scout-simple.d.ts.map +1 -0
- package/dist/tools/handlers/scout-simple.js +286 -0
- package/dist/tools/handlers/scout-simple.js.map +1 -0
- package/dist/tools/handlers/scout-zfs.d.ts +23 -0
- package/dist/tools/handlers/scout-zfs.d.ts.map +1 -0
- package/dist/tools/handlers/scout-zfs.js +82 -0
- package/dist/tools/handlers/scout-zfs.js.map +1 -0
- package/dist/tools/index.d.ts +32 -2
- package/dist/tools/index.d.ts.map +1 -1
- package/dist/tools/index.js +41 -35
- package/dist/tools/index.js.map +1 -1
- package/dist/tools/registry.d.ts +135 -0
- package/dist/tools/registry.d.ts.map +1 -0
- package/dist/tools/registry.js +151 -0
- package/dist/tools/registry.js.map +1 -0
- package/dist/tools/scout.d.ts +16 -8
- package/dist/tools/scout.d.ts.map +1 -1
- package/dist/tools/scout.js +36 -78
- package/dist/tools/scout.js.map +1 -1
- package/dist/types.d.ts +629 -1
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js.map +1 -1
- package/dist/utils/command-security.d.ts +82 -0
- package/dist/utils/command-security.d.ts.map +1 -0
- package/dist/utils/command-security.js +122 -0
- package/dist/utils/command-security.js.map +1 -0
- package/dist/utils/error-sanitization.d.ts +77 -0
- package/dist/utils/error-sanitization.d.ts.map +1 -0
- package/dist/utils/error-sanitization.js +107 -0
- package/dist/utils/error-sanitization.js.map +1 -0
- package/dist/utils/errors.d.ts +30 -6
- package/dist/utils/errors.d.ts.map +1 -1
- package/dist/utils/errors.js +91 -12
- package/dist/utils/errors.js.map +1 -1
- package/dist/utils/help-handler.d.ts +23 -0
- package/dist/utils/help-handler.d.ts.map +1 -0
- package/dist/utils/help-handler.js +21 -0
- package/dist/utils/help-handler.js.map +1 -0
- package/dist/utils/help.d.ts +1 -1
- package/dist/utils/help.d.ts.map +1 -1
- package/dist/utils/help.js +57 -16
- package/dist/utils/help.js.map +1 -1
- package/dist/utils/host-utils.d.ts +31 -0
- package/dist/utils/host-utils.d.ts.map +1 -0
- package/dist/utils/host-utils.js +80 -0
- package/dist/utils/host-utils.js.map +1 -0
- package/dist/utils/index.d.ts +8 -2
- package/dist/utils/index.d.ts.map +1 -1
- package/dist/utils/index.js +8 -2
- package/dist/utils/index.js.map +1 -1
- package/dist/utils/init-detection.d.ts +36 -0
- package/dist/utils/init-detection.d.ts.map +1 -0
- package/dist/utils/init-detection.js +79 -0
- package/dist/utils/init-detection.js.map +1 -0
- package/dist/utils/logger.d.ts +11 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/logger.js +32 -0
- package/dist/utils/logger.js.map +1 -0
- package/dist/utils/pagination.d.ts +20 -0
- package/dist/utils/pagination.d.ts.map +1 -0
- package/dist/utils/pagination.js +29 -0
- package/dist/utils/pagination.js.map +1 -0
- package/dist/utils/path-security.d.ts +132 -18
- package/dist/utils/path-security.d.ts.map +1 -1
- package/dist/utils/path-security.js +164 -35
- package/dist/utils/path-security.js.map +1 -1
- package/dist/utils/sorting.d.ts +33 -0
- package/dist/utils/sorting.d.ts.map +1 -0
- package/dist/utils/sorting.js +57 -0
- package/dist/utils/sorting.js.map +1 -0
- package/dist/utils/text-filters.d.ts +13 -0
- package/dist/utils/text-filters.d.ts.map +1 -0
- package/dist/utils/text-filters.js +18 -0
- package/dist/utils/text-filters.js.map +1 -0
- package/dist/utils/time.d.ts +11 -0
- package/dist/utils/time.d.ts.map +1 -0
- package/dist/utils/time.js +13 -0
- package/dist/utils/time.js.map +1 -0
- package/dist/utils/validation.d.ts +25 -0
- package/dist/utils/validation.d.ts.map +1 -0
- package/dist/utils/validation.js +56 -0
- package/dist/utils/validation.js.map +1 -0
- package/package.json +45 -19
- package/dist/schemas/discriminator.d.ts +0 -20
- package/dist/schemas/discriminator.d.ts.map +0 -1
- package/dist/schemas/discriminator.js +0 -25
- package/dist/schemas/discriminator.js.map +0 -1
- package/dist/schemas/unified.d.ts +0 -674
- package/dist/schemas/unified.d.ts.map +0 -1
- package/dist/schemas/unified.js +0 -453
- package/dist/schemas/unified.js.map +0 -1
- package/dist/tools/unified.d.ts +0 -7
- package/dist/tools/unified.d.ts.map +0 -1
- package/dist/tools/unified.js +0 -827
- package/dist/tools/unified.js.map +0 -1
|
@@ -0,0 +1,347 @@
|
|
|
1
|
+
import { DEFAULT_EXEC_MAX_BUFFER, DEFAULT_EXEC_TIMEOUT } from "../../constants.js";
|
|
2
|
+
import { logError } from "../../utils/errors.js";
|
|
3
|
+
import { narrowToDefaultHost } from "../../utils/host-utils.js";
|
|
4
|
+
import { applyPagination } from "../../utils/pagination.js";
|
|
5
|
+
import { createStreamContext, executeWithTimeout, setupExecInstance, } from "./utils/exec-handler.js";
|
|
6
|
+
import { parseDockerLogs, parseTimeSpec } from "./utils/log-parser.js";
|
|
7
|
+
/**
|
|
8
|
+
* Service for Docker container operations.
|
|
9
|
+
* Handles container lifecycle, monitoring, and execution.
|
|
10
|
+
*/
|
|
11
|
+
export class ContainerService {
|
|
12
|
+
clientManager;
|
|
13
|
+
constructor(clientManager) {
|
|
14
|
+
this.clientManager = clientManager;
|
|
15
|
+
}
|
|
16
|
+
matchesContainerIdentifier(container, containerId) {
|
|
17
|
+
const query = containerId.trim();
|
|
18
|
+
if (!query)
|
|
19
|
+
return false;
|
|
20
|
+
if (container.Id.startsWith(query))
|
|
21
|
+
return true;
|
|
22
|
+
const normalizedQuery = query.replace(/^\//, "");
|
|
23
|
+
const names = Array.isArray(container.Names) ? container.Names : [];
|
|
24
|
+
return names.some((name) => name.replace(/^\//, "") === normalizedQuery);
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* List containers across multiple hosts with filtering and pagination.
|
|
28
|
+
*
|
|
29
|
+
* @param hosts - List of Docker hosts to query
|
|
30
|
+
* @param options - Filtering and pagination options
|
|
31
|
+
* @param options.state - Filter by container state
|
|
32
|
+
* @param options.nameFilter - Filter by container name (partial match)
|
|
33
|
+
* @param options.imageFilter - Filter by image name (partial match)
|
|
34
|
+
* @param options.labelFilter - Filter by label (format: "key=value")
|
|
35
|
+
* @param options.limit - Maximum number of containers to return
|
|
36
|
+
* @param options.offset - Number of containers to skip before returning results
|
|
37
|
+
* @returns Promise resolving to array of container information
|
|
38
|
+
*/
|
|
39
|
+
async listContainers(hosts, options = {}) {
|
|
40
|
+
const targetHosts = narrowToDefaultHost(hosts);
|
|
41
|
+
// Query all hosts in parallel using Promise.allSettled
|
|
42
|
+
const results = await Promise.allSettled(targetHosts.map((host) => this.listContainersOnHost(host, options)));
|
|
43
|
+
// Collect results from successful queries, log failures
|
|
44
|
+
const containers = [];
|
|
45
|
+
for (let i = 0; i < results.length; i++) {
|
|
46
|
+
const result = results[i];
|
|
47
|
+
if (result.status === "fulfilled") {
|
|
48
|
+
containers.push(...result.value);
|
|
49
|
+
}
|
|
50
|
+
else {
|
|
51
|
+
logError(result.reason, {
|
|
52
|
+
operation: "listContainers",
|
|
53
|
+
metadata: { host: targetHosts[i].name },
|
|
54
|
+
});
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
// Apply pagination using shared utility
|
|
58
|
+
return applyPagination(containers, options.offset, options.limit);
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* List containers on a single host (internal helper).
|
|
62
|
+
*/
|
|
63
|
+
async listContainersOnHost(host, options) {
|
|
64
|
+
const docker = await this.clientManager.getClient(host);
|
|
65
|
+
const listOptions = {
|
|
66
|
+
all: options.state !== "running",
|
|
67
|
+
};
|
|
68
|
+
// Add label filter if specified
|
|
69
|
+
if (options.labelFilter) {
|
|
70
|
+
listOptions.filters = { label: [options.labelFilter] };
|
|
71
|
+
}
|
|
72
|
+
const containers = await docker.listContainers(listOptions);
|
|
73
|
+
const results = [];
|
|
74
|
+
for (const c of containers) {
|
|
75
|
+
const containerState = c.State?.toLowerCase();
|
|
76
|
+
// Apply state filter
|
|
77
|
+
if (options.state && options.state !== "all") {
|
|
78
|
+
if (options.state === "stopped" && containerState !== "exited")
|
|
79
|
+
continue;
|
|
80
|
+
if (options.state === "paused" && containerState !== "paused")
|
|
81
|
+
continue;
|
|
82
|
+
if (options.state === "running" && containerState !== "running")
|
|
83
|
+
continue;
|
|
84
|
+
}
|
|
85
|
+
const names = Array.isArray(c.Names) ? c.Names : [];
|
|
86
|
+
const name = names[0]?.replace(/^\//, "") || c.Id.slice(0, 12);
|
|
87
|
+
// Apply name filter
|
|
88
|
+
if (options.nameFilter && !name.toLowerCase().includes(options.nameFilter.toLowerCase())) {
|
|
89
|
+
continue;
|
|
90
|
+
}
|
|
91
|
+
// Apply image filter
|
|
92
|
+
if (options.imageFilter &&
|
|
93
|
+
!c.Image.toLowerCase().includes(options.imageFilter.toLowerCase())) {
|
|
94
|
+
continue;
|
|
95
|
+
}
|
|
96
|
+
results.push({
|
|
97
|
+
id: c.Id,
|
|
98
|
+
name,
|
|
99
|
+
image: c.Image,
|
|
100
|
+
state: containerState,
|
|
101
|
+
status: c.Status,
|
|
102
|
+
created: new Date(c.Created * 1000).toISOString(),
|
|
103
|
+
ports: (c.Ports || []).map((p) => ({
|
|
104
|
+
containerPort: p.PrivatePort,
|
|
105
|
+
hostPort: p.PublicPort,
|
|
106
|
+
protocol: p.Type,
|
|
107
|
+
hostIp: p.IP,
|
|
108
|
+
})),
|
|
109
|
+
labels: c.Labels || {},
|
|
110
|
+
hostName: host.name,
|
|
111
|
+
});
|
|
112
|
+
}
|
|
113
|
+
return results;
|
|
114
|
+
}
|
|
115
|
+
/**
|
|
116
|
+
* Find which host a container is on.
|
|
117
|
+
* Performs parallel scan across hosts for optimal performance.
|
|
118
|
+
*
|
|
119
|
+
* Note: For cache-optimized lookups, use DockerService.findContainerHost() with
|
|
120
|
+
* ContainerHostMapCache instead. The cache requires client-provider capability
|
|
121
|
+
* and is integrated at the facade level.
|
|
122
|
+
*
|
|
123
|
+
* @param containerId - Container ID, name, or ID prefix
|
|
124
|
+
* @param hosts - List of hosts to search
|
|
125
|
+
* @returns Host and container info if found, null otherwise
|
|
126
|
+
*/
|
|
127
|
+
async findContainerHost(containerId, hosts) {
|
|
128
|
+
if (hosts.length === 0) {
|
|
129
|
+
return null;
|
|
130
|
+
}
|
|
131
|
+
// Parallel scan across hosts with early return: resolve immediately when found.
|
|
132
|
+
return new Promise((resolve) => {
|
|
133
|
+
let completed = 0;
|
|
134
|
+
let settled = false;
|
|
135
|
+
const finishIfDone = () => {
|
|
136
|
+
completed += 1;
|
|
137
|
+
if (!settled && completed === hosts.length) {
|
|
138
|
+
settled = true;
|
|
139
|
+
resolve(null);
|
|
140
|
+
}
|
|
141
|
+
};
|
|
142
|
+
for (const host of hosts) {
|
|
143
|
+
void (async () => {
|
|
144
|
+
try {
|
|
145
|
+
const docker = await this.clientManager.getClient(host);
|
|
146
|
+
const containers = await docker.listContainers({ all: true });
|
|
147
|
+
const found = containers.find((container) => this.matchesContainerIdentifier(container, containerId));
|
|
148
|
+
if (found && !settled) {
|
|
149
|
+
settled = true;
|
|
150
|
+
resolve({ host, container: found });
|
|
151
|
+
return;
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
catch (error) {
|
|
155
|
+
// Log errors but continue searching other hosts
|
|
156
|
+
logError(error, { metadata: { containerId } });
|
|
157
|
+
}
|
|
158
|
+
finally {
|
|
159
|
+
finishIfDone();
|
|
160
|
+
}
|
|
161
|
+
})();
|
|
162
|
+
}
|
|
163
|
+
});
|
|
164
|
+
}
|
|
165
|
+
/**
|
|
166
|
+
* Perform action on container.
|
|
167
|
+
*
|
|
168
|
+
* @param containerId - Container ID or name
|
|
169
|
+
* @param action - Action to perform
|
|
170
|
+
* @param host - Host configuration
|
|
171
|
+
*/
|
|
172
|
+
async containerAction(containerId, action, host) {
|
|
173
|
+
const container = await this.getContainer(containerId, host);
|
|
174
|
+
switch (action) {
|
|
175
|
+
case "start":
|
|
176
|
+
await container.start();
|
|
177
|
+
break;
|
|
178
|
+
case "stop":
|
|
179
|
+
await container.stop({ t: 10 });
|
|
180
|
+
break;
|
|
181
|
+
case "restart":
|
|
182
|
+
await container.restart({ t: 10 });
|
|
183
|
+
break;
|
|
184
|
+
case "pause":
|
|
185
|
+
await container.pause();
|
|
186
|
+
break;
|
|
187
|
+
case "unpause":
|
|
188
|
+
await container.unpause();
|
|
189
|
+
break;
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
/**
|
|
193
|
+
* Get container by ID or name.
|
|
194
|
+
*/
|
|
195
|
+
async getContainer(containerId, host) {
|
|
196
|
+
const docker = await this.clientManager.getClient(host);
|
|
197
|
+
return docker.getContainer(containerId);
|
|
198
|
+
}
|
|
199
|
+
/**
|
|
200
|
+
* Get container logs.
|
|
201
|
+
*
|
|
202
|
+
* @param containerId - Container ID or name
|
|
203
|
+
* @param host - Host configuration
|
|
204
|
+
* @param options - Log filtering options
|
|
205
|
+
* @returns Promise resolving to array of log entries
|
|
206
|
+
*/
|
|
207
|
+
async getContainerLogs(containerId, host, options = {}) {
|
|
208
|
+
const container = await this.getContainer(containerId, host);
|
|
209
|
+
const logOptions = {
|
|
210
|
+
stdout: options.stream !== "stderr",
|
|
211
|
+
stderr: options.stream !== "stdout",
|
|
212
|
+
tail: options.lines || 100,
|
|
213
|
+
timestamps: true,
|
|
214
|
+
follow: false,
|
|
215
|
+
};
|
|
216
|
+
if (options.since) {
|
|
217
|
+
logOptions.since = parseTimeSpec(options.since);
|
|
218
|
+
}
|
|
219
|
+
if (options.until) {
|
|
220
|
+
logOptions.until = parseTimeSpec(options.until);
|
|
221
|
+
}
|
|
222
|
+
const logs = await container.logs(logOptions);
|
|
223
|
+
return parseDockerLogs(logs.toString());
|
|
224
|
+
}
|
|
225
|
+
/**
|
|
226
|
+
* Get container stats.
|
|
227
|
+
*
|
|
228
|
+
* @param containerId - Container ID or name
|
|
229
|
+
* @param host - Host configuration
|
|
230
|
+
* @param containerName - Optional container name (avoids redundant inspect() call)
|
|
231
|
+
* @returns Promise resolving to container resource usage stats
|
|
232
|
+
*/
|
|
233
|
+
async getContainerStats(containerId, host, containerName) {
|
|
234
|
+
const container = await this.getContainer(containerId, host);
|
|
235
|
+
const stats = await container.stats({ stream: false });
|
|
236
|
+
// Calculate CPU percentage
|
|
237
|
+
const cpuDelta = stats.cpu_stats.cpu_usage.total_usage - stats.precpu_stats.cpu_usage.total_usage;
|
|
238
|
+
const systemDelta = stats.cpu_stats.system_cpu_usage - stats.precpu_stats.system_cpu_usage;
|
|
239
|
+
const cpuCount = stats.cpu_stats.online_cpus || 1;
|
|
240
|
+
const cpuPercent = systemDelta > 0 ? (cpuDelta / systemDelta) * cpuCount * 100 : 0;
|
|
241
|
+
// Memory stats
|
|
242
|
+
const memUsage = stats.memory_stats.usage || 0;
|
|
243
|
+
const memLimit = stats.memory_stats.limit || 1;
|
|
244
|
+
const memPercent = (memUsage / memLimit) * 100;
|
|
245
|
+
// Network stats
|
|
246
|
+
let netRx = 0, netTx = 0;
|
|
247
|
+
if (stats.networks) {
|
|
248
|
+
for (const net of Object.values(stats.networks)) {
|
|
249
|
+
netRx += net.rx_bytes || 0;
|
|
250
|
+
netTx += net.tx_bytes || 0;
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
// Block I/O
|
|
254
|
+
let blockRead = 0, blockWrite = 0;
|
|
255
|
+
if (stats.blkio_stats?.io_service_bytes_recursive) {
|
|
256
|
+
for (const entry of stats.blkio_stats.io_service_bytes_recursive) {
|
|
257
|
+
if (entry.op === "read")
|
|
258
|
+
blockRead += entry.value;
|
|
259
|
+
if (entry.op === "write")
|
|
260
|
+
blockWrite += entry.value;
|
|
261
|
+
}
|
|
262
|
+
}
|
|
263
|
+
// Use provided name if available, otherwise fetch via inspect()
|
|
264
|
+
// This eliminates 1 API call per container when name is known (50% reduction)
|
|
265
|
+
let finalName;
|
|
266
|
+
if (containerName) {
|
|
267
|
+
finalName = containerName;
|
|
268
|
+
}
|
|
269
|
+
else {
|
|
270
|
+
const info = await container.inspect();
|
|
271
|
+
finalName = info.Name.replace(/^\//, "");
|
|
272
|
+
}
|
|
273
|
+
return {
|
|
274
|
+
containerId,
|
|
275
|
+
containerName: finalName,
|
|
276
|
+
cpuPercent: Math.round(cpuPercent * 100) / 100,
|
|
277
|
+
memoryUsage: memUsage,
|
|
278
|
+
memoryLimit: memLimit,
|
|
279
|
+
memoryPercent: Math.round(memPercent * 100) / 100,
|
|
280
|
+
networkRx: netRx,
|
|
281
|
+
networkTx: netTx,
|
|
282
|
+
blockRead,
|
|
283
|
+
blockWrite,
|
|
284
|
+
};
|
|
285
|
+
}
|
|
286
|
+
/**
|
|
287
|
+
* Execute a command inside a container.
|
|
288
|
+
*
|
|
289
|
+
* @param containerId - Container ID or name
|
|
290
|
+
* @param host - Host configuration
|
|
291
|
+
* @param options - Execution options
|
|
292
|
+
* @param options.command - Shell command to execute
|
|
293
|
+
* @param options.user - Optional user to run as
|
|
294
|
+
* @param options.workdir - Optional working directory
|
|
295
|
+
* @param options.timeout - Optional timeout in ms (default 30s, max 5min)
|
|
296
|
+
* @returns Promise resolving to stdout, stderr, and exit code
|
|
297
|
+
* @throws Error if timeout exceeded or buffer limit exceeded
|
|
298
|
+
*/
|
|
299
|
+
async execContainer(containerId, host, options) {
|
|
300
|
+
const container = await this.getContainer(containerId, host);
|
|
301
|
+
const timeout = options.timeout ?? DEFAULT_EXEC_TIMEOUT;
|
|
302
|
+
const maxBuffer = DEFAULT_EXEC_MAX_BUFFER;
|
|
303
|
+
const exec = await setupExecInstance(container, options);
|
|
304
|
+
const docker = await this.clientManager.getClient(host);
|
|
305
|
+
const context = await createStreamContext(exec, docker.modem, maxBuffer);
|
|
306
|
+
try {
|
|
307
|
+
await executeWithTimeout(context, timeout, maxBuffer);
|
|
308
|
+
const inspection = await exec.inspect();
|
|
309
|
+
return {
|
|
310
|
+
stdout: Buffer.concat(context.stdoutChunks).toString().trimEnd(),
|
|
311
|
+
stderr: Buffer.concat(context.stderrChunks).toString().trimEnd(),
|
|
312
|
+
exitCode: inspection.ExitCode ?? 0,
|
|
313
|
+
};
|
|
314
|
+
}
|
|
315
|
+
catch (error) {
|
|
316
|
+
context.cleanup();
|
|
317
|
+
throw error;
|
|
318
|
+
}
|
|
319
|
+
}
|
|
320
|
+
/**
|
|
321
|
+
* List running processes inside a container.
|
|
322
|
+
*
|
|
323
|
+
* @param containerId - Container ID or name
|
|
324
|
+
* @param host - Host configuration
|
|
325
|
+
* @returns Promise resolving to process list with titles and data
|
|
326
|
+
*/
|
|
327
|
+
async getContainerProcesses(containerId, host) {
|
|
328
|
+
const container = await this.getContainer(containerId, host);
|
|
329
|
+
const result = await container.top();
|
|
330
|
+
return {
|
|
331
|
+
titles: result.Titles ?? [],
|
|
332
|
+
processes: result.Processes ?? [],
|
|
333
|
+
};
|
|
334
|
+
}
|
|
335
|
+
/**
|
|
336
|
+
* Inspect a container to get detailed information.
|
|
337
|
+
*
|
|
338
|
+
* @param containerId - Container ID or name
|
|
339
|
+
* @param host - Host configuration
|
|
340
|
+
* @returns Promise resolving to Docker container inspection data
|
|
341
|
+
*/
|
|
342
|
+
async inspectContainer(containerId, host) {
|
|
343
|
+
const container = await this.getContainer(containerId, host);
|
|
344
|
+
return container.inspect();
|
|
345
|
+
}
|
|
346
|
+
}
|
|
347
|
+
//# sourceMappingURL=container-service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"container-service.js","sourceRoot":"","sources":["../../../src/services/docker/container-service.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
import type { HostConfig, ImageInfo, ListImagesOptions } from "../../types.js";
|
|
2
|
+
import type { ClientManager } from "./utils/client-manager.js";
|
|
3
|
+
/**
|
|
4
|
+
* Service for Docker image operations.
|
|
5
|
+
* Handles image lifecycle, pulling, building, and management.
|
|
6
|
+
*/
|
|
7
|
+
export declare class ImageService {
|
|
8
|
+
private clientManager;
|
|
9
|
+
constructor(clientManager: ClientManager);
|
|
10
|
+
/**
|
|
11
|
+
* List images across multiple hosts with optional filtering.
|
|
12
|
+
*
|
|
13
|
+
* @param hosts - List of Docker hosts to query
|
|
14
|
+
* @param options - Filtering options (danglingOnly)
|
|
15
|
+
* @returns Promise resolving to array of image information
|
|
16
|
+
*/
|
|
17
|
+
listImages(hosts: HostConfig[], options?: ListImagesOptions): Promise<ImageInfo[]>;
|
|
18
|
+
/**
|
|
19
|
+
* List images from a single host (internal helper).
|
|
20
|
+
*/
|
|
21
|
+
private listImagesOnHost;
|
|
22
|
+
/**
|
|
23
|
+
* Pull an image from a registry.
|
|
24
|
+
*
|
|
25
|
+
* @param imageName - Image name with optional tag (e.g., "nginx:latest")
|
|
26
|
+
* @param host - Host configuration
|
|
27
|
+
* @returns Promise resolving to pull status
|
|
28
|
+
* @throws Error if image name is empty or pull fails
|
|
29
|
+
*/
|
|
30
|
+
pullImage(imageName: string, host: HostConfig): Promise<{
|
|
31
|
+
status: string;
|
|
32
|
+
}>;
|
|
33
|
+
/**
|
|
34
|
+
* Remove an image from a host.
|
|
35
|
+
*
|
|
36
|
+
* @param imageId - Image ID or tag
|
|
37
|
+
* @param host - Host configuration
|
|
38
|
+
* @param options - Remove options (force)
|
|
39
|
+
* @returns Promise resolving to removal status
|
|
40
|
+
*/
|
|
41
|
+
removeImage(imageId: string, host: HostConfig, options?: {
|
|
42
|
+
force?: boolean;
|
|
43
|
+
}): Promise<{
|
|
44
|
+
status: string;
|
|
45
|
+
}>;
|
|
46
|
+
/**
|
|
47
|
+
* Build an image from a Dockerfile (SSH-based for remote hosts).
|
|
48
|
+
*
|
|
49
|
+
* SECURITY: Implements path traversal protection (CWE-22)
|
|
50
|
+
* - Requires absolute paths for context and dockerfile
|
|
51
|
+
* - Rejects any path containing .. or . components
|
|
52
|
+
* - Validates character set to prevent injection
|
|
53
|
+
*
|
|
54
|
+
* @param host - Docker host configuration
|
|
55
|
+
* @param options - Build options (context, tag, dockerfile, noCache)
|
|
56
|
+
* @returns Promise resolving to build status
|
|
57
|
+
* @throws Error if paths contain directory traversal or invalid characters
|
|
58
|
+
*/
|
|
59
|
+
buildImage(host: HostConfig, options: {
|
|
60
|
+
context: string;
|
|
61
|
+
tag: string;
|
|
62
|
+
dockerfile?: string;
|
|
63
|
+
noCache?: boolean;
|
|
64
|
+
}): Promise<{
|
|
65
|
+
status: string;
|
|
66
|
+
}>;
|
|
67
|
+
/**
|
|
68
|
+
* Recreate a container (stop, remove, pull latest, start with same config).
|
|
69
|
+
*
|
|
70
|
+
* @param containerId - Container ID or name
|
|
71
|
+
* @param host - Host configuration
|
|
72
|
+
* @param options - Recreate options (pull)
|
|
73
|
+
* @returns Promise resolving to recreation status and new container ID
|
|
74
|
+
*/
|
|
75
|
+
recreateContainer(containerId: string, host: HostConfig, options?: {
|
|
76
|
+
pull?: boolean;
|
|
77
|
+
}): Promise<{
|
|
78
|
+
status: string;
|
|
79
|
+
containerId: string;
|
|
80
|
+
}>;
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=image-service.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"image-service.d.ts","sourceRoot":"","sources":["../../../src/services/docker/image-service.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,SAAS,EAAE,iBAAiB,EAAE,MAAM,gBAAgB,CAAC;AAE/E,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAG/D;;;GAGG;AACH,qBAAa,YAAY;IACX,OAAO,CAAC,aAAa;gBAAb,aAAa,EAAE,aAAa;IAEhD;;;;;;OAMG;IACG,UAAU,CAAC,KAAK,EAAE,UAAU,EAAE,EAAE,OAAO,GAAE,iBAAsB,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC;IAW5F;;OAEG;YACW,gBAAgB;IAmB9B;;;;;;;OAOG;IACG,SAAS,CAAC,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,UAAU,GAAG,OAAO,CAAC;QAAE,MAAM,EAAE,MAAM,CAAA;KAAE,CAAC;IAyBjF;;;;;;;OAOG;IACG,WAAW,CACf,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,UAAU,EAChB,OAAO,GAAE;QAAE,KAAK,CAAC,EAAE,OAAO,CAAA;KAAO,GAChC,OAAO,CAAC;QAAE,MAAM,EAAE,MAAM,CAAA;KAAE,CAAC;IAS9B;;;;;;;;;;;;OAYG;IACG,UAAU,CACd,IAAI,EAAE,UAAU,EAChB,OAAO,EAAE;QACP,OAAO,EAAE,MAAM,CAAC;QAChB,GAAG,EAAE,MAAM,CAAC;QACZ,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,OAAO,CAAC,EAAE,OAAO,CAAC;KACnB,GACA,OAAO,CAAC;QAAE,MAAM,EAAE,MAAM,CAAA;KAAE,CAAC;IAmE9B;;;;;;;OAOG;IACG,iBAAiB,CACrB,WAAW,EAAE,MAAM,EACnB,IAAI,EAAE,UAAU,EAChB,OAAO,GAAE;QAAE,IAAI,CAAC,EAAE,OAAO,CAAA;KAAO,GAC/B,OAAO,CAAC;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,WAAW,EAAE,MAAM,CAAA;KAAE,CAAC;CAsCpD"}
|
|
@@ -0,0 +1,193 @@
|
|
|
1
|
+
import { narrowToDefaultHost } from "../../utils/host-utils.js";
|
|
2
|
+
import { formatImageId } from "./utils/formatters.js";
|
|
3
|
+
/**
|
|
4
|
+
* Service for Docker image operations.
|
|
5
|
+
* Handles image lifecycle, pulling, building, and management.
|
|
6
|
+
*/
|
|
7
|
+
export class ImageService {
|
|
8
|
+
clientManager;
|
|
9
|
+
constructor(clientManager) {
|
|
10
|
+
this.clientManager = clientManager;
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* List images across multiple hosts with optional filtering.
|
|
14
|
+
*
|
|
15
|
+
* @param hosts - List of Docker hosts to query
|
|
16
|
+
* @param options - Filtering options (danglingOnly)
|
|
17
|
+
* @returns Promise resolving to array of image information
|
|
18
|
+
*/
|
|
19
|
+
async listImages(hosts, options = {}) {
|
|
20
|
+
const targetHosts = narrowToDefaultHost(hosts);
|
|
21
|
+
const results = await Promise.allSettled(targetHosts.map((host) => this.listImagesOnHost(host, options)));
|
|
22
|
+
return results
|
|
23
|
+
.filter((r) => r.status === "fulfilled")
|
|
24
|
+
.flatMap((r) => r.value);
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* List images from a single host (internal helper).
|
|
28
|
+
*/
|
|
29
|
+
async listImagesOnHost(host, options) {
|
|
30
|
+
const docker = await this.clientManager.getClient(host);
|
|
31
|
+
const images = await docker.listImages({
|
|
32
|
+
filters: options.danglingOnly ? { dangling: ["true"] } : undefined,
|
|
33
|
+
});
|
|
34
|
+
return images.map((img) => ({
|
|
35
|
+
id: formatImageId(img.Id),
|
|
36
|
+
tags: img.RepoTags || ["<none>:<none>"],
|
|
37
|
+
size: img.Size,
|
|
38
|
+
created: new Date(img.Created * 1000).toISOString(),
|
|
39
|
+
containers: img.Containers || 0,
|
|
40
|
+
hostName: host.name,
|
|
41
|
+
}));
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Pull an image from a registry.
|
|
45
|
+
*
|
|
46
|
+
* @param imageName - Image name with optional tag (e.g., "nginx:latest")
|
|
47
|
+
* @param host - Host configuration
|
|
48
|
+
* @returns Promise resolving to pull status
|
|
49
|
+
* @throws Error if image name is empty or pull fails
|
|
50
|
+
*/
|
|
51
|
+
async pullImage(imageName, host) {
|
|
52
|
+
if (!imageName || imageName.trim() === "") {
|
|
53
|
+
throw new Error("Image name is required");
|
|
54
|
+
}
|
|
55
|
+
const docker = await this.clientManager.getClient(host);
|
|
56
|
+
return new Promise((resolve, reject) => {
|
|
57
|
+
docker.pull(imageName, (err, stream) => {
|
|
58
|
+
if (err) {
|
|
59
|
+
reject(new Error(`Failed to pull image: ${err.message}`));
|
|
60
|
+
return;
|
|
61
|
+
}
|
|
62
|
+
docker.modem.followProgress(stream, (err) => {
|
|
63
|
+
if (err) {
|
|
64
|
+
reject(new Error(`Pull failed: ${err.message}`));
|
|
65
|
+
}
|
|
66
|
+
else {
|
|
67
|
+
resolve({ status: `Successfully pulled ${imageName}` });
|
|
68
|
+
}
|
|
69
|
+
});
|
|
70
|
+
});
|
|
71
|
+
});
|
|
72
|
+
}
|
|
73
|
+
/**
|
|
74
|
+
* Remove an image from a host.
|
|
75
|
+
*
|
|
76
|
+
* @param imageId - Image ID or tag
|
|
77
|
+
* @param host - Host configuration
|
|
78
|
+
* @param options - Remove options (force)
|
|
79
|
+
* @returns Promise resolving to removal status
|
|
80
|
+
*/
|
|
81
|
+
async removeImage(imageId, host, options = {}) {
|
|
82
|
+
const docker = await this.clientManager.getClient(host);
|
|
83
|
+
const image = docker.getImage(imageId);
|
|
84
|
+
await image.remove({ force: options.force });
|
|
85
|
+
return { status: `Successfully removed image ${imageId}` };
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Build an image from a Dockerfile (SSH-based for remote hosts).
|
|
89
|
+
*
|
|
90
|
+
* SECURITY: Implements path traversal protection (CWE-22)
|
|
91
|
+
* - Requires absolute paths for context and dockerfile
|
|
92
|
+
* - Rejects any path containing .. or . components
|
|
93
|
+
* - Validates character set to prevent injection
|
|
94
|
+
*
|
|
95
|
+
* @param host - Docker host configuration
|
|
96
|
+
* @param options - Build options (context, tag, dockerfile, noCache)
|
|
97
|
+
* @returns Promise resolving to build status
|
|
98
|
+
* @throws Error if paths contain directory traversal or invalid characters
|
|
99
|
+
*/
|
|
100
|
+
async buildImage(host, options) {
|
|
101
|
+
// For remote builds, we need to use SSH and docker build command
|
|
102
|
+
// dockerode's build() requires local tar stream which won't work for remote
|
|
103
|
+
const { context, tag, dockerfile, noCache } = options;
|
|
104
|
+
// Validate inputs
|
|
105
|
+
if (!/^[a-zA-Z0-9._\-/:]+$/.test(tag)) {
|
|
106
|
+
throw new Error(`Invalid image tag: ${tag}`);
|
|
107
|
+
}
|
|
108
|
+
// Use secure path validation (prevents directory traversal)
|
|
109
|
+
const { validateSecurePath } = await import("../../utils/path-security.js");
|
|
110
|
+
validateSecurePath(context, "context");
|
|
111
|
+
if (dockerfile) {
|
|
112
|
+
validateSecurePath(dockerfile, "dockerfile");
|
|
113
|
+
}
|
|
114
|
+
const args = ["build", "-t", tag];
|
|
115
|
+
if (noCache) {
|
|
116
|
+
args.push("--no-cache");
|
|
117
|
+
}
|
|
118
|
+
if (dockerfile) {
|
|
119
|
+
args.push("-f", dockerfile);
|
|
120
|
+
}
|
|
121
|
+
args.push(context);
|
|
122
|
+
// Execute via SSH for remote hosts, or locally for socket connections
|
|
123
|
+
if (host.host.startsWith("/")) {
|
|
124
|
+
// Local socket - use docker directly
|
|
125
|
+
const { execFile } = await import("node:child_process");
|
|
126
|
+
const { promisify } = await import("node:util");
|
|
127
|
+
const execFileAsync = promisify(execFile);
|
|
128
|
+
await execFileAsync("docker", args, { timeout: 600000 }); // 10 min timeout for builds
|
|
129
|
+
}
|
|
130
|
+
else {
|
|
131
|
+
// Remote - use SSH
|
|
132
|
+
const { validateHostForSsh } = await import("../ssh.js");
|
|
133
|
+
const { validateAlphanumeric } = await import("../../utils/validation.js");
|
|
134
|
+
const { execFile } = await import("node:child_process");
|
|
135
|
+
const { promisify } = await import("node:util");
|
|
136
|
+
const execFileAsync = promisify(execFile);
|
|
137
|
+
validateHostForSsh(host);
|
|
138
|
+
validateAlphanumeric(host.name, "host name");
|
|
139
|
+
const sshArgs = [
|
|
140
|
+
"-o",
|
|
141
|
+
"BatchMode=yes",
|
|
142
|
+
"-o",
|
|
143
|
+
"ConnectTimeout=5",
|
|
144
|
+
"-o",
|
|
145
|
+
"StrictHostKeyChecking=accept-new",
|
|
146
|
+
host.name,
|
|
147
|
+
`docker ${args.join(" ")}`,
|
|
148
|
+
];
|
|
149
|
+
await execFileAsync("ssh", sshArgs, { timeout: 600000 });
|
|
150
|
+
}
|
|
151
|
+
return { status: `Successfully built image ${tag}` };
|
|
152
|
+
}
|
|
153
|
+
/**
|
|
154
|
+
* Recreate a container (stop, remove, pull latest, start with same config).
|
|
155
|
+
*
|
|
156
|
+
* @param containerId - Container ID or name
|
|
157
|
+
* @param host - Host configuration
|
|
158
|
+
* @param options - Recreate options (pull)
|
|
159
|
+
* @returns Promise resolving to recreation status and new container ID
|
|
160
|
+
*/
|
|
161
|
+
async recreateContainer(containerId, host, options = {}) {
|
|
162
|
+
const docker = await this.clientManager.getClient(host);
|
|
163
|
+
const container = docker.getContainer(containerId);
|
|
164
|
+
// Get current container config
|
|
165
|
+
const info = await container.inspect();
|
|
166
|
+
const imageName = info.Config.Image;
|
|
167
|
+
// Stop container if running
|
|
168
|
+
if (info.State.Running) {
|
|
169
|
+
await container.stop();
|
|
170
|
+
}
|
|
171
|
+
// Remove container
|
|
172
|
+
await container.remove();
|
|
173
|
+
// Pull latest image if requested
|
|
174
|
+
if (options.pull !== false) {
|
|
175
|
+
await this.pullImage(imageName, host);
|
|
176
|
+
}
|
|
177
|
+
// Create new container with same config
|
|
178
|
+
const newContainer = await docker.createContainer({
|
|
179
|
+
...info.Config,
|
|
180
|
+
HostConfig: info.HostConfig,
|
|
181
|
+
NetworkingConfig: {
|
|
182
|
+
EndpointsConfig: info.NetworkSettings.Networks,
|
|
183
|
+
},
|
|
184
|
+
});
|
|
185
|
+
// Start new container
|
|
186
|
+
await newContainer.start();
|
|
187
|
+
return {
|
|
188
|
+
status: "Container recreated successfully",
|
|
189
|
+
containerId: newContainer.id,
|
|
190
|
+
};
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
//# sourceMappingURL=image-service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"image-service.js","sourceRoot":"","sources":["../../../src/services/docker/image-service.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,mBAAmB,EAAE,MAAM,2BAA2B,CAAC;AAEhE,OAAO,EAAE,aAAa,EAAE,MAAM,uBAAuB,CAAC;AAEtD;;;GAGG;AACH,MAAM,OAAO,YAAY;IACH;IAApB,YAAoB,aAA4B;QAA5B,kBAAa,GAAb,aAAa,CAAe;IAAG,CAAC;IAEpD;;;;;;OAMG;IACH,KAAK,CAAC,UAAU,CAAC,KAAmB,EAAE,UAA6B,EAAE;QACnE,MAAM,WAAW,GAAG,mBAAmB,CAAC,KAAK,CAAC,CAAC;QAC/C,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,UAAU,CACtC,WAAW,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,gBAAgB,CAAC,IAAI,EAAE,OAAO,CAAC,CAAC,CAChE,CAAC;QAEF,OAAO,OAAO;aACX,MAAM,CAAC,CAAC,CAAC,EAA4C,EAAE,CAAC,CAAC,CAAC,MAAM,KAAK,WAAW,CAAC;aACjF,OAAO,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC;IAC7B,CAAC;IAED;;OAEG;IACK,KAAK,CAAC,gBAAgB,CAC5B,IAAgB,EAChB,OAA0B;QAE1B,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,aAAa,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;QACxD,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,UAAU,CAAC;YACrC,OAAO,EAAE,OAAO,CAAC,YAAY,CAAC,CAAC,CAAC,EAAE,QAAQ,EAAE,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC,CAAC,SAAS;SACnE,CAAC,CAAC;QAEH,OAAO,MAAM,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC;YAC1B,EAAE,EAAE,aAAa,CAAC,GAAG,CAAC,EAAE,CAAC;YACzB,IAAI,EAAE,GAAG,CAAC,QAAQ,IAAI,CAAC,eAAe,CAAC;YACvC,IAAI,EAAE,GAAG,CAAC,IAAI;YACd,OAAO,EAAE,IAAI,IAAI,CAAC,GAAG,CAAC,OAAO,GAAG,IAAI,CAAC,CAAC,WAAW,EAAE;YACnD,UAAU,EAAE,GAAG,CAAC,UAAU,IAAI,CAAC;YAC/B,QAAQ,EAAE,IAAI,CAAC,IAAI;SACpB,CAAC,CAAC,CAAC;IACN,CAAC;IAED;;;;;;;OAOG;IACH,KAAK,CAAC,SAAS,CAAC,SAAiB,EAAE,IAAgB;QACjD,IAAI,CAAC,SAAS,IAAI,SAAS,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAC;YAC1C,MAAM,IAAI,KAAK,CAAC,wBAAwB,CAAC,CAAC;QAC5C,CAAC;QAED,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,aAAa,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;QAExD,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE;YACrC,MAAM,CAAC,IAAI,CAAC,SAAS,EAAE,CAAC,GAAiB,EAAE,MAA6B,EAAE,EAAE;gBAC1E,IAAI,GAAG,EAAE,CAAC;oBACR,MAAM,CAAC,IAAI,KAAK,CAAC,yBAAyB,GAAG,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;oBAC1D,OAAO;gBACT,CAAC;gBAED,MAAM,CAAC,KAAK,CAAC,cAAc,CAAC,MAAM,EAAE,CAAC,GAAiB,EAAE,EAAE;oBACxD,IAAI,GAAG,EAAE,CAAC;wBACR,MAAM,CAAC,IAAI,KAAK,CAAC,gBAAgB,GAAG,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;oBACnD,CAAC;yBAAM,CAAC;wBACN,OAAO,CAAC,EAAE,MAAM,EAAE,uBAAuB,SAAS,EAAE,EAAE,CAAC,CAAC;oBAC1D,CAAC;gBACH,CAAC,CAAC,CAAC;YACL,CAAC,CAAC,CAAC;QACL,CAAC,CAAC,CAAC;IACL,CAAC;IAED;;;;;;;OAOG;IACH,KAAK,CAAC,WAAW,CACf,OAAe,EACf,IAAgB,EAChB,UAA+B,EAAE;QAEjC,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,aAAa,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;QACxD,MAAM,KAAK,GAAG,MAAM,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;QAEvC,MAAM,KAAK,CAAC,MAAM,CAAC,EAAE,KAAK,EAAE,OAAO,CAAC,KAAK,EAAE,CAAC,CAAC;QAE7C,OAAO,EAAE,MAAM,EAAE,8BAA8B,OAAO,EAAE,EAAE,CAAC;IAC7D,CAAC;IAED;;;;;;;;;;;;OAYG;IACH,KAAK,CAAC,UAAU,CACd,IAAgB,EAChB,OAKC;QAED,iEAAiE;QACjE,4EAA4E;QAE5E,MAAM,EAAE,OAAO,EAAE,GAAG,EAAE,UAAU,EAAE,OAAO,EAAE,GAAG,OAAO,CAAC;QAEtD,kBAAkB;QAClB,IAAI,CAAC,sBAAsB,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;YACtC,MAAM,IAAI,KAAK,CAAC,sBAAsB,GAAG,EAAE,CAAC,CAAC;QAC/C,CAAC;QAED,4DAA4D;QAC5D,MAAM,EAAE,kBAAkB,EAAE,GAAG,MAAM,MAAM,CAAC,8BAA8B,CAAC,CAAC;QAC5E,kBAAkB,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC;QAEvC,IAAI,UAAU,EAAE,CAAC;YACf,kBAAkB,CAAC,UAAU,EAAE,YAAY,CAAC,CAAC;QAC/C,CAAC;QAED,MAAM,IAAI,GAAa,CAAC,OAAO,EAAE,IAAI,EAAE,GAAG,CAAC,CAAC;QAE5C,IAAI,OAAO,EAAE,CAAC;YACZ,IAAI,CAAC,IAAI,CAAC,YAAY,CAAC,CAAC;QAC1B,CAAC;QAED,IAAI,UAAU,EAAE,CAAC;YACf,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,UAAU,CAAC,CAAC;QAC9B,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QAEnB,sEAAsE;QACtE,IAAI,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,EAAE,CAAC;YAC9B,qCAAqC;YACrC,MAAM,EAAE,QAAQ,EAAE,GAAG,MAAM,MAAM,CAAC,oBAAoB,CAAC,CAAC;YACxD,MAAM,EAAE,SAAS,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;YAChD,MAAM,aAAa,GAAG,SAAS,CAAC,QAAQ,CAAC,CAAC;YAE1C,MAAM,aAAa,CAAC,QAAQ,EAAE,IAAI,EAAE,EAAE,OAAO,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC,4BAA4B;QACxF,CAAC;aAAM,CAAC;YACN,mBAAmB;YACnB,MAAM,EAAE,kBAAkB,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;YACzD,MAAM,EAAE,oBAAoB,EAAE,GAAG,MAAM,MAAM,CAAC,2BAA2B,CAAC,CAAC;YAC3E,MAAM,EAAE,QAAQ,EAAE,GAAG,MAAM,MAAM,CAAC,oBAAoB,CAAC,CAAC;YACxD,MAAM,EAAE,SAAS,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;YAChD,MAAM,aAAa,GAAG,SAAS,CAAC,QAAQ,CAAC,CAAC;YAE1C,kBAAkB,CAAC,IAAI,CAAC,CAAC;YACzB,oBAAoB,CAAC,IAAI,CAAC,IAAI,EAAE,WAAW,CAAC,CAAC;YAE7C,MAAM,OAAO,GAAG;gBACd,IAAI;gBACJ,eAAe;gBACf,IAAI;gBACJ,kBAAkB;gBAClB,IAAI;gBACJ,kCAAkC;gBAClC,IAAI,CAAC,IAAI;gBACT,UAAU,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE;aAC3B,CAAC;YAEF,MAAM,aAAa,CAAC,KAAK,EAAE,OAAO,EAAE,EAAE,OAAO,EAAE,MAAM,EAAE,CAAC,CAAC;QAC3D,CAAC;QAED,OAAO,EAAE,MAAM,EAAE,4BAA4B,GAAG,EAAE,EAAE,CAAC;IACvD,CAAC;IAED;;;;;;;OAOG;IACH,KAAK,CAAC,iBAAiB,CACrB,WAAmB,EACnB,IAAgB,EAChB,UAA8B,EAAE;QAEhC,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,aAAa,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;QACxD,MAAM,SAAS,GAAG,MAAM,CAAC,YAAY,CAAC,WAAW,CAAC,CAAC;QAEnD,+BAA+B;QAC/B,MAAM,IAAI,GAAG,MAAM,SAAS,CAAC,OAAO,EAAE,CAAC;QACvC,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC;QAEpC,4BAA4B;QAC5B,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,CAAC;YACvB,MAAM,SAAS,CAAC,IAAI,EAAE,CAAC;QACzB,CAAC;QAED,mBAAmB;QACnB,MAAM,SAAS,CAAC,MAAM,EAAE,CAAC;QAEzB,iCAAiC;QACjC,IAAI,OAAO,CAAC,IAAI,KAAK,KAAK,EAAE,CAAC;YAC3B,MAAM,IAAI,CAAC,SAAS,CAAC,SAAS,EAAE,IAAI,CAAC,CAAC;QACxC,CAAC;QAED,wCAAwC;QACxC,MAAM,YAAY,GAAG,MAAM,MAAM,CAAC,eAAe,CAAC;YAChD,GAAG,IAAI,CAAC,MAAM;YACd,UAAU,EAAE,IAAI,CAAC,UAAU;YAC3B,gBAAgB,EAAE;gBAChB,eAAe,EAAE,IAAI,CAAC,eAAe,CAAC,QAAQ;aAC/C;SACF,CAAC,CAAC;QAEH,sBAAsB;QACtB,MAAM,YAAY,CAAC,KAAK,EAAE,CAAC;QAE3B,OAAO;YACL,MAAM,EAAE,kCAAkC;YAC1C,WAAW,EAAE,YAAY,CAAC,EAAE;SAC7B,CAAC;IACJ,CAAC;CACF"}
|