D
D
Dmitry2018-03-15 19:02:29
go
Dmitry, 2018-03-15 19:02:29

Why is code not being executed in goroutines?

The task is simple: a small server responding on several ports when some given messages connect. I made it so that a goroutine with a listener was raised on each port.
The code works when run locally, but does not work on a remote server on DO (it starts, writes a greeting and goes into a loop without starting to listen to ports). Rebuilding on a server VM with a similar version of golang doesn't help.

package main

import (
  "fmt"
  "net"
  "os"
  "log"
)

const HOST = "0.0.0.0"

type ServerConfig struct {
  Protocol string
  Port int
  Banner []byte
}

func main() {
  fmt.Println("Server started!")
  var config *ServerConfig
  config = &ServerConfig{
    Protocol:"tcp",
    Port:8001,
    Banner: []byte("Hello!\n")}
  go config.startListener()
  config = &ServerConfig{
    Protocol:"tcp",
    Port:8002,
    Banner: []byte("World\n")}
  go config.startListener()
  for {}
}


func (c *ServerConfig) startListener() error {
  sockAddr :=  HOST+":"+fmt.Sprintf("%v", hc.Port)
  l, err := net.Listen(c.Protocol, sockAddr)
  if err != nil {
    fmt.Println("Error listening:", err.Error())
    //os.Exit(1)
    return err
  }
  defer l.Close()
  fmt.Println("Listening on " + sockAddr)
  for {
    conn, err := l.Accept()
    if err != nil {
      fmt.Println("Error accepting: ", err.Error())
      os.Exit(1)
    }
    // Handle connections in a new goroutine.
    go handleRequest(conn, c.Banner)
  }
}

// Handles incoming requests.
func handleRequest(conn net.Conn, banner []byte) {
  // Make a buffer to hold incoming data.
  conn.Write([]byte(banner))
  buf := make([]byte, 1024)
  // Read the incoming connection into the buffer.
  _, err := conn.Read(buf)
  if err != nil {
    fmt.Println("Error reading:", err.Error())
  }
  // Send a response back to person contacting us.
  conn.Write([]byte(banner))
  // Close the connection when you're done with it.
  conn.Close()
}

What could be the problem?

Answer the question

In order to leave comments, you need to log in

3 answer(s)
U
uvelichitel, 2018-03-15
@Liro

Run the second listener in main, not in goroutine

config.startListener()  // не нужно go config.startListener()
//обязательно уберите for{}, это плохая конструкция
select{}    //хотя бы так, а если оставить листенер в main треде то и это необязательно

R
RidgeA, 2018-03-15
@RidgeA

How many cores are in a DO machine?
There is an assumption that it
does not allow processing incoming connections. clogs the percentage completely
In general, as Andrey Tsvetkov said, the code is very strange ...

A
Alexander Pavlyuk, 2018-03-15
@pav5000

Replace for{} with select{}
In your launch settings on the server, the GOMAXPROC environment variable is set to 1, most likely, so the empty loop occupies a single process and does not allow the rest of the goroutines to work. select{} will just put your main goroutine to sleep without wasting resources.

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question