func download(url, dir string, hostnameVerification utils.SSLHostnameVerification) (file *os.File, err error) { if dir == "" { dir = os.TempDir() } tempFile, err := ioutil.TempFile(dir, "inprogress-") if err != nil { return nil, err } defer func() { if err != nil { cleanTempFile(tempFile) } }() // TODO(rog) make the download operation interruptible. client := utils.GetHTTPClient(hostnameVerification) resp, err := client.Get(url) if err != nil { return nil, err } defer resp.Body.Close() if resp.StatusCode != http.StatusOK { return nil, fmt.Errorf("bad http response: %v", resp.Status) } _, err = io.Copy(tempFile, resp.Body) if err != nil { return nil, err } if _, err := tempFile.Seek(0, 0); err != nil { return nil, err } return tempFile, nil }
func (c *updateCloudsCommand) Run(ctxt *cmd.Context) error { fmt.Fprint(ctxt.Stdout, "Fetching latest public cloud list... ") client := utils.GetHTTPClient(utils.VerifySSLHostnames) resp, err := client.Get(c.publicCloudURL) if err != nil { return err } defer resp.Body.Close() noNewClouds := "\nno new public cloud information available at this time" if resp.StatusCode != http.StatusOK { switch resp.StatusCode { case http.StatusNotFound: fmt.Fprintln(ctxt.Stdout, noNewClouds) return nil case http.StatusUnauthorized: return errors.Unauthorizedf("unauthorised access to URL %q", c.publicCloudURL) } return fmt.Errorf("cannot read public cloud information at URL %q, %q", c.publicCloudURL, resp.Status) } cloudData, err := decodeCheckSignature(resp.Body, c.publicSigningKey) if err != nil { return errors.Annotate(err, "error receiving updated cloud data") } newPublicClouds, err := jujucloud.ParseCloudMetadata(cloudData) if err != nil { return errors.Annotate(err, "invalid cloud data received when updating clouds") } currentPublicClouds, _, err := jujucloud.PublicCloudMetadata(jujucloud.JujuPublicCloudsPath()) if err != nil { return errors.Annotate(err, "invalid local public cloud data") } sameCloudInfo, err := jujucloud.IsSameCloudMetadata(newPublicClouds, currentPublicClouds) if err != nil { // Should never happen. return err } if sameCloudInfo { fmt.Fprintln(ctxt.Stdout, noNewClouds) return nil } if err := jujucloud.WritePublicCloudMetadata(newPublicClouds); err != nil { return errors.Annotate(err, "error writing new local public cloud data") } fmt.Fprintln(ctxt.Stdout, "done.") return nil }
func (u *Upgrader) ensureTools(agentTools *coretools.Tools, hostnameVerification utils.SSLHostnameVerification) error { logger.Infof("fetching tools from %q", agentTools.URL) client := utils.GetHTTPClient(hostnameVerification) resp, err := client.Get(agentTools.URL) if err != nil { return err } defer resp.Body.Close() if resp.StatusCode != http.StatusOK { return fmt.Errorf("bad HTTP response: %v", resp.Status) } err = agenttools.UnpackTools(u.dataDir, agentTools, resp.Body) if err != nil { return fmt.Errorf("cannot unpack tools: %v", err) } logger.Infof("unpacked tools %s to %s", agentTools.Version, u.dataDir) return nil }
// Fetch is defined in simplestreams.DataSource. func (h *urlDataSource) Fetch(path string) (io.ReadCloser, string, error) { dataURL := urlJoin(h.baseURL, path) client := utils.GetHTTPClient(h.hostnameVerification) // dataURL can be http:// or file:// resp, err := client.Get(dataURL) if err != nil { logger.Debugf("Got error requesting %q: %v", dataURL, err) return nil, dataURL, errors.NotFoundf("invalid URL %q", dataURL) } if resp.StatusCode == http.StatusNotFound { return nil, dataURL, errors.NotFoundf("cannot find URL %q", dataURL) } if resp.StatusCode == http.StatusUnauthorized { return nil, dataURL, errors.Unauthorizedf("unauthorised access to URL %q", dataURL) } if resp.StatusCode != http.StatusOK { return nil, dataURL, fmt.Errorf("cannot access URL %q, %q", dataURL, resp.Status) } return resp.Body, dataURL, nil }
// sendTools streams the tools tarball to the client. func (h *toolsDownloadHandler) sendTools(w http.ResponseWriter, statusCode int, tools *tools.Tools, verify utils.SSLHostnameVerification) { client := utils.GetHTTPClient(verify) resp, err := client.Get(tools.URL) if err != nil { h.sendError(w, http.StatusBadRequest, fmt.Sprintf("failed to get %q: %v", tools.URL, err)) return } defer resp.Body.Close() data, err := ioutil.ReadAll(resp.Body) if err != nil { h.sendError(w, http.StatusBadRequest, fmt.Sprintf("failed to read tools: %v", err)) return } w.Header().Set("Content-Type", "application/x-gtar") w.Header().Set("Content-Length", fmt.Sprint(len(data))) w.WriteHeader(statusCode) if _, err := w.Write(data); err != nil { h.sendError(w, http.StatusBadRequest, fmt.Sprintf("failed to write tools: %v", err)) return } }
// Fetch is defined in simplestreams.DataSource. func (h *urlDataSource) Fetch(path string) (io.ReadCloser, string, error) { dataURL := urlJoin(h.baseURL, path) client := utils.GetHTTPClient(h.hostnameVerification) // dataURL can be http:// or file:// // MakeFileURL will only modify the URL if it's a file URL dataURL = utils.MakeFileURL(dataURL) resp, err := client.Get(dataURL) if err != nil { logger.Tracef("Got error requesting %q: %v", dataURL, err) return nil, dataURL, errors.NotFoundf("invalid URL %q", dataURL) } if resp.StatusCode != http.StatusOK { resp.Body.Close() switch resp.StatusCode { case http.StatusNotFound: return nil, dataURL, errors.NotFoundf("cannot find URL %q", dataURL) case http.StatusUnauthorized: return nil, dataURL, errors.Unauthorizedf("unauthorised access to URL %q", dataURL) } return nil, dataURL, fmt.Errorf("cannot access URL %q, %q", dataURL, resp.Status) } return resp.Body, dataURL, nil }
func (s *httpSuite) TestNonValidatingClientGetter(c *gc.C) { client1 := utils.GetNonValidatingHTTPClient() client2 := utils.GetHTTPClient(utils.NoVerifySSLHostnames) c.Check(client1, gc.Equals, client2) }