简体   繁体   中英

Golang panic: runtime error: invalid memory address or nil pointer dereference

i'm new to golang and it may be a very basic thing but i can't seems to find the solution.

the request return json which is like this.

{"uuid":"a0eebc99-9c0b-4ef8-bb6d-6bb9bd380a22","name":"core1","owner":"systems","description":"new","creation_date":"2017-06-10T14:20:00Z"}

This is the gocode.

package main

import (
    "crypto/tls"
    "encoding/json"
    "fmt"
    "io/ioutil"
    "net/http"
)

type Project struct {
    Uuid          string `json:"uuid"`
    Name          string `json:"name"`
    Owner         string `json:"owner"`
    Description   string `json:"description"`
    Creation_date string `json:"creation_date"`
}

func main() {
    tr := &http.Transport{
        TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
    }
    client := &http.Client{Transport: tr}
    req, err := http.NewRequest("GET", "https://localhost:4443/project/core1", nil)
    req.SetBasicAuth("rohit", "rohit")
    resp, err := client.Do(req)
    if err != nil {
        fmt.Printf("server not responding %s", err.Error())
    }
    var p Project

    b, err := ioutil.ReadAll(resp.Body)
    defer resp.Body.Close()
    err = json.Unmarshal(b, &p)
    if err != nil {
        fmt.Printf("Test case failed with error %s", err.Error())
    }
    if resp.StatusCode != 403 {
        fmt.Printf("failed %s", err.Error())
    }
}

after running i'm getting this error

panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x20 pc=0x40142f]

goroutine 1 [running]:
panic(0x60c860, 0xc42000c130)
    /usr/local/go/src/runtime/panic.go:500 +0x1a1
main.main()
    /home/rohitk/Go_projects/src/first_program/test/main.go:41 +0x42f
exit status 2

i checked and response body has right data. can someone please suggest what's happening here.Thanks!

As mentioned by commenters, your code is only printing errors, not handling them by altering the behavior of the program.

resp, err := client.Do(req)
if err != nil {
    fmt.Printf("server not responding %s", err.Error())
}
// ...

b, err := ioutil.ReadAll(resp.Body)

In the snippet above, if there was an error then it gets printed; however, flow control proceeds as usual even though the "resp" object is probably not valid (eg nil).

When a library program encounters an error you should usually return it immediately without any further action. For end-user applications, you should usually display the error (typically on the stderr stream) and exit the program (typically with a nonzero exit code). For example:

resp, err := client.Do(req)
if err != nil {
    fmt.Fprintf(os.Stderr, "ERROR: %s\n", err)
    os.Exit(1) // Exit the program if we didn't get a response.
}
// ...

b, err := ioutil.ReadAll(resp.Body)

I am just seeing this question and I just wanted to contribute. As mentioned by @maerics.As mentioned by commenters, your code is only printing errors, not handling them by altering the behavior of the program. My observation is also that there are two places that you are printing out errors and not handling them.

if err != nil {
        fmt.Printf("server not responding %s", err.Error())
    }

It should be:

if err != nil {
        fmt.Printf("server not responding %s", err.Error())
        return // the return statement here helps to handle the error
    }

Also the second one which is :

if err != nil {
        fmt.Printf("Test case failed with error %s", err.Error())
    }

It should rather be :

if err != nil {
        fmt.Printf("Test case failed with error %s", err.Error())
        return // the return statement here helps to handle the error
    }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM