Can't reach app by hostname so the webhook doesn't work (telegram bot)

I’ve got 1 critical health check.

I have a nodejs app that’s running my telegram bot. The bot was working in polling mode, but when I switched to webhook I found that the app hostname is not reachable: https://daily-polish-tg-bot.fly.dev/

I also assigned v4 (137.66.61.183) ip to the app but I doesn’t help.

I tried using ports 80 and 8080, it didn’t work. Telegram webhook needs 80, 88 or 443 telegram webhook documentation.

And I think the webhook is not working as expected because the app is not reachable. What I get from telegram is:

{“ok”:true,“result”:{“url”:“https://daily-polish-tg-bot.fly.dev/telegraf/token",“has_custom_certificate”:false,“pending_update_count”:9,“last_error_date”:1671351380,“last_error_message”:"Read timeout expired”,“max_connections”:40,“ip_address”:“137.66.61.183”}}

Seems like telegram can not reach the webhook and throws the read timeout error.

fly vm status:

Instance
  ID            = df0c21aa             
  Process       = app                  
  Version       = 35                   
  Region        = waw                  
  Desired       = run                  
  Status        = running              
  Health Checks = 1 total, 1 critical  
  Restarts      = 0                    
  Created       = 27m59s ago           

Events
TIMESTAMP           	TYPE           	MESSAGE                                                  
2022-12-18T11:10:23Z	Received       	Task received by client                                 	
2022-12-18T11:10:50Z	Task Setup     	Building Task Directory                                 	
2022-12-18T11:11:00Z	Started        	Task started by client                                  	
2022-12-18T11:15:50Z	Alloc Unhealthy	Task not running for min_healthy_time of 10s by deadline	
2022-12-18T11:35:11Z	Alloc Unhealthy	Task not running for min_healthy_time of 10s by deadline	

Checks
ID                              	SERVICE 	STATE   	OUTPUT                                                  
3df2415693844068640885b45074b954	tcp-8080	critical	dial tcp 172.19.5.146:8080: connect: connection refused	

fly.toml:

app = "daily-polish-tg-bot"
kill_signal = "SIGINT"
kill_timeout = 5
processes = []

[env]

[experimental]
  allowed_public_ports = []
  auto_rollback = true

[[services]]
  http_checks = []
  internal_port = 8080
  processes = ["app"]
  protocol = "tcp"
  script_checks = []
  [services.concurrency]
    hard_limit = 25
    soft_limit = 20
    type = "connections"

  [[services.ports]]
    force_https = true
    handlers = ["http"]
    port = 80

  [[services.ports]]
    handlers = ["tls", "http"]
    port = 443

  [[services.tcp_checks]]
    grace_period = "1s"
    interval = "15s"
    restart_limit = 0
    timeout = "2s"

.dockerfile:

FROM debian:bullseye as builder

ARG NODE_VERSION=16.18.1

RUN apt-get update; apt install -y curl

RUN curl https://get.volta.sh | bash

ENV VOLTA_HOME /root/.volta

ENV PATH /root/.volta/bin:$PATH

RUN volta install node@${NODE_VERSION}

#######################################################################

RUN mkdir /app

WORKDIR /app

# NPM will not install any package listed in "devDependencies" when NODE_ENV is set to "production",

# to install all modules: "npm install --production=false".

# Ref: https://docs.npmjs.com/cli/v9/commands/npm-install#description

ENV NODE_ENV production

COPY . .

RUN npm install --production=false

FROM debian:bullseye

LABEL fly_launch_runtime="nodejs"

COPY --from=builder /root/.volta /root/.volta

COPY --from=builder /app /app

WORKDIR /app

ENV NODE_ENV production

ENV PATH /root/.volta/bin:$PATH

EXPOSE 8080

CMD [ "npm", "run", "start" ]

And this is how I run the bot on the port in index.js (telegrafjs framework):

bot
    .launch({ webhook: { domain: process.env.WEBHOOK_URL, port: process.env.WEBHOOK_PORT }})
    .then(() => console.log("Webhook bot listening on port", process.env.WEBHOOK_PORT));

.env file:

WEBHOOK_URL = 'https://daily-polish-tg-bot.fly.dev/'
WEBHOOK_PORT = 8080;

Logs:

2022-12-18T06:30:45.345 runner[157a8c4f] waw [info] Starting virtual machine
2022-12-18T06:30:45.541 app[157a8c4f] waw [info] Starting init (commit: f447594)...
2022-12-18T06:30:45.567 app[157a8c4f] waw [info] Preparing to run: `npm run start` as root
2022-12-18T06:30:45.594 app[157a8c4f] waw [info] 2022/12/18 06:30:45 listening on [fdaa:1:701:a7b:8c:157a:8c4f:2]:22 (DNS: [fdaa::3]:53)
2022-12-18T06:30:46.412 app[157a8c4f] waw [info] > daily-polish-tg-bot@1.0.0 start
2022-12-18T06:30:46.412 app[157a8c4f] waw [info] > node src/index.js
2022-12-18T06:30:47.595 app[157a8c4f] waw [info] Webhook bot listening on port 8080;
2022-12-18T09:14:40Z runner[964a58ed] waw [info]Shutting down virtual machine
2022-12-18T09:14:40Z app[964a58ed] waw [info]Sending signal SIGINT to main child process w/ PID 520
error.message="no host specified in headers or uri" 2022-12-18T10:10:56Z proxy sjc [error]request.method="GET" request.url="/" request.id="01GMJBE5T9C80ZP80N2D65MYFY-sjc" response.status=400 

That critical-status check would be an issue:

dial tcp 172.19.5.146:8080: connect: connection refused

Your server should be binding to 0.0.0.0:8080 or [::]:8080. Looks like it’s probably listening on localhost:8080.

Sounds good, thank you!
Where I can specify it? I’ve tried adding host: "0.0.0.0" when launching the bot:

bot
    .launch({ webhook: { domain: process.env.WEBHOOK_URL, host: "0.0.0.0", port: process.env.WEBHOOK_PORT }})
    .then(() => console.log("Webhook bot listening on port", process.env.WEBHOOK_PORT));

But I receive the same error…

ID                              	SERVICE 	STATE   	OUTPUT                                                 
3df2415693844068640885b45074b954	tcp-8080	critical	dial tcp 172.19.8.26:8080: connect: connection refused	

Still an issue for me…

This is specific to your app’s code. I don’t know how that bot binds to addresses or how it can be configured.

You might be better served asking in their issue tracker how to bind to 0.0.0.0

I see! Thanks.
I was not sure that this is the bot issue. Now I tested with simple express app listening on 0.0.0.0:8080 and it works fine.

Solution that worked so far:

app.use(express.json());
app.use(await bot.createWebhook({ domain: process.env.WEBHOOK_URL }));
app.listen(process.env.WEBHOOK_PORT, '0.0.0.0', () => console.log("Listening on port", process.env.WEBHOOK_PORT)); // PORT 8443 works fine.
1 Like