программа паникует после обнаружения ошибки в главном блоке.паника: ошибка во время выполнения: неверный адрес памяти или разыменование нулевого указателя - PullRequest
0 голосов
/ 04 октября 2018

Я новичок в Голанге.Моя программа паникует после того, как я пытаюсь отловить ошибку в главном блоке после определения местоположения.Я где-то читал, добавление defer.close () может помочь, но опять же компилятор говорит, что в вашей структуре нет такого определения Помогите мне разрешить его.

type IPInfo struct {

    IP string

    Hostname string

    City string
    Country string

    Loc string
    Org string
    Postal string
}
func main() {
        ip := getLocalIpv4()
        location, err := ForeignIP(ip)
        if err != nil {
            fmt.Println("error bro")
        }

    fmt.Println("ip address of this machine is ", location.IP)
    fmt.Println(" city of this machine is ", location.City)

}

// MyIP provides information about the public IP address of the client.
func MyIP() (*IPInfo, error) {
    return ForeignIP("")
}

// ForeignIP provides information about the given IP address,
// which should be in dotted-quad form.
func ForeignIP(ip string) (*IPInfo, error) {
    if ip != "" {
        ip += "/" + ip
    }
    response, err := http.Get("http://ipinfo.io" + ip + "/json")
    if err != nil {
        return nil, err
    }
    defer response.Body.Close()

    contents, err := ioutil.ReadAll(response.Body)
    if err != nil {
        return nil, err
    }
    var ipinfo IPInfo
    if err := json.Unmarshal(contents, &ipinfo); err != nil {
        return nil, err
    }
    return &ipinfo, nil
}

// retrieves ip address of local machine
func getLocalIpv4() string {
    host, _ := os.Hostname()
    addrs, _ := net.LookupIP(host)
    for _, addr := range addrs {
        if ipv4 := addr.To4(); ipv4 != nil {
            return fmt.Sprintf("%s", ipv4)
        }
    }
    return "localhost"
}

1 Ответ

0 голосов
/ 04 октября 2018

Ваш ForeignIP() возвращает *IPInfo, который является структурой типа указателя, но вы получаете сообщение об ошибке из этой строки кода response, err := http.Get("http://ipinfo.io" + ip + "/json"), которое не удалось из-за ошибки ниже:

dialtcp: lookup ipinfo.io172.16.11.115: такого хоста нет.

Затем вы возвращаете nil там, как.

   if err != nil {
            return nil , err
   }

И вы получаете доступ к значению nilas:

location, err := ForeignIP(ip)
fmt.Println("ip address of this machine is ", location.IP)
fmt.Println(" city of this machine is ", location.City)

Так что значение nil не имеет никакой переменной IP или City, поэтому оно паникует.Поэтому вам нужно вернуть struct, которая имеет тип указателя, тогда вы можете получить доступ к переменным IP и City из ответа location, здесь я изменяю код.

func ForeignIP(ip string) (*IPInfo, error) {
    var ipinfo IPInfo
    if ip != "" {
        ip += "/" + ip
    }
    response, err := http.Get("http://ipinfo.io" + ip + "/json")
    if err != nil {
        return &ipinfo , err
    }

    defer response.Body.Close()

    contents, err := ioutil.ReadAll(response.Body)
    if err != nil {
        return &ipinfo, err
    }

    if err := json.Unmarshal(contents, &ipinfo); err != nil {
        return &ipinfo, err
    }
    return &ipinfo, nil
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...