Deploy telegram bot to heroku for free
Tags: tutorial, heroku, telegraf, javascript
Published: 2021-08-21 13:42:36

## I used telegraf, but you can use any other framework and language

> Hello there, you created your telegram bot and want to deploy it somewhere? Let me help you, I already done this before:

▶ Bot itself - https://t.me/WishBasket_bot
▶ Source code - https://github.com/T-Damer/wishBasket-bot

## First steps

Create repository on github and upload your bot to `main` branch, like [I did](https://github.com/T-Damer/wishBasket-bot).

Allright, now let's go to [Heroku Dashboard](https://dashboard.heroku.com/). Create app, if you still haven't done so:
![chrome_IyMPGdilzQ](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/l4xschcmxcvuuzbkafe9.png)

Give it a name, choose location you prefer, then scroll down and choose GitHub and Repo with your bot: ![chrome_ZMN6JLPu0u](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/wn04nybu8tcgcjx5h7ao.png)

I also recommend checking auto-deploy, so when you upload new changes to your repo, it will deploy them automatically

🎉 Nice, you completed step one 🎉

## Easy, but...

Okay, your bot will work for a while, or maybe not... You may see errors over there:

![4](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/4cpl6drcvx6kqsvunp8i.png)
 
Let's go straight through the problems you will face

### Can't get '/' : `code=H10 desc="App crashed"` and `Can not get '/'` and `Can not get 'favicon.ico'`

This error happens, because Heroku don't know, that you're deploying a bot, Heroku thinks, that you want to make a web-page. 
To awoid `Can not get '/'`, simply add express (or any other server-app) to your `App.js` or `App.ts` like this:

(Yes, I use TypeScript, no worries, you can do this with JS 🙂)
```TS
import express = require('express')

// ===Your bot logic here 

// Start app for Heroku
const app = express()
app.use(express.static('public'))
app.get('/', function (req, res) {
  res.send(
    "<h1>Hello There! You found <a href='https://t.me/wishbasket_bot'>@WishBasket_bot</a> backend</h1>"
  )
})

// Start server
app.listen(process.env.PORT || 3000, () => console.log('Server is running...'))
```

⚠ Use `process.env.PORT || 3000`, because Heroku uses it's own PORT, which will be taken from it's environment ⚠

Congratulations, you have successfully avoided first error 🎉

### Heroku started idling

Everything were good, but after 30 minutes heroku turned my bot off, it is not responding to any commands 💢 

Chill, will fix it in a minute 🍦

Consider [looking here](https://devcenter.heroku.com/articles/free-dyno-hours) before avoiding this, you must know limitations

_Quick answer_: add your bot express url (mine was - https://wishbasket-bot.herokuapp.com/, click `Open App` on Heroku Dashboard) to [kaffeine.heroku](http://kaffeine.herokuapp.com/), remember to setup badtime (time format is GTM!) It will ping your online page every 30 minutes, so your bot will never fall asleep ☕

_Long answer(s)_: well, better read [answers here](https://stackoverflow.com/questions/5480337/easy-way-to-prevent-heroku-idling). You can use [this NewRelic extension](https://elements.heroku.com/addons/newrelic), but I personally recommend you using caffeine, because if you want to add extensions on Heroku, you must enter your credit card (which I could not do, although the data is correct, thanks Heroku 🤦‍♂️)

Congratulations on your bypassing restrictions 🍾

---

## Bonus. How to add secrets?

Well, I personally used [MongoDB Cluster](https://www.mongodb.com/cloud/atlas) to manage database, I had special link with login and password to my database, hidden in `.env.local` file, and used `.dotenv` to use this file (never publish such a thing to the internet!)

So, I nedded to use this link in my bot, but it wasn't in my repo, what should I do?

### Easy, watch me

Open your app setting: 
![5](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/c61r0yzi4wvepnedtmv7.png)

Scroll to config vars: 
![6](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ehhjmecuitrfha8kjmfe.png)

Add your variable, it should have same name, as inside your app:
![7](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/nf8fcnxaoe8abnfd522r.png)

---

Thanks for reading 💛