commit
						83b0eeefde
					
				| 
						 | 
					@ -25,11 +25,11 @@ var (
 | 
				
			||||||
	ErrLoginRequired         = errors.New("Authentication is required.")
 | 
						ErrLoginRequired         = errors.New("Authentication is required.")
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func pingRegistryEndpoint(endpoint string) error {
 | 
					func pingRegistryEndpoint(endpoint string) (bool, error) {
 | 
				
			||||||
	if endpoint == auth.IndexServerAddress() {
 | 
						if endpoint == auth.IndexServerAddress() {
 | 
				
			||||||
		// Skip the check, we now this one is valid
 | 
							// Skip the check, we now this one is valid
 | 
				
			||||||
		// (and we never want to fallback to http in case of error)
 | 
							// (and we never want to fallback to http in case of error)
 | 
				
			||||||
		return nil
 | 
							return false, nil
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	httpDial := func(proto string, addr string) (net.Conn, error) {
 | 
						httpDial := func(proto string, addr string) (net.Conn, error) {
 | 
				
			||||||
		// Set the connect timeout to 5 seconds
 | 
							// Set the connect timeout to 5 seconds
 | 
				
			||||||
| 
						 | 
					@ -45,14 +45,26 @@ func pingRegistryEndpoint(endpoint string) error {
 | 
				
			||||||
	client := &http.Client{Transport: httpTransport}
 | 
						client := &http.Client{Transport: httpTransport}
 | 
				
			||||||
	resp, err := client.Get(endpoint + "_ping")
 | 
						resp, err := client.Get(endpoint + "_ping")
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		return err
 | 
							return false, err
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	defer resp.Body.Close()
 | 
						defer resp.Body.Close()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if resp.Header.Get("X-Docker-Registry-Version") == "" {
 | 
						if resp.Header.Get("X-Docker-Registry-Version") == "" {
 | 
				
			||||||
		return errors.New("This does not look like a Registry server (\"X-Docker-Registry-Version\" header not found in the response)")
 | 
							return false, errors.New("This does not look like a Registry server (\"X-Docker-Registry-Version\" header not found in the response)")
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	return nil
 | 
					
 | 
				
			||||||
 | 
						standalone := resp.Header.Get("X-Docker-Registry-Standalone")
 | 
				
			||||||
 | 
						utils.Debugf("Registry standalone header: '%s'", standalone)
 | 
				
			||||||
 | 
						// If the header is absent, we assume true for compatibility with earlier
 | 
				
			||||||
 | 
						// versions of the registry
 | 
				
			||||||
 | 
						if standalone == "" {
 | 
				
			||||||
 | 
							return true, nil
 | 
				
			||||||
 | 
						// Accepted values are "true" (case-insensitive) and "1".
 | 
				
			||||||
 | 
						} else if strings.EqualFold(standalone, "true") || standalone == "1" {
 | 
				
			||||||
 | 
							return true, nil
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						// Otherwise, not standalone
 | 
				
			||||||
 | 
						return false, nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func validateRepositoryName(repositoryName string) error {
 | 
					func validateRepositoryName(repositoryName string) error {
 | 
				
			||||||
| 
						 | 
					@ -122,16 +134,16 @@ func ExpandAndVerifyRegistryUrl(hostname string) (string, error) {
 | 
				
			||||||
			// there is no path given. Expand with default path
 | 
								// there is no path given. Expand with default path
 | 
				
			||||||
			hostname = hostname + "/v1/"
 | 
								hostname = hostname + "/v1/"
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		if err := pingRegistryEndpoint(hostname); err != nil {
 | 
							if _, err := pingRegistryEndpoint(hostname); err != nil {
 | 
				
			||||||
			return "", errors.New("Invalid Registry endpoint: " + err.Error())
 | 
								return "", errors.New("Invalid Registry endpoint: " + err.Error())
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		return hostname, nil
 | 
							return hostname, nil
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	endpoint := fmt.Sprintf("https://%s/v1/", hostname)
 | 
						endpoint := fmt.Sprintf("https://%s/v1/", hostname)
 | 
				
			||||||
	if err := pingRegistryEndpoint(endpoint); err != nil {
 | 
						if _, err := pingRegistryEndpoint(endpoint); err != nil {
 | 
				
			||||||
		utils.Debugf("Registry %s does not work (%s), falling back to http", endpoint, err)
 | 
							utils.Debugf("Registry %s does not work (%s), falling back to http", endpoint, err)
 | 
				
			||||||
		endpoint = fmt.Sprintf("http://%s/v1/", hostname)
 | 
							endpoint = fmt.Sprintf("http://%s/v1/", hostname)
 | 
				
			||||||
		if err = pingRegistryEndpoint(endpoint); err != nil {
 | 
							if _, err = pingRegistryEndpoint(endpoint); err != nil {
 | 
				
			||||||
			//TODO: triggering highland build can be done there without "failing"
 | 
								//TODO: triggering highland build can be done there without "failing"
 | 
				
			||||||
			return "", errors.New("Invalid Registry endpoint: " + err.Error())
 | 
								return "", errors.New("Invalid Registry endpoint: " + err.Error())
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
| 
						 | 
					@ -682,13 +694,19 @@ func NewRegistry(authConfig *auth.AuthConfig, factory *utils.HTTPRequestFactory,
 | 
				
			||||||
		return nil, err
 | 
							return nil, err
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	// If we're working with a private registry over HTTPS, send Basic Auth headers
 | 
						// If we're working with a standalone private registry over HTTPS, send Basic Auth headers
 | 
				
			||||||
	// alongside our requests.
 | 
						// alongside our requests.
 | 
				
			||||||
	if indexEndpoint != auth.IndexServerAddress() && strings.HasPrefix(indexEndpoint, "https://") {
 | 
						if indexEndpoint != auth.IndexServerAddress() && strings.HasPrefix(indexEndpoint, "https://") {
 | 
				
			||||||
 | 
							standalone, err := pingRegistryEndpoint(indexEndpoint)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return nil, err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							if standalone {
 | 
				
			||||||
			utils.Debugf("Endpoint %s is eligible for private registry auth. Enabling decorator.", indexEndpoint)
 | 
								utils.Debugf("Endpoint %s is eligible for private registry auth. Enabling decorator.", indexEndpoint)
 | 
				
			||||||
			dec := utils.NewHTTPAuthDecorator(authConfig.Username, authConfig.Password)
 | 
								dec := utils.NewHTTPAuthDecorator(authConfig.Username, authConfig.Password)
 | 
				
			||||||
			factory.AddDecorator(dec)
 | 
								factory.AddDecorator(dec)
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	r.reqFactory = factory
 | 
						r.reqFactory = factory
 | 
				
			||||||
	return r, nil
 | 
						return r, nil
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -23,10 +23,11 @@ func spawnTestRegistry(t *testing.T) *Registry {
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func TestPingRegistryEndpoint(t *testing.T) {
 | 
					func TestPingRegistryEndpoint(t *testing.T) {
 | 
				
			||||||
	err := pingRegistryEndpoint(makeURL("/v1/"))
 | 
						standalone, err := pingRegistryEndpoint(makeURL("/v1/"))
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		t.Fatal(err)
 | 
							t.Fatal(err)
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
						assertEqual(t, standalone, true, "Expected standalone to be true (default)")
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func TestGetRemoteHistory(t *testing.T) {
 | 
					func TestGetRemoteHistory(t *testing.T) {
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue