github.com/vmware/transport-go@v1.3.4/plank/pkg/server/server_test.go (about)

     1  // Copyright 2019-2021 VMware, Inc.
     2  // SPDX-License-Identifier: BSD-2-Clause
     3  
     4  package server
     5  
     6  import (
     7  	"context"
     8  	"fmt"
     9  	"github.com/google/uuid"
    10  	"github.com/stretchr/testify/assert"
    11  	"github.com/vmware/transport-go/bus"
    12  	"github.com/vmware/transport-go/model"
    13  	"github.com/vmware/transport-go/plank/services"
    14  	"github.com/vmware/transport-go/service"
    15  	"golang.org/x/net/context/ctxhttp"
    16  	"io/ioutil"
    17  	"net/http"
    18  	"os"
    19  	"path/filepath"
    20  	"strings"
    21  	"sync"
    22  	"testing"
    23  )
    24  
    25  func TestNewPlatformServer(t *testing.T) {
    26  	bus.ResetBus()
    27  	service.ResetServiceRegistry()
    28  	port := GetTestPort()
    29  	config := GetBasicTestServerConfig(os.TempDir(), "stdout", "stdout", "stderr", port, true)
    30  	ps := NewPlatformServer(config)
    31  	assert.NotNil(t, ps)
    32  }
    33  
    34  func TestNewPlatformServer_EmptyRootDir(t *testing.T) {
    35  	bus.ResetBus()
    36  	service.ResetServiceRegistry()
    37  	port := GetTestPort()
    38  	newConfig := GetBasicTestServerConfig("", "stdout", "stdout", "stderr", port, true)
    39  	NewPlatformServer(newConfig)
    40  	wd, _ := os.Getwd()
    41  	assert.Equal(t, wd, newConfig.RootDir)
    42  }
    43  
    44  func TestNewPlatformServer_FileLog(t *testing.T) {
    45  	defer func() {
    46  		_ = os.Remove(filepath.Join(os.TempDir(), "testlog.log"))
    47  	}()
    48  
    49  	newBus := bus.ResetBus()
    50  	service.ResetServiceRegistry()
    51  	port := GetTestPort()
    52  	newConfig := GetBasicTestServerConfig(os.TempDir(), filepath.Join(os.TempDir(), "testlog.log"), "stdout", "stderr", port, true)
    53  	ps := NewPlatformServer(newConfig)
    54  	ps.(*platformServer).eventbus = newBus
    55  	assert.FileExists(t, filepath.Join(os.TempDir(), "testlog.log"))
    56  }
    57  
    58  func TestPlatformServer_StartServer(t *testing.T) {
    59  	newBus := bus.ResetBus()
    60  	service.ResetServiceRegistry()
    61  	port := GetTestPort()
    62  	config := GetBasicTestServerConfig(os.TempDir(), "stdout", "stdout", "stderr", port, true)
    63  	ps := NewPlatformServer(config)
    64  	ps.(*platformServer).eventbus = newBus
    65  	syschan := make(chan os.Signal, 1)
    66  	wg := sync.WaitGroup{}
    67  	wg.Add(1)
    68  	go ps.StartServer(syschan)
    69  	RunWhenServerReady(t, newBus, func(t2 *testing.T) {
    70  		rsp, err := http.Get(fmt.Sprintf("http://localhost:%d", port))
    71  		assert.Nil(t, err)
    72  
    73  		_, err = ioutil.ReadAll(rsp.Body)
    74  		assert.Nil(t, err)
    75  		assert.Equal(t, 404, rsp.StatusCode)
    76  		ps.StopServer()
    77  		wg.Done()
    78  	})
    79  
    80  	wg.Wait()
    81  }
    82  
    83  func TestPlatformServer_RegisterService(t *testing.T) {
    84  	newBus := bus.ResetBus()
    85  	service.ResetServiceRegistry()
    86  	port := GetTestPort()
    87  	config := GetBasicTestServerConfig(os.TempDir(), "stdout", "stdout", "stderr", port, true)
    88  	ps := NewPlatformServer(config)
    89  	ps.(*platformServer).eventbus = newBus
    90  
    91  	err := ps.RegisterService(services.NewPingPongService(), services.PingPongServiceChan)
    92  	assert.Nil(t, err)
    93  }
    94  
    95  func TestPlatformServer_SetHttpPathPrefixChannelBridge(t *testing.T) {
    96  	// get a new bus instance and create a new platform server instance
    97  	newBus := bus.ResetBus()
    98  	service.ResetServiceRegistry()
    99  	port := GetTestPort()
   100  	config := GetBasicTestServerConfig(os.TempDir(), "stdout", "stdout", "stderr", port, true)
   101  	ps := NewPlatformServer(config)
   102  	ps.(*platformServer).eventbus = newBus
   103  
   104  	// register a service
   105  	_ = ps.RegisterService(services.NewPingPongService(), services.PingPongServiceChan)
   106  
   107  	// set PathPrefix bridge
   108  	bridgeConfig := &service.RESTBridgeConfig{
   109  		ServiceChannel: services.PingPongServiceChan,
   110  		Uri:            "/ping-pong",
   111  		FabricRequestBuilder: func(w http.ResponseWriter, r *http.Request) model.Request {
   112  			return model.Request{
   113  				Payload: "hello",
   114  				Request: "ping-get",
   115  			}
   116  		},
   117  	}
   118  	ps.SetHttpPathPrefixChannelBridge(bridgeConfig)
   119  
   120  	syschan := make(chan os.Signal, 1)
   121  	wg := sync.WaitGroup{}
   122  	wg.Add(1)
   123  	go ps.StartServer(syschan)
   124  	RunWhenServerReady(t, newBus, func(t2 *testing.T) {
   125  		// GET
   126  		rsp, err := http.Get(fmt.Sprintf("http://localhost:%d/ping-pong", port))
   127  		assert.Nil(t, err)
   128  
   129  		body, err := ioutil.ReadAll(rsp.Body)
   130  		assert.Nil(t, err)
   131  		assert.Contains(t, string(body), "hello")
   132  
   133  		// POST
   134  		rsp, err = http.Post(fmt.Sprintf("http://localhost:%d/ping-pong", port), "application/json", strings.NewReader(""))
   135  		assert.Nil(t, err)
   136  		body, err = ioutil.ReadAll(rsp.Body)
   137  		assert.Nil(t, err)
   138  		assert.Contains(t, string(body), "hello")
   139  
   140  		// DELETE
   141  		req, _ := http.NewRequest("DELETE", fmt.Sprintf("http://localhost:%d/ping-pong", port), strings.NewReader(""))
   142  		rsp, err = ctxhttp.Do(context.Background(), http.DefaultClient, req)
   143  		assert.Nil(t, err)
   144  		body, err = ioutil.ReadAll(rsp.Body)
   145  		assert.Nil(t, err)
   146  		assert.Contains(t, string(body), "hello")
   147  
   148  		ps.StopServer()
   149  		service.GetServiceRegistry().UnregisterService(services.PingPongServiceChan)
   150  		wg.Done()
   151  	})
   152  
   153  	wg.Wait()
   154  }
   155  
   156  func TestPlatformServer_SetHttpChannelBridge(t *testing.T) {
   157  	newBus := bus.ResetBus()
   158  	service.ResetServiceRegistry()
   159  	port := GetTestPort()
   160  	config := GetBasicTestServerConfig(os.TempDir(), "stdout", "stdout", "stderr", port, true)
   161  	ps := NewPlatformServer(config)
   162  	ps.(*platformServer).eventbus = newBus
   163  	_ = ps.RegisterService(services.NewPingPongService(), services.PingPongServiceChan)
   164  
   165  	syschan := make(chan os.Signal, 1)
   166  	wg := sync.WaitGroup{}
   167  	wg.Add(1)
   168  	go ps.StartServer(syschan)
   169  	RunWhenServerReady(t, newBus, func(t2 *testing.T) {
   170  		rsp, err := http.Get(fmt.Sprintf("http://localhost:%d/rest/ping-pong2?message=hello", port))
   171  		assert.Nil(t, err)
   172  
   173  		body, err := ioutil.ReadAll(rsp.Body)
   174  		assert.Nil(t, err)
   175  		assert.Contains(t, string(body), "hello")
   176  		ps.StopServer()
   177  		service.GetServiceRegistry().UnregisterService(services.PingPongServiceChan)
   178  		wg.Done()
   179  	})
   180  
   181  	wg.Wait()
   182  }
   183  
   184  func TestPlatformServer_UnknownRequest(t *testing.T) {
   185  	newBus := bus.ResetBus()
   186  	service.ResetServiceRegistry()
   187  	port := GetTestPort()
   188  	config := GetBasicTestServerConfig(os.TempDir(), "stdout", "stdout", "stderr", port, true)
   189  	ps := NewPlatformServer(config)
   190  	ps.(*platformServer).eventbus = newBus
   191  	_ = ps.RegisterService(services.NewPingPongService(), services.PingPongServiceChan)
   192  	defer service.GetServiceRegistry().UnregisterService(services.PingPongServiceChan)
   193  	setupBridge(ps, "/ping", "GET", services.PingPongServiceChan, "bubble")
   194  
   195  	syschan := make(chan os.Signal, 1)
   196  	wg := sync.WaitGroup{}
   197  	wg.Add(1)
   198  	go ps.StartServer(syschan)
   199  	RunWhenServerReady(t, newBus, func(t2 *testing.T) {
   200  		rsp, err := http.Get(fmt.Sprintf("http://localhost:%d/ping?msg=hello", port))
   201  		assert.Nil(t, err)
   202  
   203  		body, err := ioutil.ReadAll(rsp.Body)
   204  		assert.Nil(t, err)
   205  		assert.Contains(t, string(body), "unsupported request")
   206  
   207  		ps.StopServer()
   208  		wg.Done()
   209  	})
   210  
   211  	wg.Wait()
   212  }
   213  
   214  func setupBridge(ps PlatformServer, endpoint, method, channel, request string) {
   215  	bridgeConfig := &service.RESTBridgeConfig{
   216  		ServiceChannel: channel,
   217  		Uri:            endpoint,
   218  		Method:         method,
   219  		AllowHead:      false,
   220  		AllowOptions:   false,
   221  		FabricRequestBuilder: func(w http.ResponseWriter, r *http.Request) model.Request {
   222  			q := r.URL.Query()
   223  			return model.Request{
   224  				Id:      &uuid.UUID{},
   225  				Payload: q.Get("msg"),
   226  				Request: request}
   227  
   228  		},
   229  	}
   230  	ps.SetHttpChannelBridge(bridgeConfig)
   231  }