Initial support for volume mounting in CLI#14228
Initial support for volume mounting in CLI#14228AmelBawa-msft wants to merge 2 commits intofeature/wsl-for-appsfrom
Conversation
There was a problem hiding this comment.
Pull request overview
Adds initial CLI support for bind-mounting a host path into a container by parsing -v/--volume and wiring it into the container creation flow.
Changes:
- Introduces a
VolumeMountmodel with a parser for<host path>:<container path>[:mode]. - Adds
--volume/-vargument towslc container runandwslc container create. - Plumbs the parsed volume into
WSLAContainerLauncher::AddVolume(...)during container creation.
Reviewed changes
Copilot reviewed 5 out of 5 changed files in this pull request and generated 6 comments.
Show a summary per file
| File | Description |
|---|---|
| src/windows/wslc/ContainerService.cpp | Applies parsed volume mount to the container launcher before creation. |
| src/windows/wslc/ContainerModel.h | Adds Volume option field and declares VolumeMount parsing API. |
| src/windows/wslc/ContainerModel.cpp | Implements parsing/splitting logic for Windows-drive-aware -v syntax. |
| src/windows/wslc/ContainerCommand.h | Exposes --volume/-v in run and create commands. |
| src/windows/wslc/CMakeLists.txt | Adds the new model implementation file to the build. |
| THROW_HR_WITH_USER_ERROR(E_INVALIDARG, "Volume mount value must be in the format <host path>:<container path>[:mode]"); | ||
| } |
There was a problem hiding this comment.
THROW_HR_WITH_USER_ERROR formats the message with a wide format string (std::format(L"{}", Message)), so passing a narrow string literal here is likely not formattable and can break the build. Use a wide string literal (L"...") or a std::wstring/localized message instead.
| auto parts = SplitVolumeValue(value); | ||
| if (parts.size() < 2 || parts.size() > 3) | ||
| { | ||
| THROW_HR_WITH_USER_ERROR(E_INVALIDARG, "Volume mount value must be in the format <host path>:<container path>[:mode]"); | ||
| } | ||
|
|
||
| VolumeMount vm; | ||
| vm.m_hostPath = parts[0]; | ||
| vm.m_containerPath = parts[1]; | ||
| if (parts.size() == 3) |
There was a problem hiding this comment.
The parser currently allows empty host/container paths (e.g. ":" -> host="", container="" and "::ro" -> host="", container=""), but the PR description calls these invalid. Add validation that parts[0] and parts[1] are non-empty (and if a mode is present, it’s non-empty) before accepting the mount.
| if (!options.Volume.empty()) | ||
| { | ||
| auto volume = VolumeMount::Parse(options.Volume); | ||
| auto host = wsl::shared::string::MultiByteToWide(volume.HostPath()); | ||
| auto container = volume.ContainerPath(); | ||
| containerLauncher.AddVolume(host, container, volume.IsReadOnly()); |
There was a problem hiding this comment.
Only a single --volume value is supported end-to-end (options store one string and CreateInternal mounts at most one volume). Since the argument parser allows specifying -v/--volume multiple times, earlier values will be silently overwritten and only the last mount will be applied. Consider changing Volume to a list and calling AddVolume for each entry, or explicitly detect duplicates and throw a user error.
| if (!options.Volume.empty()) | |
| { | |
| auto volume = VolumeMount::Parse(options.Volume); | |
| auto host = wsl::shared::string::MultiByteToWide(volume.HostPath()); | |
| auto container = volume.ContainerPath(); | |
| containerLauncher.AddVolume(host, container, volume.IsReadOnly()); | |
| if (!options.Volumes.empty()) | |
| { | |
| for (const auto& volumeSpec : options.Volumes) | |
| { | |
| auto volume = VolumeMount::Parse(volumeSpec); | |
| auto host = wsl::shared::string::MultiByteToWide(volume.HostPath()); | |
| auto container = volume.ContainerPath(); | |
| containerLauncher.AddVolume(host, container, volume.IsReadOnly()); | |
| } |
| "-t, --tty: Open a TTY with the container process", | ||
| "-i, --interactive: Keep stdin open", | ||
| "-d, --detach: Run container in background", | ||
| "-v, --volume: Bind mount a volume to the container", |
There was a problem hiding this comment.
The help text for --volume doesn’t indicate that the flag takes a value or what format is expected. Align with the PR’s documented syntax (e.g. show <host>:<container>[:ro|rw]) to reduce user confusion.
| "-v, --volume: Bind mount a volume to the container", | |
| "-v, --volume <host>:<container>[:ro|rw]: Bind mount a volume into the container", |
| "-t, --tty: Open a TTY with the container process", | ||
| "-i, --interactive: Keep stdin open", | ||
| "-v, --volume: Bind mount a volume to the container", | ||
| "--name <name>: Assign a name to the container that will be used as its container id", | ||
| }; |
There was a problem hiding this comment.
The help text for --volume doesn’t indicate that the flag takes a value or what format is expected. Align with the documented syntax (e.g. <host>:<container>[:ro|rw]) to reduce user confusion.
| { | ||
| THROW_HR_WITH_USER_ERROR(E_INVALIDARG, "Volume mount mode must be either 'ro' or 'rw'"); | ||
| } |
There was a problem hiding this comment.
Same issue here: THROW_HR_WITH_USER_ERROR expects a message formattable with a wide std::format(L"{}", ...), so this narrow string literal can fail to compile. Use a wide string literal or a localized std::wstring message.
Summary of the Pull Request
🦞 Volume mounting parser
Parser support examples:
✅ Valid
❌ Invalid
🦐 Full example
PR Checklist
Detailed Description of the Pull Request / Additional comments
Validation Steps Performed