예제 #1
0
func TestTCP(t *testing.T) {
	// Lower maxAssertAttempts to keep this test from running too long
	maxAssertAttempts = 2

	l0, err := net.Listen("tcp", "localhost:0")
	if err != nil {
		t.Fatal(err)
	}
	defer func() {
		if err := l0.Close(); err != nil {
			t.Fatalf("Unable to close listener: %v", err)
		}
	}()

	start, fdc, err := Matching("TCP")
	if err != nil {
		t.Fatal(err)
	}
	assert.Equal(t, 1, start, "Starting count should have been 1")

	err = fdc.AssertDelta(0)
	if err != nil {
		t.Fatal(err)
	}
	assert.NoError(t, err, "Initial TCP count should be 0")

	l, err := net.Listen("tcp", "localhost:0")
	if err != nil {
		t.Fatal(err)
	}
	_, middle, err := Matching("TCP")
	if err != nil {
		t.Fatal(err)
	}

	err = fdc.AssertDelta(0)
	if assert.Error(t, err, "Asserting wrong count should fail") {
		assert.Contains(t, err.Error(), "Expected 0, have 1")
		assert.True(t, len(err.Error()) > 100)
	}
	err = fdc.AssertDelta(1)
	assert.NoError(t, err, "Ending TCP count should be 1")

	err = fdc.AssertDelta(0)
	if assert.Error(t, err, "Asserting wrong count should fail") {
		assert.Contains(t, err.Error(), "Expected 0, have 1")
		assert.Contains(t, err.Error(), "New")
		assert.True(t, len(err.Error()) > 100)
	}

	if err := l.Close(); err != nil {
		t.Fatalf("Unable to close listener: %v", err)
	}
	err = middle.AssertDelta(0)
	if assert.Error(t, err, "Asserting wrong count should fail") {
		assert.Contains(t, err.Error(), "Expected 0, have -1")
		assert.Contains(t, err.Error(), "Removed")
		assert.True(t, len(err.Error()) > 100)
	}
}
예제 #2
0
func TestTranslate(t *testing.T) {
	assertTranslation(t, "", "HELLO")
	UseOSLocale()
	assertTranslation(t, "I speak America English!", "ONLY_IN_EN_US")
	assertTranslation(t, "I speak Generic English!", "ONLY_IN_EN")
	assertTranslation(t, "", "NOT_EXISTED")

	SetMessagesDir("not-existed-dir")
	err := SetLocale("en_US")
	assert.Error(t, err, "should error if dir is not existed")

	SetMessagesDir("locale")
	assert.Error(t, SetLocale("e0"), "should error on malformed locale")
	assert.Error(t, SetLocale("e0-DO"), "should error on malformed locale")
	assert.Error(t, SetLocale("e0-DO.C"), "should error on malformed locale")
	assert.NoError(t, SetLocale("en"), "should change locale")
	if assert.NoError(t, SetLocale("en_US"), "should change locale") {
		// formatting
		assertTranslation(t, "Hello An Argument!", "HELLO", "An Argument")
		assertTranslation(t, "", "NOT_EXISTED", "extra args")
	}
	if assert.NoError(t, SetLocale("zh_CN"), "should change locale") {
		assertTranslation(t, "An Argument你好!", "HELLO", "An Argument")
		// fallbacks
		assertTranslation(t, "I speak Mandarin!", "ONLY_IN_ZH_CN")
		assertTranslation(t, "I speak Chinese!", "ONLY_IN_ZH")
		assertTranslation(t, "I speak America English!", "ONLY_IN_EN_US")
		assertTranslation(t, "I speak Generic English!", "ONLY_IN_EN")
	}
}
예제 #3
0
func TestWaitUntilNoneMatchTimeout(t *testing.T) {
	conn, err := net.Dial("tcp", "www.google.com:80")
	if err != nil {
		t.Fatalf("Unable to dial google: %v", err)
	}
	defer func() {
		if err := conn.Close(); err != nil {
			fmt.Println("Unable to close connection: %v", err)
		}
	}()

	wait := 500 * time.Millisecond
	start := time.Now()
	go func() {
		time.Sleep(wait)
		if err := conn.Close(); err != nil {
			t.Fatalf("Unable to close connection: %v", err)
		}
	}()

	err = WaitUntilNoneMatch("TCP", wait/2)
	elapsed := time.Now().Sub(start)
	assert.Error(t, err, "Waiting should have failed")
	assert.True(t, elapsed < wait, "Should have waited less than time to close conn")
}
예제 #4
0
func TestBadConnectStatus(t *testing.T) {
	l, err := net.Listen("tcp", "localhost:0")
	if err != nil {
		t.Fatalf("Unable to listen: %s", err)
	}

	hs := &http.Server{
		Handler: http.HandlerFunc(func(resp http.ResponseWriter, req *http.Request) {
			resp.WriteHeader(403) // forbidden
		}),
	}
	go func() {
		if err := hs.Serve(l); err != nil {
			t.Fatalf("Unable to serve: %v", err)
		}
	}()

	dialer := NewDialer(Config{
		DialServer: func() (net.Conn, error) {
			return net.Dial("tcp", l.Addr().String())
		},
	})
	_, err = dialer.Dial("tcp", "www.google.com")
	assert.Error(t, err, "Dialing a server that sends a non-successful HTTP status to our CONNECT request should have failed")
}
예제 #5
0
func doTestNonGlobalAddress(t *testing.T, overrideAddr string) {
	l := startServer(t, false, nil)
	d := dialerFor(t, l, 0)
	defer d.Close()

	gotConn := false
	var gotConnMutex sync.Mutex
	tl, err := net.Listen("tcp", "localhost:0")
	if err != nil {
		t.Fatalf("Unable to listen: %s", err)
	}
	go func() {
		tl.Accept()
		gotConnMutex.Lock()
		gotConn = true
		gotConnMutex.Unlock()
	}()

	addr := tl.Addr().String()
	if overrideAddr != "" {
		addr = overrideAddr
	}
	conn, err := d.Dial("tcp", addr)
	if err != nil {
		t.Fatalf("Unable to dial %v: %v", addr, err)
	}

	data := []byte("Some Meaningless Data")
	conn.Write(data)
	// Give enproxy time to flush
	time.Sleep(500 * time.Millisecond)
	_, err = conn.Write(data)
	assert.Error(t, err, "Sending data after previous attempt to write to local address should have failed")
	assert.False(t, gotConn, "Sending data to local address should never have resulted in connection")
}
예제 #6
0
func TestIdleClientConnections(t *testing.T) {
	limitedServer, err := setupNewHTTPServer(0, 100*time.Millisecond)
	if err != nil {
		assert.Fail(t, "Error starting proxy server")
	}

	okFn := func(conn net.Conn, proxy *server.Server, originURL *url.URL) {
		time.Sleep(time.Millisecond * 90)
		conn.Write([]byte("GET / HTTP/1.1\r\nHost: www.google.com\r\n\r\n"))

		var buf [400]byte
		_, err := conn.Read(buf[:])

		assert.NoError(t, err)
	}

	idleFn := func(conn net.Conn, proxy *server.Server, originURL *url.URL) {
		time.Sleep(time.Millisecond * 110)
		conn.Write([]byte("GET / HTTP/1.1\r\nHost: www.google.com\r\n\r\n"))

		var buf [400]byte
		_, err := conn.Read(buf[:])

		assert.Error(t, err)
	}

	go testRoundTrip(t, limitedServer, httpOriginServer, okFn)
	testRoundTrip(t, limitedServer, httpOriginServer, idleFn)
}
예제 #7
0
func TestTimeout(t *testing.T) {
	offer := Offer(1 * time.Millisecond)
	_, err := offer.FiveTuple()
	assert.Error(t, err, "There should be an error")
	if err != nil {
		assert.Contains(t, err.Error(), "Timed out", "Error should mention timing out")
	}
}
예제 #8
0
파일: buuid_test.go 프로젝트: 2722/lantern
func TestReadFailure(t *testing.T) {
	id1 := Random()
	b := make([]byte, EncodedLength)
	err := id1.Write(b)
	assert.NoError(t, err, "Unable to write")
	_, err = Read(b[:EncodedLength-1])
	assert.Error(t, err, "Read should have failed")
}
예제 #9
0
func TestBadEnproxyConn(t *testing.T) {
	d := NewDialer(Config{
		Host: "localhost",
		Port: 3253,
	})
	_, err := d.Dial("tcp", "www.google.com")
	assert.Error(t, err, "Dialing using a non-existent host should have failed")
}
예제 #10
0
func TestDialFailure(t *testing.T) {
	fail := int32(1)
	dialAttempts := int32(0)

	addr, err := startTestServer()
	if err != nil {
		t.Fatalf("Unable to start test server: %s", err)
	}

	_, fdc, err := fdcount.Matching("TCP")
	if err != nil {
		t.Fatal(err)
	}

	poolSize := 10

	p := New(Config{
		Size: poolSize,
		Dial: func() (net.Conn, error) {
			atomic.AddInt32(&dialAttempts, 1)
			if fail == int32(1) {
				return nil, fmt.Errorf("I'm failing intentionally!")
			}
			return net.DialTimeout("tcp", addr, 15*time.Millisecond)
		},
	})

	// Try to get connection, make sure it fails
	conn, err := p.Get()
	if !assert.Error(t, err, "Dialing should have failed") {
		if err := conn.Close(); err != nil {
			t.Fatalf("Unable to close connection: %v", err)
		}
	}

	// Wait for fill to run for a while with a failing connection
	time.Sleep(1 * time.Second)
	assert.Equal(t, 1, atomic.LoadInt32(&dialAttempts), fmt.Sprintf("There should have been only 1 dial attempt"))
	assert.NoError(t, fdc.AssertDelta(0), "There should be no additional file descriptors open")

	// Now make connection succeed and verify that it works
	atomic.StoreInt32(&fail, 0)
	time.Sleep(100 * time.Millisecond)
	connectAndRead(t, p, 1)

	time.Sleep(fillTime)
	log.Debug("Testing")
	assert.NoError(t, fdc.AssertDelta(10), "Pool should have filled")

	// Now make the connection fail again so that when we stop, we're stopping
	// while failing (tests a different code path for stopping)
	atomic.StoreInt32(&fail, 1)
	time.Sleep(100 * time.Millisecond)

	p.Close()

	assert.NoError(t, fdc.AssertDelta(0), "All connections should be closed")
}
예제 #11
0
func TestBadProtocol(t *testing.T) {
	dialer := NewDialer(Config{
		DialServer: func() (net.Conn, error) {
			return net.Dial("tcp", "www.google.com")
		},
	})
	_, err := dialer.Dial("udp", "www.google.com")
	assert.Error(t, err, "Dialing with a non-tcp protocol should have failed")
}
예제 #12
0
func TestHttpClientWithBadEnproxyConn(t *testing.T) {
	d := NewDialer(Config{
		Host: "localhost",
		Port: 3253,
	})
	hc := d.HttpClientUsing(nil)
	_, err := hc.Get("http://www.google.com/humans.txt")
	assert.Error(t, err, "HttpClient using a non-existent host should have failed")
}
예제 #13
0
func doTestTimeout(t *testing.T, timeout time.Duration) {
	_, err := DialWithDialer(&net.Dialer{
		Timeout: timeout,
	}, "tcp", ADDR, false, nil)
	assert.Error(t, err, "There should have been a problem dialing", timeout)
	if err != nil {
		assert.True(t, err.(net.Error).Timeout(), "Dial error should be timeout", timeout)
	}
}
예제 #14
0
func TestBadDialServer(t *testing.T) {
	dialer := NewDialer(Config{
		DialServer: func() (net.Conn, error) {
			return nil, fmt.Errorf("I refuse to dial")
		},
	})
	_, err := dialer.Dial("tcp", "www.google.com")
	assert.Error(t, err, "Dialing with a bad DialServer function should have failed")
}
예제 #15
0
func TestNotOKWithServerName(t *testing.T) {
	fdStart := countTCPFiles()
	conn, err := Dial("tcp", ADDR, true, nil)
	assert.Error(t, err, "There should have been a problem dialing")
	if err != nil {
		assert.Contains(t, err.Error(), CERTIFICATE_ERROR, "Wrong error on dial")
	}
	<-receivedServerNames
	closeAndCountFDs(t, conn, err, fdStart)
}
예제 #16
0
func TestWriteTooLong(t *testing.T) {
	w := NewWriter(ioutil.Discard)
	b := make([]byte, MaxFrameLength+1)
	n, err := w.Write(b)
	assert.Error(t, err, "Writing too long message should result in error")
	assert.Equal(t, 0, n, "Writing too long message should result in 0 bytes written")
	n, err = w.Write(b[:len(b)-1])
	assert.NoError(t, err, "Writing message of MaxFrameLength should be allowed")
	assert.Equal(t, MaxFrameLength, n, "Writing message of MaxFrameLength should have written MaxFrameLength bytes")
}
예제 #17
0
func TestReplaceBadOnDial(t *testing.T) {
	d := NewDialer(Config{
		Host: "fallbacks.getiantem.org",
		Port: 443,
		OnDial: func(conn net.Conn, err error) (net.Conn, error) {
			return nil, fmt.Errorf("Gotcha!")
		},
	})
	_, err := d.Dial("tcp", "www.google.com")
	assert.Error(t, err, "Dialing using a bad OnDial should fail")
}
예제 #18
0
func TestBadCertificateFile(t *testing.T) {
	server := &Server{
		Addr: "localhost:0",
		CertContext: &CertContext{
			PKFile:         "testpk.pem",
			ServerCertFile: "",
		},
	}
	_, err := server.Listen()
	assert.Error(t, err, "Listen should have failed")
}
예제 #19
0
func TestDeadlineBeforeTimeout(t *testing.T) {
	fdStart := countTCPFiles()
	conn, err := DialWithDialer(&net.Dialer{
		Timeout:  500 * time.Second,
		Deadline: time.Now().Add(5 * time.Microsecond),
	}, "tcp", ADDR, false, nil)
	assert.Error(t, err, "There should have been a problem dialing")
	if err != nil {
		assert.True(t, err.(net.Error).Timeout(), "Dial error should be timeout")
	}
	closeAndCountFDs(t, conn, err, fdStart)
}
예제 #20
0
func TestAllowed(t *testing.T) {
	gotConn := false
	var gotConnMutex sync.Mutex
	tl, err := net.Listen("tcp", "localhost:0")
	if err != nil {
		t.Fatalf("Unable to listen: %s", err)
	}
	go func() {
		if _, err := tl.Accept(); err != nil {
			t.Fatalf("Unable to accept connections: %v", err)
		}
		gotConnMutex.Lock()
		gotConn = true
		gotConnMutex.Unlock()
	}()

	_, portString, err := net.SplitHostPort(tl.Addr().String())
	if err != nil {
		t.Fatalf("Unable to get port for test server: %v", err)
	}

	port, err := strconv.Atoi(portString)
	if err != nil {
		t.Fatalf("Unable to convert port %v to integer: %v", portString, err)
	}
	// Only allow some port other than the actual port
	l := startServer(t, true, []int{port + 1})
	d := dialerFor(t, l, 0)
	defer func() {
		if err := d.Close(); err != nil {
			t.Fatalf("Unable to close dialer: %v", err)
		}
	}()

	addr := tl.Addr().String()
	conn, err := d.Dial("tcp", addr)
	defer func() {
		if err := conn.Close(); err != nil {
			t.Fatalf("Unable to close connection: %v", err)
		}
	}()

	data := []byte("Some Meaningless Data")
	if _, err := conn.Write(data); err != nil {
		t.Fatalf("Unable to write connection: %v", err)
	}
	// Give enproxy time to flush
	time.Sleep(500 * time.Millisecond)
	_, err = conn.Write(data)
	assert.Error(t, err, "Sending data after previous attempt to write to disallowed port should have failed")
	assert.False(t, gotConn, "Sending data to disallowed port should never have resulted in connection")
}
예제 #21
0
func TestNonIdempotentOp(t *testing.T) {
	defer stopMockServers()
	proxiedURL, _ := newMockServer(detourMsg)
	mockURL, mock := newMockServer("")
	u, _ := url.Parse(mockURL)
	mock.Timeout(200*time.Millisecond, directMsg)
	client := newClient(proxiedURL, 100*time.Millisecond)
	_, err := client.PostForm(mockURL, url.Values{"key": []string{"value"}})
	if assert.Error(t, err, "Non-idempotent method should not be detoured in same connection") {
		time.Sleep(50 * time.Millisecond)
		assert.True(t, wlTemporarily(u.Host), "but should be added to whitelist so will detour next time")
	}
}
예제 #22
0
func TestNotOKWithoutServerName(t *testing.T) {
	fdStart := countTCPFiles()
	conn, err := Dial("tcp", ADDR, true, &tls.Config{
		ServerName: "localhost",
	})
	assert.Error(t, err, "There should have been a problem dialing")
	if err != nil {
		assert.Contains(t, err.Error(), CERTIFICATE_ERROR, "Wrong error on dial")
	}
	serverName := <-receivedServerNames
	assert.Empty(t, serverName, "Unexpected ServerName on server")
	closeAndCountFDs(t, conn, err, fdStart)
}
예제 #23
0
func TestNonDefaultClient(t *testing.T) {
	// Set up a client that will fail
	client := &http.Client{
		Transport: &http.Transport{
			Dial: func(network, addr string) (net.Conn, error) {
				return nil, fmt.Errorf("Failing intentionally")
			},
		},
	}

	_, err := LookupIPWithClient("", client)
	assert.Error(t, err, "Using bad client should have resulted in error")
}
예제 #24
0
func TestBlockedImmediately(t *testing.T) {
	defer stopMockServers()
	proxiedURL, _ := newMockServer(detourMsg)
	TimeoutToDetour = 50 * time.Millisecond
	mockURL, mock := newMockServer(directMsg)

	client := &http.Client{Timeout: 50 * time.Millisecond}
	mock.Timeout(200*time.Millisecond, directMsg)
	resp, err := client.Get(mockURL)
	assert.Error(t, err, "direct access to a timeout url should fail")

	client = newClient(proxiedURL, 100*time.Millisecond)
	resp, err = client.Get("http://255.0.0.1") // it's reserved for future use so will always time out
	if assert.NoError(t, err, "should have no error if dialing times out") {
		assert.True(t, wlTemporarily("255.0.0.1:80"), "should be added to whitelist if dialing times out")
		assertContent(t, resp, detourMsg, "should detour if dialing times out")
	}

	client = newClient(proxiedURL, 100*time.Millisecond)
	resp, err = client.Get("http://127.0.0.1:4325") // hopefully this port didn't open, so connection will be refused
	if assert.NoError(t, err, "should have no error if connection is refused") {
		assert.True(t, wlTemporarily("127.0.0.1:4325"), "should be added to whitelist if connection is refused")
		assertContent(t, resp, detourMsg, "should detour if connection is refused")
	}

	u, _ := url.Parse(mockURL)
	resp, err = client.Get(mockURL)
	if assert.NoError(t, err, "should have no error if reading times out") {
		assert.True(t, wlTemporarily(u.Host), "should be added to whitelist if reading times out")
		assertContent(t, resp, detourMsg, "should detour if reading times out")
	}

	client = newClient(proxiedURL, 100*time.Millisecond)
	RemoveFromWl(u.Host)
	resp, err = client.PostForm(mockURL, url.Values{"key": []string{"value"}})
	if assert.Error(t, err, "Non-idempotent method should not be detoured in same connection") {
		assert.True(t, wlTemporarily(u.Host), "but should be added to whitelist so will detour next time")
	}
}
예제 #25
0
func TestMaxConnections(t *testing.T) {
	connectReq := "CONNECT %s HTTP/1.1\r\nHost: %s\r\n\r\n"

	limitedServer, err := setupNewHTTPServer(5, 30*time.Second)
	if err != nil {
		assert.Fail(t, "Error starting proxy server")
	}

	//limitedServer.httpServer.SetKeepAlivesEnabled(false)
	okFn := func(conn net.Conn, proxy *server.Server, originURL *url.URL) {
		req := fmt.Sprintf(connectReq, originURL.Host, originURL.Host)
		conn.Write([]byte(req))
		var buf [400]byte
		_, err = conn.Read(buf[:])

		assert.NoError(t, err)

		time.Sleep(time.Millisecond * 100)
	}

	waitFn := func(conn net.Conn, proxy *server.Server, originURL *url.URL) {
		conn.SetReadDeadline(time.Now().Add(50 * time.Millisecond))

		req := fmt.Sprintf(connectReq, originURL.Host, originURL.Host)
		conn.Write([]byte(req))
		var buf [400]byte
		_, err = conn.Read(buf[:])

		if assert.Error(t, err) {
			e, ok := err.(*net.OpError)
			assert.True(t, ok && e.Timeout(), "should be a time out error")
		}
	}

	for i := 0; i < 5; i++ {
		go testRoundTrip(t, limitedServer, httpOriginServer, okFn)
	}

	time.Sleep(time.Millisecond * 10)

	for i := 0; i < 5; i++ {
		go testRoundTrip(t, limitedServer, httpOriginServer, waitFn)
	}

	time.Sleep(time.Millisecond * 100)

	for i := 0; i < 5; i++ {
		go testRoundTrip(t, limitedServer, httpOriginServer, okFn)
	}
}
예제 #26
0
func TestRemoveFromWhitelist(t *testing.T) {
	defer stopMockServers()
	proxiedURL, proxy := newMockServer(detourMsg)
	proxy.Timeout(200*time.Millisecond, detourMsg)
	mockURL, _ := newMockServer(directMsg)
	client := newClient(proxiedURL, 100*time.Millisecond)

	u, _ := url.Parse(mockURL)
	AddToWl(u.Host, false)
	_, err := client.Get(mockURL)
	if assert.Error(t, err, "should have error if reading times out through detour") {
		assert.False(t, whitelisted(u.Host), "should be removed from whitelist if reading times out through detour")
	}

}
예제 #27
0
func TestNotOKWithServerName(t *testing.T) {
	_, fdc, err := fdcount.Matching("TCP")
	if err != nil {
		t.Fatal(err)
	}

	conn, err := Dial("tcp", ADDR, true, nil)
	assert.Error(t, err, "There should have been a problem dialing")
	if err != nil {
		assert.Contains(t, err.Error(), CERTIFICATE_ERROR, "Wrong error on dial")
	}
	<-receivedServerNames

	closeAndCountFDs(t, conn, err, fdc)
}
예제 #28
0
func TestBadAddressToServer(t *testing.T) {
	l := startServer(t)
	req, err := buildCONNECTRequest("somebadaddressasdfdasfds.asdfasdf.dfads:532400", nil)
	if err != nil {
		t.Fatalf("Unable to build request: %s", err)
	}
	conn, err := net.Dial("tcp", l.Addr().String())
	if err != nil {
		t.Fatalf("Unable to dial server: %s", err)
	}
	err = req.Write(conn)
	if err != nil {
		t.Fatalf("Unable to make request: %s", err)
	}

	r := bufio.NewReader(conn)
	err = checkCONNECTResponse(r, req)
	assert.Error(t, err, "Connect response should be bad")
}
예제 #29
0
func TestReadTimeout(t *testing.T) {
	defer stopMockServers()
	proxiedURL, _ := newMockServer(detourMsg)
	mockURL, mock := newMockServer("")
	mock.Timeout(200*time.Millisecond, directMsg)

	client := &http.Client{Timeout: 100 * time.Millisecond}
	resp, err := client.Get(mockURL)
	assert.Error(t, err, "direct access to a timeout url should fail")

	u, _ := url.Parse(mockURL)
	client = newClient(proxiedURL, 100*time.Millisecond)
	resp, err = client.Get(mockURL)
	if assert.NoError(t, err, "should have no error if reading times out") {
		time.Sleep(50 * time.Millisecond)
		assert.True(t, wlTemporarily(u.Host), "should be added to whitelist if reading times out")
		assertContent(t, resp, detourMsg, "should detour if reading times out")
	}
}
예제 #30
0
func TestBadServer(t *testing.T) {
	l, err := net.Listen("tcp", "localhost:0")
	if err != nil {
		t.Fatalf("Unable to listen: %s", err)
	}

	go func() {
		conn, err := l.Accept()
		if err == nil {
			conn.Close()
		}
	}()

	dialer := NewDialer(Config{
		DialServer: func() (net.Conn, error) {
			return net.Dial("tcp", l.Addr().String())
		},
	})
	_, err = dialer.Dial("tcp", "www.google.com")
	assert.Error(t, err, "Dialing a server that disconnects too soon should have failed")
}