2014-09-05 77 views
-1

我是Go的新手,编写一个脚本来测试我的Web服务器是否启动,如果没有,则启动mai。除了一个让我疯狂的小问题之外,所有的工作都在进行,尝试了其他地方发布的很多解决方案。Go Lang HTTP Connection Not Found

的问题是,当Web服务器是完全下来,不答复,走的是崩溃:

panic: runtime error: invalid memory address or nil pointer dereference 
[signal 0xc0000005 code=0x1 addr=0x0 pc=0x40140e] 

goroutine 16 [running]: 
runtime.panic(0x68b1c0, 0x83bfe2) 
     c:/go/src/pkg/runtime/panic.c:279 +0x11f 
main.httpGET(0x6f0530, 0x15) 
httpcheck.go 
:57 +0x32e 
main.main() 
httpcheck.go 
:43 +0x3b 

goroutine 19 [finalizer wait]: 
runtime.park(0x415bb0, 0x840c38, 0x83eda9) 
     c:/go/src/pkg/runtime/proc.c:1369 +0xac 
runtime.parkunlock(0x840c38, 0x83eda9) 
     c:/go/src/pkg/runtime/proc.c:1385 +0x42 
runfinq() 
     c:/go/src/pkg/runtime/mgc0.c:2644 +0xdd 
runtime.goexit() 
     c:/go/src/pkg/runtime/proc.c:1445 
exit status 2 

这里就是我有,直到崩溃....

import (
    "fmt" 
    "io/ioutil" 
    "log" 
    "net/http" 
    "github.com/sendgrid/sendgrid-go" 
    "os" 
    "time" 
    "net" 
) 

var finishedWaiting bool 
var timeout = time.Duration(2) * time.Second 
var httpClient = http.DefaultClient 

func main() { 
    const url = "http://doesnotexist.com" 
    httpGET(url) 
    log.Println("main is running") 

} 

func httpGET(url string) { 
    log.Println("httpGet is runnning") 

    resp, err := httpClient.Get(url) 

    if err != nil && !doesFileExist("down") { 

    } 

    if resp.StatusCode != 200 && !doesFileExist("down") { 
     isDown() 

    } else if resp.StatusCode == 200 && doesFileExist("down") { 
     log.Println("200 response") 
     sendmail("up") 
     removeDownFile() 

    } 
} 

func sendmail(status string) { 
    sg := sendgrid.NewSendGridClient("user", "pass") 
    message := sendgrid.NewMail() 
    message.AddTo("[email protected]") 
    message.AddToName("WebBot") 

    if status == "down" { 
     message.SetSubject("Websites Down") 
     message.SetText("Sites may be down") 
    } else { 
     message.SetSubject("Website Up") 
     message.SetText("Sites are back Up") 
    } 
    message.SetFrom("[email protected]") 
    if r := sg.Send(message); r == nil { 
     fmt.Println("Email sent!") 
    } else { 
     fmt.Println(r) 
    } 
} 

//checks if the file name is present 
func doesFileExist(name string) bool { 
    if _, err := os.Stat(name); err != nil { 
     if os.IsNotExist(err) { 
      return false 
     } 
    } 
    return true 
} 

// write down file 
func writeDownFile() { 
    contents, _ := ioutil.ReadFile("") 
    ioutil.WriteFile("down", contents, 0x777) 

} 

//remove down file if server is back up 
func removeDownFile() { 
    os.Remove("down") 

} 

func sleepForTen() { 
    log.Println("sleeping for 10.....") 
    time.Sleep(10000 * time.Millisecond) 
    finishedWaiting = true 
    main() 

} 

func isDown() { 
    if finishedWaiting != true { 
     sleepForTen() 

    } else { 
     writeDownFile() 
     log.Println("200 response") 
     sendmail("down") 
    } 
} 

轻推在正确的方向将不胜感激,以帮助我优雅地确定连接是否无法建立。

谢谢。

+0

那不是所有的代码...哪里的isDown函数...? – fabrizioM 2014-09-05 00:54:47

+0

除了添加isDown(),还请复制发生恐慌的行。 – ANisus 2014-09-05 00:57:25

+0

确定添加了我拥有的内容 – poperob 2014-09-05 03:09:30

回答

-1

如果在get中发生错误,您只需继续该程序即可。怪不得resp将在零后。

这只是一个猜测,因为我们只能猜测行号。

0

即使Get返回错误,您也想检查resp.StatusCodehttp.Response在这种情况下无效,可能为零,或包含零指针,因此您不能使用它。

2

问题是你忽略了err对象。 resp可能因为此错误而为零,当您尝试访问resp.StatusCode时会导致恐慌。我不知道doesFileExist有什么意义,但试试这个:

func httpGET(url string) { 
    log.Println("httpGet is runnning") 

    resp, err := httpClient.Get(url) 

    if err != nil || resp.StatusCode != 200 && !doesFileExist("down") { 
     isDown() 
    } else if resp.StatusCode == 200 && doesFileExist("down") { 
     log.Println("200 response") 
     sendmail("up") 
     removeDownFile() 
    } 
} 
+0

感谢您的帮助@ sebcap26。我的第一个Go代码。非常感激得到一个直接的非讽刺的答案。 – poperob 2014-09-05 14:21:13