I used mkp224o to generate a key. Afterwards I tried to use Go to parse the key and start a service with Bine. Unfortunately I can't seem to be able to generate the same v3 onion address as mkp224o.
package main
import (
"bytes"
"context"
"crypto/ed25519"
"fmt"
"log"
"net/http"
"os"
"time"
"github.com/cretz/bine/tor"
"github.com/ipsn/go-libtor"
"github.com/pkg/errors"
)
func main() {
log.SetOutput(os.Stdout)
if len(os.Args) != 2 {
check(errors.New("need 1 argument"))
}
var known ed25519.PrivateKey
buf, _ := os.ReadFile("/home/user/mkp224o/onions/rocin4w356yd7jadjppabxivaz56z4k2wfvy5xpxieirenda3yt2aiqd.onion/hs_ed25519_secret_key")
known = bytes.TrimLeft(buf, "== ed25519v1-secret: type0 ==\x00\x00\x00")
fmt.Println("Starting and registering onion service, please wait a bit...")
t, err := tor.Start(context.Background(), &tor.StartConf{ProcessCreator: libtor.Creator, DebugWriter: nil})
check(errors.Wrap(err, "Failed to start tor"))
defer t.Close()
ctx, cancel := context.WithTimeout(context.Background(), 3*time.Minute)
defer cancel()
onion, err := t.Listen(ctx, &tor.ListenConf{Version3: true, RemotePorts: []int{80}, Key: known})
check(errors.Wrap(err, "Failed to create tor service"))
defer onion.Close()
fmt.Printf("Please open a Tor capable browser and navigate to http://%v.onion\n", onion.ID)
http.HandleFunc("/", pathHandler())
http.Serve(onion, nil)
}
func check(err error) {
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %v\n", err)
os.Exit(1)
}
}
func pathHandler() http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
}
}
Returns:
Starting and registering onion service, please wait a bit...
Please open a Tor capable browser and navigate to http://r3jvsuoxe37pn6ik5vjvcxrky37bxsuopo5yn436r5pamjfkz2mkytqd.onion
when it should be returning the rocin4w356yd7jadjppabxivaz56z4k2wfvy5xpxieirenda3yt2aiqd.onion address that mkp224o generated. What am I missing?
Related
I try to setup a small Golang Microservice for users with Gin and Mongodb.
package main
import (
"context"
"fmt"
"github.com/wzslr321/artiver/entity"
"github.com/wzslr321/artiver/settings"
"go.mongodb.org/mongo-driver/mongo"
"go.mongodb.org/mongo-driver/mongo/options"
"log"
"os"
"os/signal"
"syscall"
"time"
)
type application struct {
users *entity.UserCollection
}
var app *application
func init() {
initMongo()
}
func initMongo() {
oc := options.Client().ApplyURI(settings.MongodbSettings.Uri)
client, err := mongo.NewClient(oc)
if err != nil {
log.Fatalf("Error occured while initializing a new mongo client: %v", err)
}
ctx, cancel := context.WithTimeout(context.Background(), 15*time.Second)
defer cancel()
err = client.Connect(ctx)
if err != nil {
log.Fatalf("Errorr occurred while connecting to a client: %v", err)
}
defer func() {
if err = client.Disconnect(ctx); err != nil {
panic(err)
}
}()
log.Println("Successfully connected to the database!")
app = &application{
users: &entity.UserCollection{
C: client.Database("artiver").Collection("users"),
},
}
}
func main() {
router := app.InitRouter()
It doesn't show any errors in my IDE ( GoLand ), but when I try to build it I get an error:
# command-line-arguments
users/cmd/app/main.go:67:15: app.InitRouter undefined (type *application has no field or method InitRouter)
It it easily visible on the image above, that I do have access to such a method. It is defined in the same package.
package main
import (
"github.com/gin-gonic/gin"
cors "github.com/rs/cors/wrapper/gin"
"net/http"
)
func (app *application) InitRouter() *gin.Engine {
r := gin.New()
r.Use(gin.Recovery())
r.Use(cors.Default())
r.GET("/", func(ctx *gin.Context) {
ctx.String(http.StatusOK, "Hello World")
})
user := r.Group("/api/user")
{
user.POST("/add", app.CreateUser)
}
return r
}
I have no idea how am I supposed to fix it and what is done wrong. I'd appreciate any hint about what isn't done correctly.
Answer based on #mkopriva help in comments.
The issue was related to not running all needed .go files.
In my case, the solution was to build it this way in my Makefile:
go build -o $(path)users cmd/app/*
In similar cases, go run . most likely will do the job.
I want to achieve resolving a given domain by the DNS Server I provide.
The code below I've grabbed from https://play.golang.org/p/s2KtkFrQs7R
The result is giving the correct results - but unfortunately even when I'm giving an IP like 123.123.123.123:53 as the resolver IP...
I guess there's a fallback - but I could not find (https://golang.org/pkg/net/) the switch to turn it off...
Thanks in advance for any hint...
Matthias
package main
import (
"context"
"fmt"
"log"
"net"
"time"
)
func GoogleDNSDialer(ctx context.Context, network, address string) (net.Conn, error) {
d := net.Dialer{}
return d.DialContext(ctx, "udp", "123.123.123.123:53")
}
func main() {
domain := "www.google.com"
const timeout = 1000 * time.Millisecond
ctx, cancel := context.WithTimeout(context.TODO(), timeout)
defer cancel()
// var r net.Resolver
r := net.Resolver{
PreferGo: true,
Dial: GoogleDNSDialer,
}
records, err := r.LookupHost(ctx, domain)
if err != nil {
log.Fatal(err)
} else {
fmt.Printf("Records %v \n", records[0])
}
}
I'm writing a TCP Server and Client in Go, just as a working example to get familiar with this language. I want to write a server, let's call it MyServer, which does the following - it has a backend TCP Server, which listens for incoming messages, but it also has a Client which allows him to send other messages, independently on the received once. However, I don't know how to tell MyServer to listen "in the background", without blocking the main thread. Here is the code for my TCPServer:
package main
import (
"fmt"
"net"
"os"
)
func main() {
startListener()
doOtherThins()
}
func startListener() {
listener, err := net.Listen("tcp", "localhost:9998")
if err != nil {
fmt.Println("Error listening:", err.Error())
os.Exit(1)
}
defer listener.Close()
fmt.Println("Listening on " + "localhost:9998")
for {
// Listen for an incoming connection.
conn, err := listener.Accept()
if err != nil {
fmt.Println("Error during accepting: ", err.Error())
os.Exit(1)
}
go handleConnection(conn)
}
}
func handleConnection(conn net.Conn) {
buf := make([]byte, 1024)
_, err := conn.Read(buf)
if err != nil {
fmt.Println("Error reading:", err.Error())
}
conn.Write([]byte("Message correctly received."))
conn.Close()
}
Function startListener() blocks the main function, so the function doOtherThins() (which I want to independently send packets to other servers) is never triggered as long as the server is listening. I tried to change the main function and use the goroutine:
func main() {
go startListener()
doOtherThins()
}
But then the server is not listening for the incoming packets (it just triggers doOtherThins() and ends main()).
Is it possible to spin the listener in the background, to allow the main thread do also other operations?
Your last example should do what you want, the issue is that the main thread ends before you can do anything. There's 2 solutions start doOtherThins() on another goroutine and then call startListener() which blocks but the other goroutine is already running:
func main() {
go doOtherThins()
startListener()
}
Or use waitGroups to wait until the code ends before exiting.
Here is a cleaner way of achieving this using channels.
package main
import (
"net/http"
"fmt"
)
func main() {
// Create a channel to synchronize goroutines
finish := make(chan bool)
server8001 := http.NewServeMux()
server8001.HandleFunc("/foo", foo8001)
server8001.HandleFunc("/bar", bar8001)
go func() {
http.ListenAndServe(":8001", server8001)
}()
go func() {
//do other things in a separate routine
fmt.Println("doing some work")
// you can also start a new server on a different port here
}()
// do other things in the main routine
<-finish //wait for all the routines to finish
}
func foo8001(w http.ResponseWriter, r *http.Request) {
w.Write([]byte("Listening on 8001: foo "))
}
func bar8001(w http.ResponseWriter, r *http.Request) {
w.Write([]byte("Listening on 8001: bar "))
}
adding another variation of Anuruddha answer
package main
import (
"io"
"net/http"
"os"
"time"
)
func main() {
server8001 := http.NewServeMux()
server8001.HandleFunc("/foo", foo8001)
server8001.HandleFunc("/bar", bar8001)
unblock(func() error {
return http.ListenAndServe(":8001", server8001)
})//forgot err check, must be done!
res, err := http.Get("http://0.0.0.0:8001/foo")
if err != nil {
panic(err)
}
defer res.Body.Close()
io.Copy(os.Stdout, res.Body)
os.Exit(0)
}
func unblock(h func() error) error {
w := make(chan error)
go func() {
w <- h()
}()
select {
case err := <-w:
return err
case <-time.After(time.Millisecond * 50):
return nil
}
}
func foo8001(w http.ResponseWriter, r *http.Request) {
w.Write([]byte("Listening on 8001: foo "))
}
func bar8001(w http.ResponseWriter, r *http.Request) {
w.Write([]byte("Listening on 8001: bar "))
}
here is my code trying to display a base64 image it worked before using mux.
I've used http handlefunc before using mux, here i want to use mux and get the value of key.
package main
import (
"fmt"
"net/http"
"strconv"
base64 "encoding/base64"
"log"
"io"
"io/ioutil"
"os"
"github.com/gorilla/mux"
)
var (
Trace *log.Logger
Info *log.Logger
Warning *log.Logger
Error *log.Logger
)
func Init(
traceHandle io.Writer,
infoHandle io.Writer,
warningHandle io.Writer,
errorHandle io.Writer) {
Trace = log.New(traceHandle,
"TRACE: ",
log.Ldate|log.Ltime|log.Lshortfile)
Info = log.New(infoHandle,
"INFO: ",
log.Ldate|log.Ltime|log.Lshortfile)
Warning = log.New(warningHandle,
"WARNING: ",
log.Ldate|log.Ltime|log.Lshortfile)
Error = log.New(errorHandle,
"ERROR: ",
log.Ldate|log.Ltime|log.Lshortfile)
}
func get_info(r *http.Request){
fmt.Println(r.RemoteAddr)
fmt.Println(r.Header.Get("x-forwarded-for"))
fmt.Println(r.UserAgent())
fmt.Println(r.Referer())
}
func pix(w http.ResponseWriter, r *http.Request) {
Info.Println("Hi there, I love %s!", r.URL.Path[1:])
vars := mux.Vars(r)
key := vars["key"]
Info.Println("key", key)
var cookie *http.Cookie
cookie , err := r.Cookie("csrftoken")
if (err != nil ){
fmt.Printf("error")
fmt.Println(err)
}
get_info(r)
fmt.Printf(cookie.Value)
w.Header().Set("Content-Type", "image/jpeg")
p, err := base64.StdEncoding.DecodeString("iVBORw0KGgoAAAANSUhEUgAAADIAAAAyCAIAAACRXR/mAAADMUlEQVRYw+2YTUgUYRjHZzOJIoNA+rrUyYNIRQgRHaLo4qFDBEGeunSxS9TFU0QEnhIh6IvokrUzO2uamRmbG6XmR/mVaKZpZVbYvvO143zszsxOz+yahNm+785sITEP72F3Z+adH8/zf5+PpagwtxKXj+Vj+Vg+lo/lY+W+WI4KpddKwWIQFUSF97nNLcLGZt75SiOHchEXfskDVmYjlowpiEoei3UT2ljcFJOpOd169C1Z2SuvgsdpB7cgzB16EV/byGM2xDIVPxQujKmBDF/2m2l0vFvmEin7N2v8kiiPiOeGlGHRvP1RdxA9eYtGR7pk2Pf6lI7RCoP2RaWkZWe3fsFc18hvesAHPGEFUc24ltnx3kyiCJwfRMs6dTXLdSIjO9Osal18qzKfE5V9coDxhlU7qS3uOyiaB55JDtkS2TKoLCLaOLPS4b02pQdCHiUfRKf653/d2kjZN6f10jYxI2EnrGk5H+2WsVi6ZZ8fVSmGQKaYyyFuR6ugmUtVrJo2C7HokeGq8447sYpOPBbo3XFzKC95626sZlz905sUM9XLGbXvtKtTOhZrQDApkhNNkiAOPo/viojh2YSZsj1aF2eQ5n2stuomNQjiiGQanrFufdCXP8gu8tbhjridJ6saVPKExXJrwlwfb3pnAg2Ut0tEBZFI8gza81Tik15DCDIoINQ7aQdBo90RMfrdwNaWLFY9opJGkBQrhCA/HXspQ8W1XHkN6vfWFiGH9ouwhdpJUFuy2JX3eg6uyqENpNHZYcUd02jcLMI2WO67UwZVv1G1HLMq3L83KuEbLPdY7IL2L42p0MMQiuzkq/ncwucOi6qPbWkWoPfCUsENpweUnP1EmE4XGhgagT72RyXolkSCHBbTU3By3fgJj8VyJW3CmSHl8oTWMJuYUUizVvtcsuyJ6J4J663CMLevXar/lJgnKNSgbphzKjriTn5i0F8eX9ODXnEzf6JHvjGtv+aNGdWCOEKnJRmpr5oFVQV8WTWglIKHMlPhv5uqQ1xGYfB5fRMPo+n2VmFbi7ChiS9oWBhZvXrI01TNLg7yPxt51v9rxMfysXwsH8vH+g+wfgDUr+5LcyNV4AAAAABJRU5ErkJggg==")
if err != nil {
http.Error(w, "internal error", 500)
return
}
w.Header().Set("Content-Length", strconv.Itoa(len(p))) //len(dec)
w.Write(p)
}
func main() {
Init(ioutil.Discard, os.Stdout, os.Stdout, os.Stderr)
Info.Println("1")
r := mux.NewRouter()
Info.Println("2")
r.HandleFunc("/pix/{key}/pixel.gif", pix)
err := http.ListenAndServe(":9080", nil)
Info.Println("3")
if err != nil {
fmt.Println(err)
}
}
It seems that when i call http://localhost:9080/pix/2/pixel.gif
it doesn't call pix.
the url for calling it seems correct
any idea why ?
regards and thanks
It appears that you are not assigning r to anything, you should add the following at the end of your main:
http.Handle("/", r)
Server.go
package main
import (
"fmt"
"net/http"
//"strings"
"encoding/json"
"io/ioutil"
"strconv"
"net"
"bufio"
)
type Message struct {
Text string
}
func Unmarshal(data []byte, v interface{}) error
func main() {
//http.HandleFunc("/", handler)
server,_ := net.Listen("tcp", ":" + strconv.Itoa(8080))
if server == nil {
panic("couldn't start listening: ")
}
conns := clientConns(server)
for {
go handleConn(<-conns)
}
}
func clientConns(listener net.Listener) chan net.Conn {
ch := make(chan net.Conn)
i := 0
go func() {
for {
client, _ := listener.Accept()
if client == nil {
fmt.Printf("couldn't accept: ")
continue
}
i++
fmt.Printf("%d: %v <-> %v\n", i, client.LocalAddr(), client.RemoteAddr())
ch <- client
}
}()
return ch
}
func handleConn(client net.Conn) {
b := bufio.NewReader(client)
fmt.Println("Buffer")
for {
line, err := b.ReadBytes('\n')
if err != nil { // EOF, or worse
break
}
client.Write(line)
}
}
Client.go
package main
import (
"encoding/json"
"fmt"
"log"
"net/http"
"strings"
"flag"
//"io"
// "net"
// "net/rpc"
// "sync"
)
func Unmarshal(data []byte, v interface{}) error
func Marshal(v interface{}) ([]byte, error)
type Message struct {
Text string
}
func main(){
var flagtext = flag.String("flagtext", "Hello!", "Flag")
flag.Parse()
var text string
text = *flagtext
m := Message{text}
var m1 Message
b, err := json.Marshal(m)
if err == nil{
resp, err := http.Post("http://127.0.0.1:8080","application/json", strings.NewReader(string(b)))
if err != nil{
log.Fatal("Error while post: %v",err)
}
fmt.Println(resp)
err = json.Unmarshal(b, &m1)
}
}
Error I get when I run client.go is this:
Error while post: %vmalformed HTTP status code "/"
Though, the server registers a channel for each post, it shows a malformed HTTP status code. Is it because I'm listening in the wrong channel? I'm confused why this error is occurring.
This line in the server code:
client.Write(line)
sends the request line back to the client. Since the client is posting something like GET / HTTP/1.1, this means that the server is responding with something like GET / HTTP/1.1, instead of something like HTTP/1.1 200 OK. The error-message you're seeing is because / appears in the status-code position.
In server.go it seems you are trying to write your own HTTP server from the TCP socket level up. This is unnecessary work - take the easy route and use the built-in HTTP server API.
The general outline of such a server is like this:
package main
import (
"fmt"
"net/http"
)
func handler(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "Hi there, I love %s!", r.URL.Path[1:])
}
func main() {
http.HandleFunc("/", handler)
http.ListenAndServe(":8080", nil)
}
and is described further in this article. More documentation is in net/http.