The following pull request was submitted through Github. It can be accessed and reviewed at: https://github.com/lxc/lxd/pull/4079
This e-mail was sent by the LXC bot, direct replies will not reach the author unless they happen to be subscribed to this list. === Description (from pull-request) ===
From c4441a537cd1257a525dbd9cee4acd9ced0077fc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?St=C3=A9phane=20Graber?= <[email protected]> Date: Tue, 5 Dec 2017 18:29:40 -0500 Subject: [PATCH 1/4] doc: Fix markdown escaping for prlimits MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Stéphane Graber <[email protected]> --- doc/containers.md | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/doc/containers.md b/doc/containers.md index 5e0855d8b..c232e4ec3 100644 --- a/doc/containers.md +++ b/doc/containers.md @@ -360,18 +360,18 @@ supported limit on their system. Some common limits are: Key | Resource | Description :-- | :--- | :---------- -limits.kernel.as | RLIMIT_AS | Maximum size of the process's virtual memory -limits.kernel.core | RLIMIT_CORE | Maximum size of the process's coredump file -limits.kernel.cpu | RLIMIT_CPU | Limit in seconds on the amount of cpu time the process can consume -limits.kernel.data | RLIMIT_DATA | Maximum size of the process's data segment -limits.kernel.fsize | RLIMIT_FSIZE | Maximum size of files the process may create -limits.kernel.locks | RLIMIT_LOCKS | Limit on the number of file locks that this process may establish -limits.kernel.memlock | RLIMIT_MEMLOCK | Limit on the number of bytes of memory that the process may lock in RAM -limits.kernel.nice | RLIMIT_NICE | Maximum value to which the process's nice value can be raised -limits.kernel.nofile | RLIMIT_NOFILE | Maximum number of open files for the process -limits.kernel.nproc | RLIMIT_NPROC | Maximum number of processes that can be created for the user of the calling process -limits.kernel.rtprio | RLIMIT_RTPRIO | Maximum value on the real-time-priority that maybe set for this process -limits.kernel.sigpending | RLIMIT_SIGPENDING | Maximum number of signals that maybe queued for the user of the calling process +limits.kernel.as | RLIMIT\_AS | Maximum size of the process's virtual memory +limits.kernel.core | RLIMIT\_CORE | Maximum size of the process's coredump file +limits.kernel.cpu | RLIMIT\_CPU | Limit in seconds on the amount of cpu time the process can consume +limits.kernel.data | RLIMIT\_DATA | Maximum size of the process's data segment +limits.kernel.fsize | RLIMIT\_FSIZE | Maximum size of files the process may create +limits.kernel.locks | RLIMIT\_LOCKS | Limit on the number of file locks that this process may establish +limits.kernel.memlock | RLIMIT\_MEMLOCK | Limit on the number of bytes of memory that the process may lock in RAM +limits.kernel.nice | RLIMIT\_NICE | Maximum value to which the process's nice value can be raised +limits.kernel.nofile | RLIMIT\_NOFILE | Maximum number of open files for the process +limits.kernel.nproc | RLIMIT\_NPROC | Maximum number of processes that can be created for the user of the calling process +limits.kernel.rtprio | RLIMIT\_RTPRIO | Maximum value on the real-time-priority that maybe set for this process +limits.kernel.sigpending | RLIMIT\_SIGPENDING | Maximum number of signals that maybe queued for the user of the calling process A full list of all available limits can be found in the manpages for the `getrlimit(2)`/`setrlimit(2)` system calls. To specify a limit within the From ac5d69d67ca5c5b0813b2865e9800e697b513468 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?St=C3=A9phane=20Graber?= <[email protected]> Date: Tue, 5 Dec 2017 22:10:07 -0500 Subject: [PATCH 2/4] Makefile: Better detect sqlite3.h MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Closes #4078 Signed-off-by: Stéphane Graber <[email protected]> --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index 0491e8623..51b83c8ba 100644 --- a/Makefile +++ b/Makefile @@ -9,7 +9,7 @@ POTFILE=po/$(DOMAIN).pot # TODO: use git describe for versioning VERSION=$(shell grep "var Version" shared/version/flex.go | cut -d'"' -f2) ARCHIVE=lxd-$(VERSION).tar -TAGS=$(shell test -e /usr/include/sqlite3.h && echo "-tags libsqlite3") +TAGS=$(shell printf "\#include <sqlite3.h>\nvoid main(){}" | gcc -o /dev/null -xc - >/dev/null 2>&1 && echo "-tags libsqlite3") .PHONY: default default: From edc4227e28b75775596324afda2eb62b06a83434 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?St=C3=A9phane=20Graber?= <[email protected]> Date: Tue, 5 Dec 2017 22:18:50 -0500 Subject: [PATCH 3/4] networks: Extend allowed character set for interfaces MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Closes #4042 Signed-off-by: Stéphane Graber <[email protected]> --- lxd/networks_utils.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lxd/networks_utils.go b/lxd/networks_utils.go index fa7c0fd9b..20b9b9024 100644 --- a/lxd/networks_utils.go +++ b/lxd/networks_utils.go @@ -472,7 +472,7 @@ func networkValidName(value string) error { } // Validate the character set - match, _ := regexp.MatchString("^[-a-zA-Z0-9]*$", value) + match, _ := regexp.MatchString("^[-_a-zA-Z0-9.]*$", value) if !match { return fmt.Errorf("Interface name contains invalid characters") } From da8878bdaf644f797e7c0853c97592b2c0499e9e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?St=C3=A9phane=20Graber?= <[email protected]> Date: Tue, 5 Dec 2017 23:54:18 -0500 Subject: [PATCH 4/4] client: URL escape all user input MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Closes #4077 Signed-off-by: Stéphane Graber <[email protected]> --- client/lxd_certificates.go | 7 ++-- client/lxd_containers.go | 81 ++++++++++++++++++++----------------------- client/lxd_images.go | 26 +++++++------- client/lxd_networks.go | 9 ++--- client/lxd_operations.go | 9 ++--- client/lxd_profiles.go | 9 ++--- client/lxd_storage_pools.go | 9 ++--- client/lxd_storage_volumes.go | 19 +++++----- 8 files changed, 85 insertions(+), 84 deletions(-) diff --git a/client/lxd_certificates.go b/client/lxd_certificates.go index bf5349599..1c036b523 100644 --- a/client/lxd_certificates.go +++ b/client/lxd_certificates.go @@ -2,6 +2,7 @@ package lxd import ( "fmt" + "net/url" "strings" "github.com/lxc/lxd/shared/api" @@ -47,7 +48,7 @@ func (r *ProtocolLXD) GetCertificate(fingerprint string) (*api.Certificate, stri certificate := api.Certificate{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/certificates/%s", fingerprint), nil, "", &certificate) + etag, err := r.queryStruct("GET", fmt.Sprintf("/certificates/%s", url.QueryEscape(fingerprint)), nil, "", &certificate) if err != nil { return nil, "", err } @@ -73,7 +74,7 @@ func (r *ProtocolLXD) UpdateCertificate(fingerprint string, certificate api.Cert } // Send the request - _, _, err := r.query("PUT", fmt.Sprintf("/certificates/%s", fingerprint), certificate, ETag) + _, _, err := r.query("PUT", fmt.Sprintf("/certificates/%s", url.QueryEscape(fingerprint)), certificate, ETag) if err != nil { return err } @@ -84,7 +85,7 @@ func (r *ProtocolLXD) UpdateCertificate(fingerprint string, certificate api.Cert // DeleteCertificate removes a certificate from the LXD trust store func (r *ProtocolLXD) DeleteCertificate(fingerprint string) error { // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/certificates/%s", fingerprint), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/certificates/%s", url.QueryEscape(fingerprint)), nil, "") if err != nil { return err } diff --git a/client/lxd_containers.go b/client/lxd_containers.go index 50a52d28a..04585e135 100644 --- a/client/lxd_containers.go +++ b/client/lxd_containers.go @@ -5,6 +5,7 @@ import ( "fmt" "io" "net/http" + "net/url" "strings" "github.com/gorilla/websocket" @@ -53,7 +54,7 @@ func (r *ProtocolLXD) GetContainer(name string) (*api.Container, string, error) container := api.Container{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s", name), nil, "", &container) + etag, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s", url.QueryEscape(name)), nil, "", &container) if err != nil { return nil, "", err } @@ -97,7 +98,7 @@ func (r *ProtocolLXD) tryCreateContainer(req api.ContainersPost, urls []string) if operation == "" { req.Source.Server = serverURL } else { - req.Source.Operation = fmt.Sprintf("%s/1.0/operations/%s", serverURL, operation) + req.Source.Operation = fmt.Sprintf("%s/1.0/operations/%s", serverURL, url.QueryEscape(operation)) } op, err := r.CreateContainer(req) @@ -462,7 +463,7 @@ func (r *ProtocolLXD) proxyMigration(targetOp *Operation, targetSecrets map[stri // UpdateContainer updates the container definition func (r *ProtocolLXD) UpdateContainer(name string, container api.ContainerPut, ETag string) (*Operation, error) { // Send the request - op, _, err := r.queryOperation("PUT", fmt.Sprintf("/containers/%s", name), container, ETag) + op, _, err := r.queryOperation("PUT", fmt.Sprintf("/containers/%s", url.QueryEscape(name)), container, ETag) if err != nil { return nil, err } @@ -478,7 +479,7 @@ func (r *ProtocolLXD) RenameContainer(name string, container api.ContainerPost) } // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s", name), container, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s", url.QueryEscape(name)), container, "") if err != nil { return nil, err } @@ -502,7 +503,7 @@ func (r *ProtocolLXD) tryMigrateContainer(source ContainerServer, name string, r success := false errors := []string{} for _, serverURL := range urls { - req.Target.Operation = fmt.Sprintf("%s/1.0/operations/%s", serverURL, operation) + req.Target.Operation = fmt.Sprintf("%s/1.0/operations/%s", serverURL, url.QueryEscape(operation)) op, err := source.MigrateContainer(name, req) if err != nil { @@ -550,7 +551,7 @@ func (r *ProtocolLXD) MigrateContainer(name string, container api.ContainerPost) } // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s", name), container, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s", url.QueryEscape(name)), container, "") if err != nil { return nil, err } @@ -561,7 +562,7 @@ func (r *ProtocolLXD) MigrateContainer(name string, container api.ContainerPost) // DeleteContainer requests that LXD deletes the container func (r *ProtocolLXD) DeleteContainer(name string) (*Operation, error) { // Send the request - op, _, err := r.queryOperation("DELETE", fmt.Sprintf("/containers/%s", name), nil, "") + op, _, err := r.queryOperation("DELETE", fmt.Sprintf("/containers/%s", url.QueryEscape(name)), nil, "") if err != nil { return nil, err } @@ -578,7 +579,7 @@ func (r *ProtocolLXD) ExecContainer(containerName string, exec api.ContainerExec } // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/exec", containerName), exec, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/exec", url.QueryEscape(containerName)), exec, "") if err != nil { return nil, err } @@ -701,7 +702,7 @@ func (r *ProtocolLXD) ExecContainer(containerName string, exec api.ContainerExec func (r *ProtocolLXD) GetContainerFile(containerName string, path string) (io.ReadCloser, *ContainerFileResponse, error) { // Prepare the HTTP request requestURL, err := shared.URLEncode( - fmt.Sprintf("%s/1.0/containers/%s/files", r.httpHost, containerName), + fmt.Sprintf("%s/1.0/containers/%s/files", r.httpHost, url.QueryEscape(containerName)), map[string]string{"path": path}) if err != nil { return nil, nil, err @@ -786,13 +787,7 @@ func (r *ProtocolLXD) CreateContainerFile(containerName string, path string, arg } // Prepare the HTTP request - requestURL, err := shared.URLEncode( - fmt.Sprintf("%s/1.0/containers/%s/files", r.httpHost, containerName), - map[string]string{"path": path}) - if err != nil { - return err - } - req, err := http.NewRequest("POST", requestURL, args.Content) + req, err := http.NewRequest("POST", fmt.Sprintf("%s/1.0/containers/%s/files?path=%s", r.httpHost, url.QueryEscape(containerName), url.QueryEscape(path)), args.Content) if err != nil { return err } @@ -845,7 +840,7 @@ func (r *ProtocolLXD) DeleteContainerFile(containerName string, path string) err } // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/containers/%s/files?path=%s", containerName, path), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/containers/%s/files?path=%s", url.QueryEscape(containerName), url.QueryEscape(path)), nil, "") if err != nil { return err } @@ -858,15 +853,15 @@ func (r *ProtocolLXD) GetContainerSnapshotNames(containerName string) ([]string, urls := []string{} // Fetch the raw value - _, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/snapshots", containerName), nil, "", &urls) + _, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/snapshots", url.QueryEscape(containerName)), nil, "", &urls) if err != nil { return nil, err } // Parse it names := []string{} - for _, url := range urls { - fields := strings.Split(url, fmt.Sprintf("/containers/%s/snapshots/", containerName)) + for _, uri := range urls { + fields := strings.Split(uri, fmt.Sprintf("/containers/%s/snapshots/", url.QueryEscape(containerName))) names = append(names, fields[len(fields)-1]) } @@ -878,7 +873,7 @@ func (r *ProtocolLXD) GetContainerSnapshots(containerName string) ([]api.Contain snapshots := []api.ContainerSnapshot{} // Fetch the raw value - _, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/snapshots?recursion=1", containerName), nil, "", &snapshots) + _, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/snapshots?recursion=1", url.QueryEscape(containerName)), nil, "", &snapshots) if err != nil { return nil, err } @@ -891,7 +886,7 @@ func (r *ProtocolLXD) GetContainerSnapshot(containerName string, name string) (* snapshot := api.ContainerSnapshot{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/snapshots/%s", containerName, name), nil, "", &snapshot) + etag, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/snapshots/%s", url.QueryEscape(containerName), url.QueryEscape(name)), nil, "", &snapshot) if err != nil { return nil, "", err } @@ -902,7 +897,7 @@ func (r *ProtocolLXD) GetContainerSnapshot(containerName string, name string) (* // CreateContainerSnapshot requests that LXD creates a new snapshot for the container func (r *ProtocolLXD) CreateContainerSnapshot(containerName string, snapshot api.ContainerSnapshotsPost) (*Operation, error) { // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/snapshots", containerName), snapshot, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/snapshots", url.QueryEscape(containerName)), snapshot, "") if err != nil { return nil, err } @@ -1100,7 +1095,7 @@ func (r *ProtocolLXD) RenameContainerSnapshot(containerName string, name string, } // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/snapshots/%s", containerName, name), container, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/snapshots/%s", url.QueryEscape(containerName), url.QueryEscape(name)), container, "") if err != nil { return nil, err } @@ -1124,7 +1119,7 @@ func (r *ProtocolLXD) tryMigrateContainerSnapshot(source ContainerServer, contai success := false errors := []string{} for _, serverURL := range urls { - req.Target.Operation = fmt.Sprintf("%s/1.0/operations/%s", serverURL, operation) + req.Target.Operation = fmt.Sprintf("%s/1.0/operations/%s", serverURL, url.QueryEscape(operation)) op, err := source.MigrateContainerSnapshot(containerName, name, req) if err != nil { @@ -1166,7 +1161,7 @@ func (r *ProtocolLXD) MigrateContainerSnapshot(containerName string, name string } // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/snapshots/%s", containerName, name), container, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/snapshots/%s", url.QueryEscape(containerName), url.QueryEscape(name)), container, "") if err != nil { return nil, err } @@ -1177,7 +1172,7 @@ func (r *ProtocolLXD) MigrateContainerSnapshot(containerName string, name string // DeleteContainerSnapshot requests that LXD deletes the container snapshot func (r *ProtocolLXD) DeleteContainerSnapshot(containerName string, name string) (*Operation, error) { // Send the request - op, _, err := r.queryOperation("DELETE", fmt.Sprintf("/containers/%s/snapshots/%s", containerName, name), nil, "") + op, _, err := r.queryOperation("DELETE", fmt.Sprintf("/containers/%s/snapshots/%s", url.QueryEscape(containerName), url.QueryEscape(name)), nil, "") if err != nil { return nil, err } @@ -1190,7 +1185,7 @@ func (r *ProtocolLXD) GetContainerState(name string) (*api.ContainerState, strin state := api.ContainerState{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/state", name), nil, "", &state) + etag, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/state", url.QueryEscape(name)), nil, "", &state) if err != nil { return nil, "", err } @@ -1201,7 +1196,7 @@ func (r *ProtocolLXD) GetContainerState(name string) (*api.ContainerState, strin // UpdateContainerState updates the container to match the requested state func (r *ProtocolLXD) UpdateContainerState(name string, state api.ContainerStatePut, ETag string) (*Operation, error) { // Send the request - op, _, err := r.queryOperation("PUT", fmt.Sprintf("/containers/%s/state", name), state, ETag) + op, _, err := r.queryOperation("PUT", fmt.Sprintf("/containers/%s/state", url.QueryEscape(name)), state, ETag) if err != nil { return nil, err } @@ -1214,15 +1209,15 @@ func (r *ProtocolLXD) GetContainerLogfiles(name string) ([]string, error) { urls := []string{} // Fetch the raw value - _, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/logs", name), nil, "", &urls) + _, err := r.queryStruct("GET", fmt.Sprintf("/containers/%s/logs", url.QueryEscape(name)), nil, "", &urls) if err != nil { return nil, err } // Parse it logfiles := []string{} - for _, url := range logfiles { - fields := strings.Split(url, fmt.Sprintf("/containers/%s/logs/", name)) + for _, uri := range logfiles { + fields := strings.Split(uri, fmt.Sprintf("/containers/%s/logs/", url.QueryEscape(name))) logfiles = append(logfiles, fields[len(fields)-1]) } @@ -1234,7 +1229,7 @@ func (r *ProtocolLXD) GetContainerLogfiles(name string) ([]string, error) { // Note that it's the caller's responsibility to close the returned ReadCloser func (r *ProtocolLXD) GetContainerLogfile(name string, filename string) (io.ReadCloser, error) { // Prepare the HTTP request - url := fmt.Sprintf("%s/1.0/containers/%s/logs/%s", r.httpHost, name, filename) + url := fmt.Sprintf("%s/1.0/containers/%s/logs/%s", r.httpHost, url.QueryEscape(name), url.QueryEscape(filename)) req, err := http.NewRequest("GET", url, nil) if err != nil { return nil, err @@ -1265,7 +1260,7 @@ func (r *ProtocolLXD) GetContainerLogfile(name string, filename string) (io.Read // DeleteContainerLogfile deletes the requested logfile func (r *ProtocolLXD) DeleteContainerLogfile(name string, filename string) error { // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/containers/%s/logs/%s", name, filename), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/containers/%s/logs/%s", url.QueryEscape(name), url.QueryEscape(filename)), nil, "") if err != nil { return err } @@ -1281,7 +1276,7 @@ func (r *ProtocolLXD) GetContainerMetadata(name string) (*api.ImageMetadata, str metadata := api.ImageMetadata{} - url := fmt.Sprintf("/containers/%s/metadata", name) + url := fmt.Sprintf("/containers/%s/metadata", url.QueryEscape(name)) etag, err := r.queryStruct("GET", url, nil, "", &metadata) if err != nil { return nil, "", err @@ -1296,7 +1291,7 @@ func (r *ProtocolLXD) SetContainerMetadata(name string, metadata api.ImageMetada return fmt.Errorf("The server is missing the required \"container_edit_metadata\" API extension") } - url := fmt.Sprintf("/containers/%s/metadata", name) + url := fmt.Sprintf("/containers/%s/metadata", url.QueryEscape(name)) _, _, err := r.query("PUT", url, metadata, ETag) if err != nil { return err @@ -1313,7 +1308,7 @@ func (r *ProtocolLXD) GetContainerTemplateFiles(containerName string) ([]string, templates := []string{} - url := fmt.Sprintf("/containers/%s/metadata/templates", containerName) + url := fmt.Sprintf("/containers/%s/metadata/templates", url.QueryEscape(containerName)) _, err := r.queryStruct("GET", url, nil, "", &templates) if err != nil { return nil, err @@ -1328,7 +1323,7 @@ func (r *ProtocolLXD) GetContainerTemplateFile(containerName string, templateNam return nil, fmt.Errorf("The server is missing the required \"container_edit_metadata\" API extension") } - url := fmt.Sprintf("%s/1.0/containers/%s/metadata/templates?path=%s", r.httpHost, containerName, templateName) + url := fmt.Sprintf("%s/1.0/containers/%s/metadata/templates?path=%s", r.httpHost, url.QueryEscape(containerName), url.QueryEscape(templateName)) req, err := http.NewRequest("GET", url, nil) if err != nil { return nil, err @@ -1371,7 +1366,7 @@ func (r *ProtocolLXD) setContainerTemplateFile(containerName string, templateNam return fmt.Errorf("The server is missing the required \"container_edit_metadata\" API extension") } - url := fmt.Sprintf("%s/1.0/containers/%s/metadata/templates?path=%s", r.httpHost, containerName, templateName) + url := fmt.Sprintf("%s/1.0/containers/%s/metadata/templates?path=%s", r.httpHost, url.QueryEscape(containerName), url.QueryEscape(templateName)) req, err := http.NewRequest(httpMethod, url, content) if err != nil { return err @@ -1400,7 +1395,7 @@ func (r *ProtocolLXD) DeleteContainerTemplateFile(name string, templateName stri if !r.HasExtension("container_edit_metadata") { return fmt.Errorf("The server is missing the required \"container_edit_metadata\" API extension") } - _, _, err := r.query("DELETE", fmt.Sprintf("/containers/%s/metadata/templates?path=%s", name, templateName), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/containers/%s/metadata/templates?path=%s", url.QueryEscape(name), url.QueryEscape(templateName)), nil, "") return err } @@ -1411,7 +1406,7 @@ func (r *ProtocolLXD) ConsoleContainer(containerName string, console api.Contain } // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/console", containerName), console, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/containers/%s/console", url.QueryEscape(containerName)), console, "") if err != nil { return nil, err } @@ -1482,7 +1477,7 @@ func (r *ProtocolLXD) GetContainerConsoleLog(containerName string, args *Contain } // Prepare the HTTP request - url := fmt.Sprintf("%s/1.0/containers/%s/console", r.httpHost, containerName) + url := fmt.Sprintf("%s/1.0/containers/%s/console", r.httpHost, url.QueryEscape(containerName)) req, err := http.NewRequest("GET", url, nil) if err != nil { return nil, err @@ -1517,7 +1512,7 @@ func (r *ProtocolLXD) DeleteContainerConsoleLog(containerName string, args *Cont } // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/containers/%s/console", containerName), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/containers/%s/console", url.QueryEscape(containerName)), nil, "") if err != nil { return err } diff --git a/client/lxd_images.go b/client/lxd_images.go index d01c27da1..8d0889640 100644 --- a/client/lxd_images.go +++ b/client/lxd_images.go @@ -77,9 +77,9 @@ func (r *ProtocolLXD) GetPrivateImage(fingerprint string, secret string) (*api.I image := api.Image{} // Build the API path - path := fmt.Sprintf("/images/%s", fingerprint) + path := fmt.Sprintf("/images/%s", url.QueryEscape(fingerprint)) if secret != "" { - path = fmt.Sprintf("%s?secret=%s", path, secret) + path = fmt.Sprintf("%s?secret=%s", path, url.QueryEscape(secret)) } // Fetch the raw value @@ -102,13 +102,13 @@ func (r *ProtocolLXD) GetPrivateImageFile(fingerprint string, secret string, req resp := ImageFileResponse{} // Build the URL - url := fmt.Sprintf("%s/1.0/images/%s/export", r.httpHost, fingerprint) + uri := fmt.Sprintf("%s/1.0/images/%s/export", r.httpHost, url.QueryEscape(fingerprint)) if secret != "" { - url = fmt.Sprintf("%s?secret=%s", url, secret) + uri = fmt.Sprintf("%s?secret=%s", uri, url.QueryEscape(secret)) } // Prepare the download request - request, err := http.NewRequest("GET", url, nil) + request, err := http.NewRequest("GET", uri, nil) if err != nil { return nil, err } @@ -271,7 +271,7 @@ func (r *ProtocolLXD) GetImageAlias(name string) (*api.ImageAliasesEntry, string alias := api.ImageAliasesEntry{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/images/aliases/%s", name), nil, "", &alias) + etag, err := r.queryStruct("GET", fmt.Sprintf("/images/aliases/%s", url.QueryEscape(name)), nil, "", &alias) if err != nil { return nil, "", err } @@ -570,7 +570,7 @@ func (r *ProtocolLXD) CopyImage(source ImageServer, image api.Image, args *Image // UpdateImage updates the image definition func (r *ProtocolLXD) UpdateImage(fingerprint string, image api.ImagePut, ETag string) error { // Send the request - _, _, err := r.query("PUT", fmt.Sprintf("/images/%s", fingerprint), image, ETag) + _, _, err := r.query("PUT", fmt.Sprintf("/images/%s", url.QueryEscape(fingerprint)), image, ETag) if err != nil { return err } @@ -581,7 +581,7 @@ func (r *ProtocolLXD) UpdateImage(fingerprint string, image api.ImagePut, ETag s // DeleteImage requests that LXD removes an image from the store func (r *ProtocolLXD) DeleteImage(fingerprint string) (*Operation, error) { // Send the request - op, _, err := r.queryOperation("DELETE", fmt.Sprintf("/images/%s", fingerprint), nil, "") + op, _, err := r.queryOperation("DELETE", fmt.Sprintf("/images/%s", url.QueryEscape(fingerprint)), nil, "") if err != nil { return nil, err } @@ -596,7 +596,7 @@ func (r *ProtocolLXD) RefreshImage(fingerprint string) (*Operation, error) { } // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/images/%s/refresh", fingerprint), nil, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/images/%s/refresh", url.QueryEscape(fingerprint)), nil, "") if err != nil { return nil, err } @@ -607,7 +607,7 @@ func (r *ProtocolLXD) RefreshImage(fingerprint string) (*Operation, error) { // CreateImageSecret requests that LXD issues a temporary image secret func (r *ProtocolLXD) CreateImageSecret(fingerprint string) (*Operation, error) { // Send the request - op, _, err := r.queryOperation("POST", fmt.Sprintf("/images/%s/secret", fingerprint), nil, "") + op, _, err := r.queryOperation("POST", fmt.Sprintf("/images/%s/secret", url.QueryEscape(fingerprint)), nil, "") if err != nil { return nil, err } @@ -629,7 +629,7 @@ func (r *ProtocolLXD) CreateImageAlias(alias api.ImageAliasesPost) error { // UpdateImageAlias updates the image alias definition func (r *ProtocolLXD) UpdateImageAlias(name string, alias api.ImageAliasesEntryPut, ETag string) error { // Send the request - _, _, err := r.query("PUT", fmt.Sprintf("/images/aliases/%s", name), alias, ETag) + _, _, err := r.query("PUT", fmt.Sprintf("/images/aliases/%s", url.QueryEscape(name)), alias, ETag) if err != nil { return err } @@ -640,7 +640,7 @@ func (r *ProtocolLXD) UpdateImageAlias(name string, alias api.ImageAliasesEntryP // RenameImageAlias renames an existing image alias func (r *ProtocolLXD) RenameImageAlias(name string, alias api.ImageAliasesEntryPost) error { // Send the request - _, _, err := r.query("POST", fmt.Sprintf("/images/aliases/%s", name), alias, "") + _, _, err := r.query("POST", fmt.Sprintf("/images/aliases/%s", url.QueryEscape(name)), alias, "") if err != nil { return err } @@ -651,7 +651,7 @@ func (r *ProtocolLXD) RenameImageAlias(name string, alias api.ImageAliasesEntryP // DeleteImageAlias removes an alias from the LXD image store func (r *ProtocolLXD) DeleteImageAlias(name string) error { // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/images/aliases/%s", name), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/images/aliases/%s", url.QueryEscape(name)), nil, "") if err != nil { return err } diff --git a/client/lxd_networks.go b/client/lxd_networks.go index cbc3fd30a..84ea4703c 100644 --- a/client/lxd_networks.go +++ b/client/lxd_networks.go @@ -2,6 +2,7 @@ package lxd import ( "fmt" + "net/url" "strings" "github.com/lxc/lxd/shared/api" @@ -45,7 +46,7 @@ func (r *ProtocolLXD) GetNetwork(name string) (*api.Network, string, error) { network := api.Network{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/networks/%s", name), nil, "", &network) + etag, err := r.queryStruct("GET", fmt.Sprintf("/networks/%s", url.QueryEscape(name)), nil, "", &network) if err != nil { return nil, "", err } @@ -71,7 +72,7 @@ func (r *ProtocolLXD) CreateNetwork(network api.NetworksPost) error { // UpdateNetwork updates the network to match the provided Network struct func (r *ProtocolLXD) UpdateNetwork(name string, network api.NetworkPut, ETag string) error { // Send the request - _, _, err := r.query("PUT", fmt.Sprintf("/networks/%s", name), network, ETag) + _, _, err := r.query("PUT", fmt.Sprintf("/networks/%s", url.QueryEscape(name)), network, ETag) if err != nil { return err } @@ -82,7 +83,7 @@ func (r *ProtocolLXD) UpdateNetwork(name string, network api.NetworkPut, ETag st // RenameNetwork renames an existing network entry func (r *ProtocolLXD) RenameNetwork(name string, network api.NetworkPost) error { // Send the request - _, _, err := r.query("POST", fmt.Sprintf("/networks/%s", name), network, "") + _, _, err := r.query("POST", fmt.Sprintf("/networks/%s", url.QueryEscape(name)), network, "") if err != nil { return err } @@ -93,7 +94,7 @@ func (r *ProtocolLXD) RenameNetwork(name string, network api.NetworkPost) error // DeleteNetwork deletes an existing network func (r *ProtocolLXD) DeleteNetwork(name string) error { // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/networks/%s", name), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/networks/%s", url.QueryEscape(name)), nil, "") if err != nil { return err } diff --git a/client/lxd_operations.go b/client/lxd_operations.go index f585196dc..d5886214b 100644 --- a/client/lxd_operations.go +++ b/client/lxd_operations.go @@ -2,6 +2,7 @@ package lxd import ( "fmt" + "net/url" "strings" "github.com/gorilla/websocket" @@ -55,7 +56,7 @@ func (r *ProtocolLXD) GetOperation(uuid string) (*api.Operation, string, error) op := api.Operation{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/operations/%s", uuid), nil, "", &op) + etag, err := r.queryStruct("GET", fmt.Sprintf("/operations/%s", url.QueryEscape(uuid)), nil, "", &op) if err != nil { return nil, "", err } @@ -65,9 +66,9 @@ func (r *ProtocolLXD) GetOperation(uuid string) (*api.Operation, string, error) // GetOperationWebsocket returns a websocket connection for the provided operation func (r *ProtocolLXD) GetOperationWebsocket(uuid string, secret string) (*websocket.Conn, error) { - path := fmt.Sprintf("/operations/%s/websocket", uuid) + path := fmt.Sprintf("/operations/%s/websocket", url.QueryEscape(uuid)) if secret != "" { - path = fmt.Sprintf("%s?secret=%s", path, secret) + path = fmt.Sprintf("%s?secret=%s", path, url.QueryEscape(secret)) } return r.websocket(path) @@ -76,7 +77,7 @@ func (r *ProtocolLXD) GetOperationWebsocket(uuid string, secret string) (*websoc // DeleteOperation deletes (cancels) a running operation func (r *ProtocolLXD) DeleteOperation(uuid string) error { // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/operations/%s", uuid), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/operations/%s", url.QueryEscape(uuid)), nil, "") if err != nil { return err } diff --git a/client/lxd_profiles.go b/client/lxd_profiles.go index a11f4cb3f..bcaa8848f 100644 --- a/client/lxd_profiles.go +++ b/client/lxd_profiles.go @@ -2,6 +2,7 @@ package lxd import ( "fmt" + "net/url" "strings" "github.com/lxc/lxd/shared/api" @@ -47,7 +48,7 @@ func (r *ProtocolLXD) GetProfile(name string) (*api.Profile, string, error) { profile := api.Profile{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/profiles/%s", name), nil, "", &profile) + etag, err := r.queryStruct("GET", fmt.Sprintf("/profiles/%s", url.QueryEscape(name)), nil, "", &profile) if err != nil { return nil, "", err } @@ -69,7 +70,7 @@ func (r *ProtocolLXD) CreateProfile(profile api.ProfilesPost) error { // UpdateProfile updates the profile to match the provided Profile struct func (r *ProtocolLXD) UpdateProfile(name string, profile api.ProfilePut, ETag string) error { // Send the request - _, _, err := r.query("PUT", fmt.Sprintf("/profiles/%s", name), profile, ETag) + _, _, err := r.query("PUT", fmt.Sprintf("/profiles/%s", url.QueryEscape(name)), profile, ETag) if err != nil { return err } @@ -80,7 +81,7 @@ func (r *ProtocolLXD) UpdateProfile(name string, profile api.ProfilePut, ETag st // RenameProfile renames an existing profile entry func (r *ProtocolLXD) RenameProfile(name string, profile api.ProfilePost) error { // Send the request - _, _, err := r.query("POST", fmt.Sprintf("/profiles/%s", name), profile, "") + _, _, err := r.query("POST", fmt.Sprintf("/profiles/%s", url.QueryEscape(name)), profile, "") if err != nil { return err } @@ -91,7 +92,7 @@ func (r *ProtocolLXD) RenameProfile(name string, profile api.ProfilePost) error // DeleteProfile deletes a profile func (r *ProtocolLXD) DeleteProfile(name string) error { // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/profiles/%s", name), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/profiles/%s", url.QueryEscape(name)), nil, "") if err != nil { return err } diff --git a/client/lxd_storage_pools.go b/client/lxd_storage_pools.go index 661371efe..8e10288f1 100644 --- a/client/lxd_storage_pools.go +++ b/client/lxd_storage_pools.go @@ -2,6 +2,7 @@ package lxd import ( "fmt" + "net/url" "strings" "github.com/lxc/lxd/shared/api" @@ -51,7 +52,7 @@ func (r *ProtocolLXD) GetStoragePool(name string) (*api.StoragePool, string, err pool := api.StoragePool{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s", name), nil, "", &pool) + etag, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s", url.QueryEscape(name)), nil, "", &pool) if err != nil { return nil, "", err } @@ -81,7 +82,7 @@ func (r *ProtocolLXD) CreateStoragePool(pool api.StoragePoolsPost) error { // UpdateStoragePool updates the pool to match the provided StoragePool struct func (r *ProtocolLXD) UpdateStoragePool(name string, pool api.StoragePoolPut, ETag string) error { // Send the request - _, _, err := r.query("PUT", fmt.Sprintf("/storage-pools/%s", name), pool, ETag) + _, _, err := r.query("PUT", fmt.Sprintf("/storage-pools/%s", url.QueryEscape(name)), pool, ETag) if err != nil { return err } @@ -92,7 +93,7 @@ func (r *ProtocolLXD) UpdateStoragePool(name string, pool api.StoragePoolPut, ET // DeleteStoragePool deletes a storage pool func (r *ProtocolLXD) DeleteStoragePool(name string) error { // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/storage-pools/%s", name), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/storage-pools/%s", url.QueryEscape(name)), nil, "") if err != nil { return err } @@ -109,7 +110,7 @@ func (r *ProtocolLXD) GetStoragePoolResources(name string) (*api.ResourcesStorag res := api.ResourcesStoragePool{} // Fetch the raw value - _, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s/resources", name), nil, "", &res) + _, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s/resources", url.QueryEscape(name)), nil, "", &res) if err != nil { return nil, err } diff --git a/client/lxd_storage_volumes.go b/client/lxd_storage_volumes.go index 92f88cccf..1aa576e7f 100644 --- a/client/lxd_storage_volumes.go +++ b/client/lxd_storage_volumes.go @@ -2,6 +2,7 @@ package lxd import ( "fmt" + "net/url" "strings" "github.com/lxc/lxd/shared/api" @@ -18,15 +19,15 @@ func (r *ProtocolLXD) GetStoragePoolVolumeNames(pool string) ([]string, error) { urls := []string{} // Fetch the raw value - _, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s/volumes", pool), nil, "", &urls) + _, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s/volumes", url.QueryEscape(pool)), nil, "", &urls) if err != nil { return nil, err } // Parse it names := []string{} - for _, url := range urls { - fields := strings.Split(url, fmt.Sprintf("/storage-pools/%s/volumes/", pool)) + for _, uri := range urls { + fields := strings.Split(uri, fmt.Sprintf("/storage-pools/%s/volumes/", url.QueryEscape(pool))) names = append(names, fields[len(fields)-1]) } @@ -38,7 +39,7 @@ func (r *ProtocolLXD) GetStoragePoolVolumes(pool string) ([]api.StorageVolume, e volumes := []api.StorageVolume{} // Fetch the raw value - _, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s/volumes?recursion=1", pool), nil, "", &volumes) + _, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s/volumes?recursion=1", url.QueryEscape(pool)), nil, "", &volumes) if err != nil { return nil, err } @@ -51,7 +52,7 @@ func (r *ProtocolLXD) GetStoragePoolVolume(pool string, volType string, name str volume := api.StorageVolume{} // Fetch the raw value - etag, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s/volumes/%s/%s", pool, volType, name), nil, "", &volume) + etag, err := r.queryStruct("GET", fmt.Sprintf("/storage-pools/%s/volumes/%s/%s", url.QueryEscape(pool), url.QueryEscape(volType), url.QueryEscape(name)), nil, "", &volume) if err != nil { return nil, "", err } @@ -62,7 +63,7 @@ func (r *ProtocolLXD) GetStoragePoolVolume(pool string, volType string, name str // CreateStoragePoolVolume defines a new storage volume func (r *ProtocolLXD) CreateStoragePoolVolume(pool string, volume api.StorageVolumesPost) error { // Send the request - _, _, err := r.query("POST", fmt.Sprintf("/storage-pools/%s/volumes/%s", pool, volume.Type), volume, "") + _, _, err := r.query("POST", fmt.Sprintf("/storage-pools/%s/volumes/%s", url.QueryEscape(pool), url.QueryEscape(volume.Type)), volume, "") if err != nil { return err } @@ -73,7 +74,7 @@ func (r *ProtocolLXD) CreateStoragePoolVolume(pool string, volume api.StorageVol // UpdateStoragePoolVolume updates the volume to match the provided StoragePoolVolume struct func (r *ProtocolLXD) UpdateStoragePoolVolume(pool string, volType string, name string, volume api.StorageVolumePut, ETag string) error { // Send the request - _, _, err := r.query("PUT", fmt.Sprintf("/storage-pools/%s/volumes/%s/%s", pool, volType, name), volume, ETag) + _, _, err := r.query("PUT", fmt.Sprintf("/storage-pools/%s/volumes/%s/%s", url.QueryEscape(pool), url.QueryEscape(volType), url.QueryEscape(name)), volume, ETag) if err != nil { return err } @@ -84,7 +85,7 @@ func (r *ProtocolLXD) UpdateStoragePoolVolume(pool string, volType string, name // DeleteStoragePoolVolume deletes a storage pool func (r *ProtocolLXD) DeleteStoragePoolVolume(pool string, volType string, name string) error { // Send the request - _, _, err := r.query("DELETE", fmt.Sprintf("/storage-pools/%s/volumes/%s/%s", pool, volType, name), nil, "") + _, _, err := r.query("DELETE", fmt.Sprintf("/storage-pools/%s/volumes/%s/%s", url.QueryEscape(pool), url.QueryEscape(volType), url.QueryEscape(name)), nil, "") if err != nil { return err } @@ -99,7 +100,7 @@ func (r *ProtocolLXD) RenameStoragePoolVolume(pool string, volType string, name } // Send the request - _, _, err := r.query("POST", fmt.Sprintf("/storage-pools/%s/volumes/%s/%s", pool, volType, name), volume, "") + _, _, err := r.query("POST", fmt.Sprintf("/storage-pools/%s/volumes/%s/%s", url.QueryEscape(pool), url.QueryEscape(volType), url.QueryEscape(name)), volume, "") if err != nil { return err }
_______________________________________________ lxc-devel mailing list [email protected] http://lists.linuxcontainers.org/listinfo/lxc-devel
