github.com/polarismesh/polaris@v1.17.8/store/boltdb/ratelimit_test.go (about)

     1  /**
     2   * Tencent is pleased to support the open source community by making Polaris available.
     3   *
     4   * Copyright (C) 2019 THL A29 Limited, a Tencent company. All rights reserved.
     5   *
     6   * Licensed under the BSD 3-Clause License (the "License");
     7   * you may not use this file except in compliance with the License.
     8   * You may obtain a copy of the License at
     9   *
    10   * https://opensource.org/licenses/BSD-3-Clause
    11   *
    12   * Unless required by applicable law or agreed to in writing, software distributed
    13   * under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
    14   * CONDITIONS OF ANY KIND, either express or implied. See the License for the
    15   * specific language governing permissions and limitations under the License.
    16   */
    17  
    18  package boltdb
    19  
    20  import (
    21  	"math/rand"
    22  	"reflect"
    23  	"sort"
    24  	"strings"
    25  	"testing"
    26  	"time"
    27  
    28  	"github.com/google/uuid"
    29  	"github.com/stretchr/testify/assert"
    30  
    31  	"github.com/polarismesh/polaris/common/model"
    32  )
    33  
    34  var letterRunes = []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ")
    35  
    36  func RandStringRunes(n int) string {
    37  	b := make([]rune, n)
    38  	for i := range b {
    39  		b[i] = letterRunes[rand.Intn(len(letterRunes))]
    40  	}
    41  	return string(b)
    42  }
    43  
    44  func createTestRateLimit(id string, createId bool) *model.RateLimit {
    45  
    46  	if strings.Compare(id, "") == 0 && createId {
    47  		id = uuid.NewString()
    48  	}
    49  
    50  	return &model.RateLimit{
    51  		ID:         id,
    52  		ServiceID:  RandStringRunes(10),
    53  		Labels:     RandStringRunes(20),
    54  		Rule:       RandStringRunes(20),
    55  		Revision:   RandStringRunes(30),
    56  		Valid:      false,
    57  		CreateTime: time.Now(),
    58  		ModifyTime: time.Now(),
    59  		EnableTime: time.Now(),
    60  	}
    61  }
    62  
    63  func Test_rateLimitStore_CreateRateLimit(t *testing.T) {
    64  	CreateTableDBHandlerAndRun(t, "test_ratelimit", func(t *testing.T, handler BoltHandler) {
    65  
    66  		testVal := createTestRateLimit("", true)
    67  
    68  		store := &rateLimitStore{
    69  			handler: handler,
    70  		}
    71  		if err := store.CreateRateLimit(testVal); (err != nil) != false {
    72  			t.Fatalf("rateLimitStore.CreateRateLimit() error = %v, wantErr %v", err, false)
    73  		}
    74  
    75  		saveVal, err := store.GetRateLimitWithID(testVal.ID)
    76  		if err != nil {
    77  			t.Fatal(err)
    78  		}
    79  
    80  		tN := time.Now()
    81  		tVal := testVal
    82  		tVal.ModifyTime = tN
    83  		tVal.CreateTime = tN
    84  		tVal.EnableTime = tN
    85  		saveVal.ModifyTime = tN
    86  		saveVal.CreateTime = tN
    87  		saveVal.EnableTime = tN
    88  		if !reflect.DeepEqual(saveVal, tVal) {
    89  			t.FailNow()
    90  		}
    91  	})
    92  }
    93  
    94  func Test_rateLimitStore_CreateRateLimitWithBadParam(t *testing.T) {
    95  	CreateTableDBHandlerAndRun(t, "test_ratelimit", func(t *testing.T, handler BoltHandler) {
    96  
    97  		testVal := createTestRateLimit("", false)
    98  
    99  		store := &rateLimitStore{
   100  			handler: handler,
   101  		}
   102  		if err := store.CreateRateLimit(testVal); err == nil {
   103  			t.Fatalf("rateLimitStore.CreateRateLimit() need to return error")
   104  		} else {
   105  			if strings.Compare(ErrBadParam.Error(), err.Error()) != 0 {
   106  				t.Fatalf("error msg must : %s", ErrBadParam.Error())
   107  			}
   108  		}
   109  	})
   110  }
   111  
   112  func Test_rateLimitStore_UpdateRateLimit(t *testing.T) {
   113  	CreateTableDBHandlerAndRun(t, "test_ratelimit", func(t *testing.T, handler BoltHandler) {
   114  		r := &rateLimitStore{
   115  			handler: handler,
   116  		}
   117  
   118  		testVal := createTestRateLimit("", true)
   119  
   120  		if err := r.CreateRateLimit(testVal); err != nil {
   121  			t.Fatalf("rateLimitStore.CreateRateLimit() error = %v", err)
   122  		}
   123  
   124  		newVal := *testVal
   125  		newVal.Revision = RandStringRunes(15)
   126  
   127  		if err := r.UpdateRateLimit(&newVal); err != nil {
   128  			t.Errorf("rateLimitStore.UpdateRateLimit() error = %v", err)
   129  		}
   130  
   131  		saveVal, err := r.GetRateLimitWithID(newVal.ID)
   132  		if err != nil {
   133  			t.Fatal(err)
   134  		}
   135  
   136  		tN := time.Now()
   137  
   138  		newVal.ModifyTime = tN
   139  		newVal.CreateTime = tN
   140  		newVal.EnableTime = tN
   141  		saveVal.ModifyTime = tN
   142  		saveVal.CreateTime = tN
   143  		saveVal.EnableTime = tN
   144  
   145  		if !reflect.DeepEqual(saveVal, &newVal) {
   146  			t.FailNow()
   147  		}
   148  	})
   149  
   150  }
   151  
   152  func Test_rateLimitStore_DeleteRateLimit(t *testing.T) {
   153  	CreateTableDBHandlerAndRun(t, "test_ratelimit", func(t *testing.T, handler BoltHandler) {
   154  		r := &rateLimitStore{
   155  			handler: handler,
   156  		}
   157  
   158  		testVal := createTestRateLimit("", true)
   159  
   160  		if err := r.CreateRateLimit(testVal); err != nil {
   161  			t.Fatalf("rateLimitStore.CreateRateLimit() error = %v", err)
   162  		}
   163  
   164  		if err := r.DeleteRateLimit(testVal); err != nil {
   165  			t.Errorf("rateLimitStore.DeleteRateLimit() error = %v", err)
   166  		}
   167  
   168  		saveVal, err := r.GetRateLimitWithID(testVal.ID)
   169  		if err != nil {
   170  			t.Fatal(err)
   171  		}
   172  
   173  		assert.Nil(t, saveVal, "delete failed")
   174  	})
   175  }
   176  
   177  func Test_rateLimitStore_GetExtendRateLimits(t *testing.T) {
   178  	CreateTableDBHandlerAndRun(t, "test_ratelimit", func(t *testing.T, handler BoltHandler) {
   179  		r := &rateLimitStore{
   180  			handler: handler,
   181  		}
   182  
   183  		svcS := &serviceStore{
   184  			handler: handler,
   185  		}
   186  
   187  		vals := make([]*model.RateLimit, 0)
   188  
   189  		Cluster_2 := make([]*model.RateLimit, 0)
   190  		Cluster_3 := make([]*model.RateLimit, 0)
   191  		Cluster_5 := make([]*model.RateLimit, 0)
   192  
   193  		for i := 0; i < 10; i++ {
   194  			testVal := createTestRateLimit(uuid.NewString(), false)
   195  
   196  			if i%2 == 0 {
   197  				testVal.Method = "Service_Cluster_2"
   198  				testVal.Labels = "Cluster_2@@Labels@@12345"
   199  				Cluster_2 = append(Cluster_2, testVal)
   200  			} else if i%3 == 0 {
   201  				testVal.Method = "Service_Cluster_3"
   202  				testVal.Labels = "Cluster_3@@Labels@@67890"
   203  				Cluster_3 = append(Cluster_3, testVal)
   204  			} else if i%5 == 0 {
   205  				testVal.Method = "Service_Cluster_5"
   206  				testVal.Labels = "Cluster_5@@Labels@@abcde"
   207  				Cluster_5 = append(Cluster_5, testVal)
   208  			}
   209  
   210  			//  create service
   211  			svcS.AddService(&model.Service{
   212  				ID:        testVal.ServiceID,
   213  				Name:      testVal.ServiceID,
   214  				Namespace: testVal.ServiceID,
   215  				Owner:     "Polaris",
   216  				Token:     testVal.Revision,
   217  			})
   218  
   219  			vals = append(vals, testVal)
   220  			if err := r.CreateRateLimit(testVal); err != nil {
   221  				t.Fatalf("rateLimitStore.CreateRateLimit() error = %v", err)
   222  			}
   223  		}
   224  
   225  		// Test 1
   226  		got, got1, err := r.GetExtendRateLimits(map[string]string{
   227  			"method": "Cluster_2",
   228  		}, 0, 10)
   229  		if err != nil {
   230  			t.Errorf("rateLimitStore.GetExtendRateLimits() error = %v", err)
   231  			return
   232  		}
   233  		if int(got) != len(Cluster_2) {
   234  			t.Fatalf("expect result cnt : %d, actual cnt : %d", len(Cluster_2), got)
   235  		}
   236  
   237  		got1Limits := make([]*model.RateLimit, 0)
   238  		for i := range got1 {
   239  			got1Limits = append(got1Limits, got1[i].RateLimit)
   240  		}
   241  
   242  		tN := time.Now()
   243  
   244  		sort.Slice(got1, func(i, j int) bool {
   245  			got1Limits[i].CreateTime = tN
   246  			got1Limits[i].ModifyTime = tN
   247  			got1Limits[i].EnableTime = tN
   248  			got1Limits[j].CreateTime = tN
   249  			got1Limits[j].ModifyTime = tN
   250  			got1Limits[j].EnableTime = tN
   251  			return strings.Compare(got1Limits[i].ID, got1Limits[j].ID) < 0
   252  		})
   253  		sort.Slice(Cluster_2, func(i, j int) bool {
   254  			Cluster_2[i].CreateTime = tN
   255  			Cluster_2[i].ModifyTime = tN
   256  			Cluster_2[i].EnableTime = tN
   257  			Cluster_2[j].CreateTime = tN
   258  			Cluster_2[j].ModifyTime = tN
   259  			Cluster_2[j].EnableTime = tN
   260  			return strings.Compare(Cluster_2[i].ID, Cluster_2[j].ID) < 0
   261  		})
   262  		assert.ElementsMatch(t, got1Limits, Cluster_2, "result must be equal")
   263  
   264  		// Test 2
   265  		got, got1, err = r.GetExtendRateLimits(map[string]string{
   266  			strings.ToLower("Labels"): "Cluster_3",
   267  		}, 0, 10)
   268  		if err != nil {
   269  			t.Errorf("rateLimitStore.GetExtendRateLimits() error = %v", err)
   270  			return
   271  		}
   272  		if int(got) != len(Cluster_3) {
   273  			t.Fatalf("expect result cnt : %d, actual cnt : %d", len(Cluster_3), got)
   274  		}
   275  
   276  		got1Limits = make([]*model.RateLimit, 0)
   277  		for i := range got1 {
   278  			got1Limits = append(got1Limits, got1[i].RateLimit)
   279  		}
   280  
   281  		sort.Slice(got1, func(i, j int) bool {
   282  			got1Limits[i].CreateTime = tN
   283  			got1Limits[i].ModifyTime = tN
   284  			got1Limits[i].EnableTime = tN
   285  			got1Limits[j].CreateTime = tN
   286  			got1Limits[j].ModifyTime = tN
   287  			got1Limits[j].EnableTime = tN
   288  			return strings.Compare(got1Limits[i].ID, got1Limits[j].ID) < 0
   289  		})
   290  		sort.Slice(Cluster_3, func(i, j int) bool {
   291  			Cluster_3[i].CreateTime = tN
   292  			Cluster_3[i].ModifyTime = tN
   293  			Cluster_3[i].EnableTime = tN
   294  			Cluster_3[j].CreateTime = tN
   295  			Cluster_3[j].ModifyTime = tN
   296  			Cluster_3[j].EnableTime = tN
   297  			return strings.Compare(Cluster_3[i].ID, Cluster_3[j].ID) < 0
   298  		})
   299  		assert.ElementsMatch(t, got1Limits, Cluster_3, "result must be equal")
   300  	})
   301  
   302  }
   303  
   304  func Test_rateLimitStore_GetExtendRateLimitsDisable(t *testing.T) {
   305  	CreateTableDBHandlerAndRun(t, "test_ratelimit_disable", func(t *testing.T, handler BoltHandler) {
   306  		r := &rateLimitStore{
   307  			handler: handler,
   308  		}
   309  
   310  		svcS := &serviceStore{
   311  			handler: handler,
   312  		}
   313  
   314  		vals := make([]*model.RateLimit, 0)
   315  
   316  		for i := 0; i < 10; i++ {
   317  			testVal := createTestRateLimit(uuid.NewString(), false)
   318  			if i%2 == 0 {
   319  				testVal.Disable = true
   320  			} else {
   321  				testVal.Disable = false
   322  			}
   323  			//  create service
   324  			svcS.AddService(&model.Service{
   325  				ID:        testVal.ServiceID,
   326  				Name:      testVal.ServiceID,
   327  				Namespace: testVal.ServiceID,
   328  				Owner:     "Polaris",
   329  				Token:     testVal.Revision,
   330  			})
   331  
   332  			vals = append(vals, testVal)
   333  			if err := r.CreateRateLimit(testVal); err != nil {
   334  				t.Fatalf("rateLimitStore.CreateRateLimit() error = %v", err)
   335  			}
   336  		}
   337  
   338  		// Test 1
   339  		_, ret, err := r.GetExtendRateLimits(map[string]string{
   340  			"disable": "true",
   341  		}, 0, 100)
   342  		if err != nil {
   343  			t.Errorf("rateLimitStore.GetExtendRateLimits() error = %v", err)
   344  			return
   345  		}
   346  		assert.Equal(t, int32(5), int32(len(ret)))
   347  
   348  		// Test 1
   349  		_, ret, err = r.GetExtendRateLimits(map[string]string{
   350  			"disable": "false",
   351  		}, 0, 100)
   352  		if err != nil {
   353  			t.Errorf("rateLimitStore.GetExtendRateLimits() error = %v", err)
   354  			return
   355  		}
   356  		assert.Equal(t, int32(5), int32(len(ret)))
   357  	})
   358  }
   359  
   360  func Test_rateLimitStore_GetRateLimitWithID(t *testing.T) {
   361  	CreateTableDBHandlerAndRun(t, "test_ratelimit", func(t *testing.T, handler BoltHandler) {
   362  		r := &rateLimitStore{
   363  			handler: handler,
   364  		}
   365  
   366  		testVal := createTestRateLimit("", true)
   367  
   368  		if err := r.CreateRateLimit(testVal); err != nil {
   369  			t.Fatalf("rateLimitStore.CreateRateLimit() error = %v", err)
   370  		}
   371  
   372  		saveVal, err := r.GetRateLimitWithID(testVal.ID)
   373  		if err != nil {
   374  			t.Errorf("rateLimitStore.GetRateLimitWithID() error = %v", err)
   375  		}
   376  
   377  		tN := time.Now()
   378  		testVal.CreateTime = tN
   379  		testVal.ModifyTime = tN
   380  		testVal.EnableTime = tN
   381  		saveVal.CreateTime = tN
   382  		saveVal.ModifyTime = tN
   383  		saveVal.EnableTime = tN
   384  
   385  		assert.Equal(t, testVal, saveVal, "not equal")
   386  	})
   387  }
   388  
   389  func Test_rateLimitStore_GetRateLimitsForCache(t *testing.T) {
   390  	CreateTableDBHandlerAndRun(t, "test_ratelimit", func(t *testing.T, handler BoltHandler) {
   391  		r := &rateLimitStore{
   392  			handler: handler,
   393  		}
   394  
   395  		vals := make([]*model.RateLimit, 0, 10)
   396  
   397  		tN := time.Now().Add(time.Duration(-30) * time.Minute)
   398  
   399  		for i := 0; i < 10; i++ {
   400  			testVal := createTestRateLimit(uuid.NewString(), false)
   401  			testVal.Valid = true
   402  			testVal.ModifyTime = tN.Add(time.Duration(i+20) * time.Minute)
   403  			vals = append(vals, testVal)
   404  			if err := r.createRateLimit(testVal); err != nil {
   405  				t.Fatalf("rateLimitStore.CreateRateLimit() error = %v", err)
   406  			}
   407  		}
   408  
   409  		testT_1 := time.Now().Add(time.Duration(-5) * time.Minute)
   410  
   411  		limits, err := r.GetRateLimitsForCache(testT_1, false)
   412  		if err != nil {
   413  			t.Fatal(err)
   414  		}
   415  
   416  		expectList := make([]*model.RateLimit, 0)
   417  
   418  		for i := range vals {
   419  			item := vals[i]
   420  			if !item.ModifyTime.Before(testT_1) {
   421  				expectList = append(expectList, item)
   422  			}
   423  		}
   424  
   425  		assert.Equal(t, len(expectList), len(limits), "len(limits) not equal len(expectList)")
   426  
   427  		for i := range expectList {
   428  			expectList[i].CreateTime = testT_1
   429  			expectList[i].ModifyTime = testT_1
   430  			expectList[i].EnableTime = testT_1
   431  			limits[i].CreateTime = testT_1
   432  			limits[i].ModifyTime = testT_1
   433  			limits[i].EnableTime = testT_1
   434  		}
   435  
   436  		assert.ElementsMatch(t, limits, expectList, "not equal")
   437  
   438  	})
   439  
   440  }