HTTP/HTTPS load balancer includes port number with hostname

We use Apigee X and have a custom domain setup for our Integrated Portal (using these instructions). I have things setup so non http requests are redirected to https, and requests with www (either http or https) are redirected to the https non-www domain.

I noticed recently that when the load balancer responds with a HTTP 301 redirect, the URL in the location header and in the response body appends ":443" to end the URL. Of course, it functions all the same, and Chrome at least removes that port from the address bar, so no harm. But I am curious why the load balancer started doing this. We haven't made any changes to this configuration but it seems like the load balancer started appending the port number at some point.

In any case, does anyone know if it's possible to remove the port number from the URL sent back with the redirect response?

Here's a snippet of the terraform we use to configure this:

variable "developer_portal_hostname" {
  type        = string
  description = "Developer portal hostname."
  default     = "developer.example.com"
}

variable "backend_integrated_portal_hostname" {
  type        = string
  description = "Default hostname for Apigee integrated portal. https://cloud.google.com/apigee/docs/api-platform/publish/portal/custom-domain#default-host"
  default     = "example.apigee.io"
}

resource "google_compute_global_network_endpoint_group" "this" {
  name                  = "apigee-developer-portal"
  network_endpoint_type = "INTERNET_FQDN_PORT"
}

resource "google_compute_global_network_endpoint" "this" {
  global_network_endpoint_group = google_compute_global_network_endpoint_group.this.name
  port                          = 0
  fqdn                          = var.backend_integrated_portal_hostname
}

resource "google_compute_backend_service" "this" {
  provider = google-beta
  name     = "apigee-developer-portal"
  protocol = "HTTPS"

  backend {
    group = google_compute_global_network_endpoint_group.this.id
  }
}

resource "google_compute_global_address" "this" {
  name         = "apigee-developer-portal"
  ip_version   = "IPV4"
  address_type = "EXTERNAL"
}


resource "google_compute_global_forwarding_rule" "https" {
  provider   = google-beta
  name       = "apigee-developer-portal"
  target     = google_compute_target_https_proxy.https.id
  ip_address = google_compute_global_address.this.address
  port_range = "443"
}

resource "google_compute_url_map" "https" {
  name            = "apigee-developer-portal"
  default_service = google_compute_backend_service.this.id

  host_rule {
    hosts        = ["www.${var.developer_portal_hostname}"]
    path_matcher = "www"
  }

  path_matcher {
    name = "www"
    default_url_redirect {
      host_redirect          = var.developer_portal_hostname
      https_redirect         = true
      redirect_response_code = "MOVED_PERMANENTLY_DEFAULT"
      strip_query            = false
    }
  }

  default_route_action {
    url_rewrite {
      host_rewrite = var.backend_integrated_portal_hostname
    }
  }
}

resource "google_compute_target_https_proxy" "https" {
  name    = "apigee-developer-portal"
  url_map = google_compute_url_map.https.id

  ssl_certificates = [google_compute_managed_ssl_certificate.this.id]
}

resource "google_compute_global_forwarding_rule" "http" {
  provider   = google-beta
  name       = "apigee-developer-portal-non-tls"
  target     = google_compute_target_http_proxy.http.id
  ip_address = google_compute_global_address.this.address
  port_range = "80"
}

resource "google_compute_target_http_proxy" "http" {
  name    = "apigee-developer-portal-non-tls"
  url_map = google_compute_url_map.http.id
}

resource "google_compute_url_map" "http" {
  name = "apigee-developer-portal-non-tls"

  # Redirect all non-https requests to https.
  default_url_redirect {
    host_redirect          = var.developer_portal_hostname
    https_redirect         = true
    redirect_response_code = "MOVED_PERMANENTLY_DEFAULT"
    strip_query            = false
  }
}

resource "google_compute_managed_ssl_certificate" "this" {
  name = "apigee-developer-portal"

  managed {
    domains = [
      var.developer_portal_hostname,
      "www.${var.developer_portal_hostname}"
    ]
  }
}

 

1 9 1,472
9 REPLIES 9

The HTTP 301 code happens because the Enable HTTP to HTTPS Redirect checkbox was selected when the load balancer was created, so when one client points to http instead of https, the load balancer redirects the request to https with the http 301 code, but you can customize this code to use 302 or 308. 

If you want to stop receiving this code, you will need to recreate your load balancer without enabling the HTTP to HTTPS Redirect checkbox. In this link, you can read more about how the HTTP-HTTPS load balancer uses the 301 code to redirect traffic .

 

 

Thanks for the reply. The redirect behavior is expected since this is how I intended to set it up. What I’m wondering about is why the URL sent back in the Location response header, as well as the html response body, contains the port number (443). I don’t believe it has always done this, but regardless, I’d like to revert it so it doesn’t contain the port number unless there is some best practice I’m overlooking. 

Regarding why the URL sent back the Location response header, as well as the html response body with the port number (443), it is because the load balancer is forcing the port to forward to https instead of http, so it is normal behavior. Also, you could force manually the forwarding like this:  http://google.com:443, some browsers like Google Chrome can use Strict-Transport-Security HTTP Header , which informs the browser that "this site is supposed to be accessed only via HTTPS.” This policy mechanism helps to protect websites and automatically redirect an insecure link (http) to an secure link (https). It is worth mentioning that perhaps you will need to upgrade your other browsers to their latest version in order to support STS. Also, you can follow this guide as a best practice to deploy an external LB with HTTP redirect to HTTPS in GCP with a Terraform module.

 

The documentation for the google_compute_url_map says for https_redirect: "If set to true, the URL scheme in the redirected request is set to https."

This just says the URL scheme is changed, it doesn't say anything about the port number. Like I mentioned, the fact that we're getting the port number now and were not before isn't a big deal. What I was more concerned about is why the change happened, and whether it was documented anywhere that this is expected behavior.

For now, I'll update our integration tests to reflect this new behavior.

 

Same problem here, and it seems to cause problems with third party tools.
The documentation reports an example without "443", we just want something like this.

ludovicogrossi_1-1680192411259.png

 

Hi, Is there any update on this, we're experiencing this with our sites... Our SEO partners are seeing if we can remove the port.

We create the LB using Terraform

resource "google_compute_url_map" "http" {
name        = "${var.project.prefix}-${var.project.env}-http-map"
description = "${var.project.name} ${var.project.env} HTTP Map"

// Send to the HTTPS version
default_url_redirect {
https_redirect = true
strip_query    = false
}
}

Then a curl test comes back with  

curl -i http://{site-redacted}

HTTP/1.1 301 Moved Permanently
Cache-Control: private
Location: https://{site-redacted}:443/
Content-Length: 0
Date: Wed, 28 Jun 2023 13:56:21 GMT
Content-Type: text/html; charset=UTF-8

 We're really after a response like 

Location: https://{site-redacted}/

Thanks

We are also facing the same issue. http to https includes the 443 port in the URL. it is now affecting our SEO performance. Any idea how to resolve this issue 

Is there a way to summon someone from Google to comment on this post? It seems like the original googler doesn't work here anymore.

facing the same issue... our SEO team asks us to remove the port from the location header.