c.ClientIP always returns 127.0.0.1

Hello,

I am using go and gin following this doc: Deploy a Go Gin Web Server | Render.

I’ve got a simple version of my app up and running and I want to log the IP of clients making requests to my service. My problem is that c.ClientIP()(gins method for getting the clients IP) is always logging 127.0.0.1. So I’m just getting the loopback address for all my requests.

I do not believe this is a problem in the app itself, but is an issue with how traffic is forwarded to my app. I am not 100% sure though.

Any advice would be appreciated and I can clarify anything if needed.

Hi @HunterHeston,

It looks like some other folks have run into similar issues using c.ClientIP() in Gin, as seen on this thread: c.ClientIP() · Issue #2697 · gin-gonic/gin · GitHub

From the gin documentation:

ClientIP implements one best effort algorithm to return the real client IP. It called c.RemoteIP() under the hood, to check if the remote IP is a trusted proxy or not. If it is it will then try to parse the headers defined in Engine.RemoteIPHeaders (defaulting to [X-Forwarded-For, X-Real-Ip]). If the headers are not syntactically valid OR the remote IP does not correspond to a trusted proxy, the remote IP (coming form Request.RemoteAddr) is returned.

It seems possible that the result you’re getting may be caught up in the logic implemented in ClientIP. Can you confirm if referencing the X-Forwarded-For header is resulting in the correct IP?

Hey @Jade_Paoletta,

Thanks for the response I gave that a try but X-Forwarded-For isn’t providing the real client IP. It appears to provide only the proxies that the request was forwarded through, hard to be sure. But I can confirm that none of them are my personal IP.

The answer, in my case, is to read the CF-Connecting-IP header. I believe all render services are behind CloudFlare by default? CloudFlares docs say this is the real connecting IP and I confirmed that it’s value matched what I was expecting.

That same documentation indicates that the real client IP should be the first entry in X-Forwarded-For but for whatever reason I’m not seeing it there.

So for anyone seeing this in the future c.Request.Header.Get("CF-Connecting-IP") should give you the real client ip. At least that’s what I’m seeing.

@HunterHeston
Did you get the real ip?

Yes i can confirm that does give real ip.

here is my nginx.conf file

events {
    worker_connections 1024; # You can adjust this value as needed
}

http {
    include /etc/nginx/mime.types; # Include the MIME types file
    default_type application/octet-stream; # Default MIME type

    # Configure access log to send logs to Papertrail
    access_log stdout;

    # Set the real IP header and trusted proxy IPs
    set_real_ip_from 0.0.0.0/0;
    real_ip_header CF-Connecting-IP;
    real_ip_recursive on;

    server {
        listen 80;
        server_name example.com; # Replace with your domain or IP

        root /usr/share/nginx/html; # Path to your Trunk build folder

        index index.html;

        location / {
            try_files $uri $uri/ /index.html; # This will serve index.html for any unknown routes
        }

        # Optional: Configure caching for static files (e.g., images, CSS, JS)
        location ~* \.(?:css|js|jpg|jpeg|png|gif|ico|woff2?)$ {
            expires 1y;
            add_header Cache-Control "public";
        }
    }
}

This topic was automatically closed after 13 days. New replies are no longer allowed.