Endpoint config when deploying to Gigalixir using mix

Hi
Just after the ‘secret sauce’ to get my links working correctly after the app is deployed. They all stubbornly display localhost

Here’s where I’ve been with prod.exs

url: ["${APP_NAME}.gigalixirapp.com"] I’m deploying with mix not distillery and I think this is the config for the latter

APP_NAME is available by default, and so I tried

url: ["#{System.get_env("APP_NAME")}.gigalixirapp.com"] but no luck

and of course

url: ["example.com"] which is where I started from

At a loss to know what to try next. Something so simple seems very opaque in the docs and it’s not always clear with other resources which of the three deploy methods the author is using. And lots of the help resources are now dated.

Not sure to include PORT or not. Sometimes it’s included and other times not. I have this in prod.exs too

http: [port: {:system, "PORT"}]

Any help welcomed.

2 Likes
# prod.exs
config :bob_versions_web, BobVersionsWeb.Endpoint,
  http: [:inet6, port: System.get_env("PORT") || 4000],
  url: [scheme: "https", port: 443],
  force_ssl: [rewrite_on: [:x_forwarded_proto], host: nil],
  check_origin: ["//*.kobrakai.de", "//*.gigalixirapp.com"]

# releases.exs
config :bob_versions_web, BobVersionsWeb.Endpoint,
  secret_key_base: System.fetch_env!("SECRET_KEY_BASE")

This is what I deploy to gigalixir using releases.

Generally you should not need to configure url: [host: …] unless you’re using MyAppWeb.Endpoint for url generation (of non-relative paths) instead of a conn. The latter does hold the current request host and simply uses that one.

4 Likes

Oh :slight_smile:

I use MyAppWeb.Endpoint when I use a path helper (Routes) to create a url to display.

Not so many though, so I’ll refactor and use the conn instead and hope that’ll fix it.

Thanks!

Changed my url generating code to use conn instead of MyAppWeb.Endpoint.

From:
Routes.v1_authentication_url(MyAppWeb.Endpoint, :register)
To:
Routes.v1_authentication_url(conn, :register)

Switched prod.exs back from whence it came
url: [nil, port: 80],

Behaviour of deployed app unchanged :frowning:
http://localhost/api/v1/register

The config follows the docs
https://gigalixir.readthedocs.io/en/latest/modify-app/mix.html#modifying-existing-app-with-mix

“Whenever possible prefer to pass a conn (or @conn in your views) in place of an Endpoint .”
https://hexdocs.pm/phoenix/routing.html#more-on-path-helpers

Hmmm,

On the server

IO.inspect(conn.host)
app_name.gigalixir.com (also set in the req headers)

But,
IO.inspect(Routes.v1_authentication_url(conn, :register))
http://localhost/

I’m clearly missing something fundamental to how the path helpers work … will investigate

Phoenix.Router.Helpers matches on %Conn{private: private}. There are 2 possibles for private either %{phoenix_router_url: _} or %{phoenix_endpoint: _}.

My conn only has phoenix_endpoint set. The upshot is a call to endpoint.url() in Phoenix.Endpoint. Which gets it’s info from prod.exs and defaults to [host: "localhost", path: "/"]

So, I’m still no further forward. I’m not sure how url [nil, port:80] in the Gigalixir docs works - clearly in my case it doesn’t.

I need my links to work, so I’m going to fallback to simply String replacing with a hardcoded app name on the result of the helper. If anyone can throw light on why my config doesn’t work I’d be interested to learn more.

Maybe I was wrong with the host of the conn being picked up. The one app I have in production with urls (emails) needs to deal with subdomains, so I have handling for that anyways.

If all you have is one domain you can set it to url: [host: "wherever_domain.com"]. That’s at least better than using some string replacement.

I’ve had to literally replace localhost with this tiny helper to make progress. Would like the permanent fix, but this works.

def route(route) do
case Mix.env() do
:prod →
String.replace_leading(route,“http://localhost”, “https://my-app-name.gigalixirapp.com”)
_ → route
end
end

I did try that among the various options - just hard coding the Gigalixir app name like that. But it didn’t get picked up. There must be something else that’s wrong somewhere. Time to move on :slight_smile:

Are you sure you added it to url: […] and not http: []? The :url config is meant for that exact case.

1 Like

I’m never sure when it comes to deployment, but happens you’re right! I thought I’d tried that, but clearly I hadn’t. Thanks for making me persist +1

Ha, ha, just when you thought it was safe … Gigalixir logs have gone a little bit daft. Failing health checks on port 4000 although I’ve moved to using url: [host: "my-app-name.gigalixirapp.com", port: 4000]

I’m going to write to Gigalixir and ask them for the vanilla mix config set-up guaranteed to work and support path helpers. I’ll copy their reply here.

You don’t want port 4000 for the url, but 80 or 443 depending on if you use http or https.

:url is the config used only for url generation. Ports for urls look like this: example.com:4000 unless the scheme is http and the port 80 or the scheme https and the port 443, when the port is skipped.

All this is completely separate from configuring where phoenix listens on incoming requests, which is configured on the :http/:https key. Here you want to set the port to something gigalixir routes requests to.

1 Like

I was just in the process of trying 80 (having tried 443 last night). The logs just kept complaining that Your app is failing health checks, which means it isn't listening on port 4000 which confused me - not hard admittedly.

80 is working. The generated urls don’t show the port number even though the app is served through https.

That error is about the listening port though, therefore completely unrelated with how you configure :url.

Yeah, the app has been deployed and working for a while, it was just touching the url config that was causing the probs. This seems to have fixed it. Very simple, but not in the Gigalixir docs nor any tutorial that I’ve been able to find. No doubt I will find the very instruction in hindsight - everything is so blindingly obvious then :slight_smile:

1 Like

Hey, I have the same problem with Gigalixir :slightly_smiling_face:
Your app is failing health checks, which means it isn't listening on port 4000

How did you handle it? Add any healthcheck endpoint?
I could find anything related in Gigalixir docs too :slightly_smiling_face: