examples/boilerplate/boilerplate.go
func RunBot(apiKey string, bot BotFunc, name, description string) {
	closing := make(chan struct{})

	fmt.Printf("%s: %s\n", name, description)
	fmt.Println("Starting...")

	api, err := tbotapi.New(apiKey)
	if err != nil {
		log.Fatal(err)
	}

	// Just to show its working.
	fmt.Printf("User ID: %d\n", api.ID)
	fmt.Printf("Bot Name: %s\n", api.Name)
	fmt.Printf("Bot Username: %s\n", api.Username)

	closed := make(chan struct{})
	wg := &sync.WaitGroup{}

	wg.Add(1)
	go func() {
		defer wg.Done()
		for {
			select {
			case <-closed:
				return
			case update := <-api.Updates:
				if update.Error() != nil {
					// TODO handle this properly
					fmt.Printf("Update error: %s\n", update.Error())
					continue
				}

				bot(update.Update(), api)
			}
		}
	}()

	// Ensure a clean shutdown.
	shutdown := make(chan os.Signal)
	signal.Notify(shutdown, syscall.SIGINT, syscall.SIGTERM)

	go func() {
		<-shutdown
		close(closing)
	}()

	fmt.Println("Bot started. Press CTRL-C to close...")

	// Wait for the signal.
	<-closing
	fmt.Println("Closing...")

	// Always close the API first, let it clean up the update loop.
	// This might take a while.
	api.Close()
	close(closed)
	wg.Wait()
}
func RunBot(apiKey string, bot BotFunc, name, description string) {
	closing := make(chan struct{})

	fmt.Printf("%s: %s\n", name, description)
	fmt.Println("Starting...")

	api, err := tbotapi.New(apiKey)
	if err != nil {
		log.Fatal(err)
	}

	// Just to show its working.
	fmt.Printf("User ID: %d\n", api.ID)
	fmt.Printf("Bot Name: %s\n", api.Name)
	fmt.Printf("Bot Username: %s\n", api.Username)

	closed := make(chan struct{})
	wg := &sync.WaitGroup{}

	wg.Add(1)
	go func() {
		defer wg.Done()
		for {
			select {
			case <-closed:
				return
			case update := <-api.Updates:
				if update.Error() != nil {
					// TODO handle this properly
					fmt.Printf("Update error: %s\n", update.Error())
					continue
				}

				bot(update.Update(), api)
			}
		}
	}()

	// Ensure a clean shutdown.
	shutdown := make(chan os.Signal)
	signal.Notify(shutdown, syscall.SIGINT, syscall.SIGTERM)

	go func() {
		<-shutdown
		close(closing)
	}()

	fmt.Println("Bot started. Press CTRL-C to close...")

	// Wait for the signal.
	<-closing
	fmt.Println("Closing...")

	// Always close the API first, let it clean up the update loop.
	// This might take a while.
	api.Close()
	close(closed)
	wg.Wait()
}
// RunBot runs a bot.
// It will block until either something very bad happens or closing is closed.