Unable to create online web-page - go

I am trying to create Golang web-pages...
Progress:
Ubuntu 18.04 installed both locally and on a Linode VPS.
Created and compiled a local Golang "Hello World" script that renders OK both locally and online.
Created a net/http Golang script that works OK when called locally http://localhost:8080/testing to see if it works
Uploaded the script to the Linode server and initial status messages appear but when calling http:123.456.789.32:8080/testing to see if it works the browser freezes.
//
// Golang - main.go
//
package main
import (
"net/http"
)
func sayHello(w http.ResponseWriter, r *http.Request) {
message := r.URL.Path
message = "Hello " + message
w.Write([]byte(message))
}
func main() {
http.HandleFunc("/", sayHello)
if err := http.ListenAndServe(":8080", nil); err != nil {
panic(err)
}
}
There are no errors or warnings rendered and unable to find any log references.
Can error and warnings similar to PHP error_reporting(-1), declare(strict_types=1) etc be logged or rendered?

A quick check with Nmap showed this result:
nmap -sV -p 8080 <yourIP>
Starting Nmap 7.70 ( https://nmap.org ) at 2019-07-04 07:45 CEST
Nmap scan report for <your-domain>.com (<yourIP>)
Host is up (0.032s latency).
PORT STATE SERVICE VERSION
8080/tcp filtered http-proxy
Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 0.90 seconds
The state of "filtered" actually means that there was no response on that port as opposed to an outright rejection of the request.
Check the output of iptables -L -n. Presumably, you have a firewall running and blocking port 8080. Do not simply deactivate the firewall, but read up on how to open port 8080 in the firewall product you are using. Linode has guides for the commonly used/preinstalled firewalls of various Linux distributions.
If you plan to go into production, please have someone help you to ensure security and availability of your deployment.

Related

What causes urn:acme:error:unauthorized 403 error in golang's acme/autocert?

The full error message is:
403 urn:acme:error:unauthorized: Account creation on ACMEv1 is
disabled. Please upgrade your ACME client to a version that supports
ACMEv2 / RFC 8555. See
https://community.letsencrypt.org/t/end-of-life-plan-for-acmev1/88430
for details
And I've googled this and reviewed that link, but I'm just using:
golang.org/x/crypto/acme/autocert
package in a very normal way:
package main
import (
"crypto/tls"
"net/http"
"github.com/gin-gonic/gin"
"golang.org/x/crypto/acme/autocert"
)
func main() {
router := gin.Default()
hosts := []string{"yourdomain.com"}
certManager := autocert.Manager{
Prompt: autocert.AcceptTOS,
HostPolicy: autocert.HostWhitelist(hosts...),
Cache: autocert.DirCache("/certs"),
}
server := &http.Server{
Addr: ":https",
Handler: router,
TLSConfig: &tls.Config{
GetCertificate: certManager.GetCertificate,
},
}
server.ListenAndServeTLS("", "")
}
In fact this code has been running and working fine for the last 6 months. But just today I switched the server it was on and now get the above message.
I tried getting the very latest version of golang, but still same problem.
I changed my DNS for my hosts to this new server's ip and the hostname of the server is correct.
Far as I can tell, it's 100% identical to the previous working server but with a new IP.
Is golang's acme/autocert really this out of date and not using ACMEv2?
This statement:
In fact this code has been running and working fine for the last 6 months. But just today I switched the server it was on and now get the above message.
Might indicate that you're building against an older version of golang.org/x/crypto - check your go.mod file and ensure you're using a fairly recent version. I completed a project recently that uses almost identical code. The require in my go.mod looks like this:
golang.org/x/crypto v0.0.0-20200602180216-279210d13fed

telegraf output to Elasticsearch: "health check timeout: no Elasticsearch node available"

I'm having trouble connecting to an Elasticsearch instance with a Telegraf output plugin.
I created an Elasticsearch setup via the Elasticsearch service. I created a user and password (connected to a role) in Kibana for it.
Then I setup a Telegraf output for it:
[[outputs.elasticsearch]]
urls = [ "https://hostname:port" ] # required.
timeout = "5s"
enable_sniffer = false
health_check_interval = "10s"
## HTTP basic authentication details.
username = "my_username"
password = "my_password"
index_name = "device_logs" # required.
insecure_skip_verify = true
manage_template = true
template_name = "telegraf"
overwrite_template = false
But when I try to start Telegraf with this, it just gives the error,
[agent] Failed to connect to [outputs.elasticsearch], retrying in 15s, error was 'health check timeout: no Elasticsearch node available'
The connect fail seems to originate deep in the bowels of golang's net/http library, and I don't know how to get some more useful output at this point.
Things I've tried:
Thing #1: I tested cURL:
curl -u my_username:my_password -X POST "https://hostname:port/device_logs/_doc" -H 'Content-Type: application/json' -d'
{
"name": "John Doe"
}'
This works fine.
Thing #2: I created a simple Go program to connect to elasticsearch from Go:
package main
import (
"log"
"time"
"gopkg.in/olivere/elastic.v3"
)
func main() {
// configure connection to ES
client, err := elastic.NewClient(elastic.SetURL("https://hostname:port"))
if err != nil {
panic(err)
}
log.Printf("client.running? %v",client.IsRunning())
if ! client.IsRunning() {
panic("Could not make connection, not running")
}
}
.. and it hits the first panic with the same "no Elasticsearch node available".
Thing #3: I tried running gdb on that Go program to debug into it.
It jumps down to assembly as soon as I call NewClient, so I can't really learn what is happening in the bowels of net/http.
I've never used Go before, so I'm hoping to avoid hours of learning Go, spelunking, and debugging to get around what hopefully is a simple issue here.
Any ideas on how to get more info here or why this is failing? Are there build or runtime flags for Go that I can use? gdb-with-Go debugging tips so I can step down into the Go library code? Elasticsearch client know-how?
To answer my own question, the problem here turned out to be the roles permissions. The Telegraf output plugin for Elasticsearch needs both the monitor and the manage_index_templates permissions to be enabled, or else it'll fail to connect to the Elasticsearch server without printing any information about why.
BTW: to build golang code and be able to debug into the libraries it calls:
go build -gcflags=all="-N -l"

Client timeout exceeded while awaiting headers

I got below error, I am using go v1.10.4 linux/amd64.
I am not behind any firewall or whatsoever. New Relic in java server (same network segment) that we have runs fine.
We have tried:
Increasing the timeout to 60 seconds
Use http2 in the server
Using Postman return 503 with response:
{"exception":{"message":"Server Error","error_type":"RuntimeError"}}
troubleshooting with ./nrdiag says “No Issues Found”
Below is our code:
config := newrelic.NewConfig(os.Getenv("NEW_RELIC_APP_NAME"), os.Getenv("NEW_RELIC_KEY"))
config.Logger = newrelic.NewDebugLogger(os.Stdout)
app, err := newrelic.NewApplication(config)
if err != nil {
fmt.Println("Failed to create newrelic application", err)
os.Exit(1)
}
.................
httpListener, err := net.Listen("tcp", *httpAddr)
if err != nil {
oldlog.Print("Error: ", err)
logger.Log("transport", "HTTP", "during", "Listen", "err", err)
os.Exit(1)
}
g.Add(func() error {
logger.Log("transport", "HTTP", "addr", *httpAddr)
return http.Serve(httpListener, nrgorilla.InstrumentRoutes(httpHandler, app))
}, func(error) {
httpListener.Close()
})
}
However this what we got,note some_key was removed:
(28422) 2019/07/29 18:08:50.058559 {"level":"warn","msg":"application connect failure","context":{"error":"Post https://collector-001.eu01.nr-data.net/agent_listener/invoke_raw_method?license_key=some_key\u0026marshal_format=json\u0026method=connect\u0026protocol_version=17: net/http: request canceled (Client.Timeout exceeded while awaiting headers)"}}
I think it is due to DNS network timeout.
You can easily test this out by using the following steps (in Ubuntu)
Select the IPv4 Settings tab.
Disable the “Automatic” toggle switch and enter the DNS resolvers' IP addresses, separated by a comma. We’ll use the Google DNS nameservers:
8.8.8.8,8.8.4.4
If it works, then you may be able to reset the DNS to "Automatic"
On Windows OS, Running Linux Containers with WSL2, i followed the following steps,
Ran the command docker logout
Ran the command, docker network prune, so as to remove all the preconfigured settings of the network.
From Docker Settings, Enabled the DNS server configuration with 8.8.8.8
Restarted the Docker
Now executed login command with registry to login, docker login {registry}

http.ListenAndServe handler function executed twice on port 80 [duplicate]

This question already has answers here:
HandleFunc being called twice
(4 answers)
Why this simple web server is called even number times?
(1 answer)
Closed 5 years ago.
If I run the following simple http server code on port 8080 everything works as expected. If I run the same code on port 80, by just changing the port, the handler function is executed twice with each request. Why, and how to fix it?
// httptest project main.go
package main
import (
"net/http"
"log"
"fmt"
"html"
)
var count int
func defaultHandler(w http.ResponseWriter, r *http.Request) {
count++
fmt.Fprintf(w, "Hello, %q count=%d", html.EscapeString(r.URL.Path), count)
fmt.Println(count,r.RemoteAddr)
}
func main() {
http.HandleFunc("/", defaultHandler)
log.Fatal(http.ListenAndServe(":8080", nil))
}
If I enter localhost:8080 in the browser, I get a response with a count starting at 1 and increased by 1 with each new request.
If I change the code to port 80 and enter just localhost or localhost:80 in the browser, I get a first response with a count starting at 1 but increased by two with each following request. At the same time the print statement for the console output is executed twice.
Terminal console when running on port 80 with 3 requests:
>go run main.go
1 [::1]:51335
2 [::1]:51335
3 [::1]:51335
4 [::1]:51335
5 [::1]:51335
6 [::1]:51335
The responses in the browser are Hello, "/" count=1, Hello, "/" count=3 and Hello, "/" count=5.
I've been running this locally on Windows 10 with Go version go1.9.2 windows/amd64 and the latest Google Chrome Browser.
However, I detected the issue in a simple web application on a remote Linux server where the code has been compiled with go version go1.9.1 linux/amd64.
i just tried it on my pc with Fiddler open
I noticed when navigating to the url using Google Chrome, the browser makes 2 request
GET / HTTP/1.1
GET /favicon.ico HTTP/1.1
the request for the favicon also gets handled by the defaultHandler, which causes the count to increment
I also tried with firefox and it doesn't send another request for the favicon
Try to log requests. Possibly browser is calling /favicon.ico

Get golang http server working with rerun

I'm trying to use rerun to relaunch a go http server when the source files change, but the restart always fails to launch.
Simple server
package main
import (
"net/http"
"fmt"
"log"
"html"
)
func main() {
http.HandleFunc("/hello", func(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "Hello, %q", html.EscapeString(r.URL.Path))
})
log.Fatal(http.ListenAndServe(":8080", nil))
}
Command line output
$ rerun -p "**/*.{go,html}" go run my_server.go
16:49:24 [rerun] Rerun_test launched
16:49:26 [rerun] Watching . for **/*.{go,html} using Darwin adapter
16:50:17 [rerun] Change detected: 1 modified
16:50:17 [rerun] Sending signal TERM to 75688
16:50:17 [rerun] Rerun_test restarted
2014/07/15 16:50:17 listen tcp :8080: bind: address already in use
exit status 1
16:50:19 [rerun] Rerun_test Launch Failed
How can I get this working, or why can't the server bind to the port when it is relaunched?
Also, I am using OSX 10.9.
A process already running on port 8080 that's why it cannot re-run, go to your activity monitor find the process in your case it may be named as (my_server), and quit it.

Resources