package upstreamimpl import ( "context" "encoding/json" "net/http" "net/http/httptest" "testing" "time" "git.5iot.com/iotlcm-public/iotlcm-upstream-chan/internal/model" "git.5iot.com/iotlcm-public/iotlcm-upstream-chan/internal/model/entity" "git.5iot.com/iotlcm-public/iotlcm-upstream-chan/internal/service" ) func TestMobilePublicTemplateRegistration(t *testing.T) { for _, templateKey := range []string{ sharedOneLinkMobilePublicTemplateKey, sharedOneLinkMobilePublicPreviousKey, sharedOneLinkMobilePublicLegacyKey, } { t.Run(templateKey, func(t *testing.T) { template, ok := service.UpstreamAPI().GetTemp(templateKey) if !ok || template == nil { t.Fatal("mobile public template not registered") } config := &model.SimChannelConfigItemCache{ Template: &entity.TSimChannelTemplate{ TempKey: templateKey, TempConfig: `{"token":{"provider":"mobile_public","baseUrl":"https://example.com","path":"/api/get/yd/api/msg"}}`, }, Channel: &entity.TSimChannels{ ChanKey: "daliuliang-test", ChanConfig: `{"userId":"102369"}`, AppSecret: "test-secret", }, } if instance := template.NewTemp(context.Background(), config); instance == nil { t.Fatal("mobile public channel failed to instantiate") } }) } } func TestMobilePublicSign(t *testing.T) { const timestamp = int64(1699606000) if got, want := mobilePublicSign("bbb", "aaa", timestamp), "2337f8d0d5c0cd9e415a3b3c27c4a595"; got != want { t.Fatalf("sign = %q, want %q", got, want) } } func TestMobilePublicTokenProviderFetch(t *testing.T) { now := time.Unix(1700000000, 0) server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { if r.Method != http.MethodPost || r.URL.Path != mobilePublicTokenPath { t.Fatalf("request = %s %s", r.Method, r.URL.Path) } var input struct { UserID int64 `json:"userid"` Time int64 `json:"time"` Sign string `json:"sign"` } if err := json.NewDecoder(r.Body).Decode(&input); err != nil { t.Fatal(err) } if input.UserID != 102369 || input.Time != now.Unix() { t.Fatalf("payload = %#v", input) } if want := mobilePublicSign("secret", "102369", input.Time); input.Sign != want { t.Fatalf("sign = %q, want %q", input.Sign, want) } _, _ = w.Write([]byte(`{"code":200,"msg":"success","data":{"token":"token-1","expire_time":1700003600}}`)) })) defer server.Close() provider := NewMobilePublicTokenProvider(MobilePublicTokenConfig{ BaseURL: server.URL, UserID: "102369", Secret: "secret", Timeout: time.Second, }) provider.now = func() time.Time { return now } token, err := provider.Fetch(context.Background()) if err != nil { t.Fatalf("fetch token: %v", err) } if token.Value != "token-1" || !token.ExpiresAt.Equal(time.Unix(1700003600, 0)) { t.Fatalf("token = %#v", token) } } func TestMobilePublicTokenProviderRejectsExpiredToken(t *testing.T) { now := time.Unix(1700000000, 0) server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { _, _ = w.Write([]byte(`{"code":200,"data":{"token":"token-1","expire_time":1699999999}}`)) })) defer server.Close() provider := NewMobilePublicTokenProvider(MobilePublicTokenConfig{ BaseURL: server.URL, UserID: "102369", Secret: "secret", Timeout: time.Second, }) provider.now = func() time.Time { return now } if _, err := provider.Fetch(context.Background()); err == nil { t.Fatal("expected expired token error") } } func TestMobilePublicTokenProviderRejectsNonNumericUserID(t *testing.T) { provider := NewMobilePublicTokenProvider(MobilePublicTokenConfig{ BaseURL: "http://127.0.0.1", UserID: "not-a-number", Secret: "secret", Timeout: time.Second, }) if _, err := provider.Fetch(context.Background()); err == nil { t.Fatal("expected invalid userId error") } }