Skip to content

Commit

Permalink
add support for fargate
Browse files Browse the repository at this point in the history
  • Loading branch information
simongottschlag committed Nov 6, 2023
1 parent 475ac6b commit b58563d
Show file tree
Hide file tree
Showing 3 changed files with 103 additions and 3 deletions.
72 changes: 69 additions & 3 deletions src/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,27 @@ func run(ctx context.Context, cfg config) error {
r.URL.Scheme = registryURL.Scheme
}

httpClient := &http.Client{
Transport: &http.Transport{
MaxIdleConns: 20,
MaxConnsPerHost: 20,
},
}
rp.ModifyResponse = func(res *http.Response) error {
user, _, ok := res.Request.BasicAuth()
if !ok {
return nil
}

if !strings.HasPrefix(user, "fargate") {
return nil
}

// NOTE: Fargate doesn't support redirects, so we need to rewrite the request.
// This is a really ugly hack, but it works for now.
return rewriteFargateRequest(httpClient, res)
}

v2 := r.Group("/v2")
v2.HEAD("*path", func(c *gin.Context) {
c.Status(http.StatusOK)
Expand All @@ -121,16 +142,15 @@ func run(ctx context.Context, cfg config) error {
if c.Request.URL.Path == "/v2" || c.Request.URL.Path == "/v2/" {
c.Writer.Header().Set("Www-Authenticate", fmt.Sprintf(`Basic realm="https://%s", service="%s"`, c.Request.Host, c.Request.Host))
c.Writer.Header().Set("Docker-Distribution-Api-Version", "registry/2.0")
c.Status(http.StatusUnauthorized)
c.JSON(http.StatusUnauthorized, generateDistributionError("UNAUTHORIZED", "authentication required"))
return
}

_, token, ok := c.Request.BasicAuth()
if !ok || token == "" {
c.Writer.Header().Set("Www-Authenticate", fmt.Sprintf(`Basic realm="https://%s", service="%s"`, c.Request.Host, c.Request.Host))
c.Writer.Header().Set("Docker-Distribution-Api-Version", "registry/2.0")
//nolint:errcheck // ignore
c.AbortWithError(http.StatusUnauthorized, fmt.Errorf("unable to extract token from basic auth"))
c.JSON(http.StatusUnauthorized, generateDistributionError("UNAUTHORIZED", "authentication required"))
return
}

Expand Down Expand Up @@ -174,6 +194,52 @@ func run(ctx context.Context, cfg config) error {
return g.Wait()
}

// rewriteFargateRequest rewrites the request to follow the redirect
func rewriteFargateRequest(httpClient *http.Client, res *http.Response) error {
if res.StatusCode != http.StatusTemporaryRedirect {
return nil
}

location := res.Header.Get("Location")
if location == "" {
return nil
}

locationURL, err := url.Parse(location)
if err != nil {
return nil
}

req, err := http.NewRequestWithContext(res.Request.Context(), http.MethodGet, locationURL.String(), http.NoBody)
if err != nil {
return nil
}

newRes, err := http.DefaultClient.Do(req)
if err != nil {
return nil
}

res.Header = newRes.Header
res.StatusCode = newRes.StatusCode
res.Status = newRes.Status
res.ContentLength = newRes.ContentLength
res.Body = newRes.Body

return nil
}

func generateDistributionError(code string, message string) gin.H {
return gin.H{
"errors": []gin.H{
{
"code": code,
"message": message,
},
},
}
}

type config struct {
Address string `json:"address" arg:"--address,env:ADDRESS" default:":8080" help:"The address to listen on."`
AzureContainerRegistryName string `json:"azure_container_registry_name" arg:"--azure-container-registry-name,env:AZURE_CONTAINER_REGISTRY_NAME,required" help:"The name of the Azure Container Registry that should be proxied."`
Expand Down
19 changes: 19 additions & 0 deletions terraform/.terraform.lock.hcl

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

15 changes: 15 additions & 0 deletions terraform/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,11 @@ resource "azurerm_container_registry" "this" {
admin_enabled = true
}

resource "random_password" "acr_proxy_static_secret" {
length = 32
special = false
}

resource "azurerm_container_app" "this" {
name = "acr-proxy"
container_app_environment_id = azurerm_container_app_environment.this.id
Expand Down Expand Up @@ -109,6 +114,11 @@ resource "azurerm_container_app" "this" {
name = "AZURE_CONTAINER_REGISTRY_PASSWORD"
secret_name = "container-registry-password"
}

env {
name = "STATIC_SECRET"
secret_name = "static-secret"
}
}
}

Expand All @@ -126,6 +136,11 @@ resource "azurerm_container_app" "this" {
value = azurerm_container_registry.this.admin_password
}

secret {
name = "static-secret"
value = random_password.acr_proxy_static_secret.result
}

registry {
server = azurerm_container_registry.this.login_server
password_secret_name = "container-registry-password"
Expand Down

0 comments on commit b58563d

Please sign in to comment.