mirror of https://github.com/dapr/go-sdk.git
Report SDK version to Dapr as User-Agent (#328)
* Report SDK version to Dapr
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
* Fixed typos
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
* Fixes
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
* 💄
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
* Making the linter happy-maybe
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
* Update linter to support go:embed comments
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
This commit is contained in:
parent
014b4d6836
commit
718044ad12
|
|
@ -20,6 +20,14 @@ jobs:
|
|||
- name: Checkout
|
||||
uses: actions/checkout@v2
|
||||
|
||||
- name: Check sdk-version file
|
||||
run: |
|
||||
if [[ "$(head -n1 version/sdk-version)" != "${{ github.ref }}" ]]; then
|
||||
echo "File version/sdk-version needs to be updated to ${{ github.ref }}"
|
||||
exit 1
|
||||
fi
|
||||
shell: bash
|
||||
|
||||
- name: Tidy
|
||||
run: |
|
||||
go mod tidy -compat=1.17
|
||||
|
|
@ -39,7 +47,7 @@ jobs:
|
|||
with:
|
||||
tag_name: ${{ github.ref }}
|
||||
release_name: Release ${{ github.ref }}
|
||||
body: Automatic go Dapr client release
|
||||
body: Automatic Go Dapr client release
|
||||
draft: false
|
||||
prerelease: false
|
||||
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ jobs:
|
|||
runs-on: ubuntu-latest
|
||||
env:
|
||||
GOVER: 1.17
|
||||
GOLANGCILINT_VER: v1.31
|
||||
GOLANGCILINT_VER: v1.48.0
|
||||
|
||||
steps:
|
||||
|
||||
|
|
|
|||
|
|
@ -244,9 +244,28 @@ linters:
|
|||
- goerr113
|
||||
- nestif
|
||||
- nlreturn
|
||||
- tagliatelle
|
||||
- ifshort
|
||||
- forbidigo
|
||||
- exhaustive
|
||||
- contextcheck
|
||||
- exhaustruct
|
||||
- exhaustivestruct
|
||||
- wrapcheck
|
||||
- predeclared
|
||||
- varnamelen
|
||||
- ireturn
|
||||
- noctx
|
||||
- forcetypeassert
|
||||
- cyclop
|
||||
- errchkjson
|
||||
- godot
|
||||
- gci
|
||||
- paralleltest
|
||||
- nonamedreturns
|
||||
- nosnakecase
|
||||
- nilnil
|
||||
- staticcheck
|
||||
issues:
|
||||
exclude-rules:
|
||||
- path: .*_test.go
|
||||
|
|
|
|||
|
|
@ -25,6 +25,7 @@ import (
|
|||
|
||||
"github.com/dapr/go-sdk/actor"
|
||||
"github.com/dapr/go-sdk/actor/config"
|
||||
"github.com/dapr/go-sdk/version"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
"google.golang.org/grpc"
|
||||
|
|
@ -44,8 +45,8 @@ const (
|
|||
traceparentKey = "traceparent"
|
||||
apiTokenKey = "dapr-api-token" /* #nosec */
|
||||
apiTokenEnvVarName = "DAPR_API_TOKEN" /* #nosec */
|
||||
clientDefaultTimoutSeconds = 5
|
||||
clientTimoutSecondsEnvVarName = "DAPR_CLIENT_TIMEOUT_SECONDS"
|
||||
clientDefaultTimeoutSeconds = 5
|
||||
clientTimeoutSecondsEnvVarName = "DAPR_CLIENT_TIMEOUT_SECONDS"
|
||||
)
|
||||
|
||||
var (
|
||||
|
|
@ -222,7 +223,7 @@ func NewClientWithPort(port string) (client Client, err error) {
|
|||
// NewClientWithAddress instantiates Dapr using specific address (including port).
|
||||
func NewClientWithAddress(address string) (client Client, err error) {
|
||||
if address == "" {
|
||||
return nil, errors.New("nil address")
|
||||
return nil, errors.New("empty address")
|
||||
}
|
||||
logger.Printf("dapr client initializing for: %s", address)
|
||||
|
||||
|
|
@ -230,28 +231,29 @@ func NewClientWithAddress(address string) (client Client, err error) {
|
|||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
ctx, ctxCancel := context.WithTimeout(context.Background(), time.Duration(timeoutSeconds)*time.Second)
|
||||
ctx, cancel := context.WithTimeout(context.Background(), time.Duration(timeoutSeconds)*time.Second)
|
||||
conn, err := grpc.DialContext(
|
||||
ctx,
|
||||
address,
|
||||
grpc.WithTransportCredentials(insecure.NewCredentials()),
|
||||
grpc.WithUserAgent("dapr-sdk-go/"+version.SDKVersion),
|
||||
grpc.WithBlock(),
|
||||
)
|
||||
cancel()
|
||||
if err != nil {
|
||||
ctxCancel()
|
||||
return nil, errors.Wrapf(err, "error creating connection to '%s': %v", address, err)
|
||||
return nil, fmt.Errorf("error creating connection to '%s': %w", address, err)
|
||||
}
|
||||
if hasToken := os.Getenv(apiTokenEnvVarName); hasToken != "" {
|
||||
logger.Println("client uses API token")
|
||||
}
|
||||
|
||||
return newClientWithConnectionAndCancelFunc(conn, ctxCancel), nil
|
||||
return NewClientWithConnection(conn), nil
|
||||
}
|
||||
|
||||
func getClientTimeoutSeconds() (int, error) {
|
||||
timeoutStr := os.Getenv(clientTimoutSecondsEnvVarName)
|
||||
timeoutStr := os.Getenv(clientTimeoutSecondsEnvVarName)
|
||||
if len(timeoutStr) == 0 {
|
||||
return clientDefaultTimoutSeconds, nil
|
||||
return clientDefaultTimeoutSeconds, nil
|
||||
}
|
||||
timeoutVar, err := strconv.Atoi(timeoutStr)
|
||||
if err != nil {
|
||||
|
|
@ -269,10 +271,14 @@ func NewClientWithSocket(socket string) (client Client, err error) {
|
|||
return nil, errors.New("nil socket")
|
||||
}
|
||||
logger.Printf("dapr client initializing for: %s", socket)
|
||||
addr := fmt.Sprintf("unix://%s", socket)
|
||||
conn, err := grpc.Dial(addr, grpc.WithTransportCredentials(insecure.NewCredentials()))
|
||||
addr := "unix://" + socket
|
||||
conn, err := grpc.Dial(
|
||||
addr,
|
||||
grpc.WithTransportCredentials(insecure.NewCredentials()),
|
||||
grpc.WithUserAgent("dapr-sdk-go/"+version.SDKVersion),
|
||||
)
|
||||
if err != nil {
|
||||
return nil, errors.Wrapf(err, "error creating connection to '%s': %v", addr, err)
|
||||
return nil, fmt.Errorf("error creating connection to '%s': %w", addr, err)
|
||||
}
|
||||
if hasToken := os.Getenv(apiTokenEnvVarName); hasToken != "" {
|
||||
logger.Println("client uses API token")
|
||||
|
|
@ -282,16 +288,8 @@ func NewClientWithSocket(socket string) (client Client, err error) {
|
|||
|
||||
// NewClientWithConnection instantiates Dapr client using specific connection.
|
||||
func NewClientWithConnection(conn *grpc.ClientConn) Client {
|
||||
return newClientWithConnectionAndCancelFunc(conn, func() {})
|
||||
}
|
||||
|
||||
func newClientWithConnectionAndCancelFunc(
|
||||
conn *grpc.ClientConn,
|
||||
cancelFunc context.CancelFunc,
|
||||
) Client {
|
||||
return &GRPCClient{
|
||||
connection: conn,
|
||||
ctxCancelFunc: cancelFunc,
|
||||
protoClient: pb.NewDaprClient(conn),
|
||||
authToken: os.Getenv(apiTokenEnvVarName),
|
||||
}
|
||||
|
|
@ -300,14 +298,12 @@ func newClientWithConnectionAndCancelFunc(
|
|||
// GRPCClient is the gRPC implementation of Dapr client.
|
||||
type GRPCClient struct {
|
||||
connection *grpc.ClientConn
|
||||
ctxCancelFunc context.CancelFunc
|
||||
protoClient pb.DaprClient
|
||||
authToken string
|
||||
}
|
||||
|
||||
// Close cleans up all resources created by the client.
|
||||
func (c *GRPCClient) Close() {
|
||||
c.ctxCancelFunc()
|
||||
if c.connection != nil {
|
||||
c.connection.Close()
|
||||
c.connection = nil
|
||||
|
|
|
|||
|
|
@ -27,6 +27,7 @@ import (
|
|||
"github.com/google/uuid"
|
||||
"github.com/pkg/errors"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
"google.golang.org/grpc"
|
||||
"google.golang.org/grpc/credentials/insecure"
|
||||
"google.golang.org/grpc/test/bufconn"
|
||||
|
|
@ -85,7 +86,7 @@ func TestNewClient(t *testing.T) {
|
|||
t.Run("new client closed with token", func(t *testing.T) {
|
||||
t.Setenv(apiTokenEnvVarName, "test")
|
||||
c, err := NewClientWithSocket(testSocket)
|
||||
assert.NoError(t, err)
|
||||
require.NoError(t, err)
|
||||
defer c.Close()
|
||||
c.WithAuthToken("")
|
||||
})
|
||||
|
|
@ -101,21 +102,21 @@ func TestNewClient(t *testing.T) {
|
|||
t.Run("new socket client closed with token", func(t *testing.T) {
|
||||
t.Setenv(apiTokenEnvVarName, "test")
|
||||
c, err := NewClientWithSocket(testSocket)
|
||||
assert.NoError(t, err)
|
||||
require.NoError(t, err)
|
||||
defer c.Close()
|
||||
c.WithAuthToken("")
|
||||
})
|
||||
|
||||
t.Run("new socket client closed with empty token", func(t *testing.T) {
|
||||
c, err := NewClientWithSocket(testSocket)
|
||||
assert.NoError(t, err)
|
||||
require.NoError(t, err)
|
||||
defer c.Close()
|
||||
c.WithAuthToken("")
|
||||
})
|
||||
|
||||
t.Run("new socket client with trace ID", func(t *testing.T) {
|
||||
c, err := NewClientWithSocket(testSocket)
|
||||
assert.NoError(t, err)
|
||||
require.NoError(t, err)
|
||||
defer c.Close()
|
||||
ctx := c.WithTraceID(context.Background(), "")
|
||||
_ = c.WithTraceID(ctx, "test")
|
||||
|
|
@ -197,33 +198,33 @@ func getTestClientWithSocket(ctx context.Context) (client Client, closer func())
|
|||
|
||||
func Test_getClientTimeoutSeconds(t *testing.T) {
|
||||
t.Run("empty env var", func(t *testing.T) {
|
||||
os.Setenv(clientTimoutSecondsEnvVarName, "")
|
||||
t.Setenv(clientTimeoutSecondsEnvVarName, "")
|
||||
got, err := getClientTimeoutSeconds()
|
||||
assert.NoError(t, err)
|
||||
assert.Equal(t, clientDefaultTimoutSeconds, got)
|
||||
assert.Equal(t, clientDefaultTimeoutSeconds, got)
|
||||
})
|
||||
|
||||
t.Run("invalid env var", func(t *testing.T) {
|
||||
os.Setenv(clientTimoutSecondsEnvVarName, "invalid")
|
||||
t.Setenv(clientTimeoutSecondsEnvVarName, "invalid")
|
||||
_, err := getClientTimeoutSeconds()
|
||||
assert.Error(t, err)
|
||||
})
|
||||
|
||||
t.Run("normal env var", func(t *testing.T) {
|
||||
os.Setenv(clientTimoutSecondsEnvVarName, "7")
|
||||
t.Setenv(clientTimeoutSecondsEnvVarName, "7")
|
||||
got, err := getClientTimeoutSeconds()
|
||||
assert.NoError(t, err)
|
||||
assert.Equal(t, 7, got)
|
||||
})
|
||||
|
||||
t.Run("zero env var", func(t *testing.T) {
|
||||
os.Setenv(clientTimoutSecondsEnvVarName, "0")
|
||||
t.Setenv(clientTimeoutSecondsEnvVarName, "0")
|
||||
_, err := getClientTimeoutSeconds()
|
||||
assert.Error(t, err)
|
||||
})
|
||||
|
||||
t.Run("negative env var", func(t *testing.T) {
|
||||
os.Setenv(clientTimoutSecondsEnvVarName, "-3")
|
||||
t.Setenv(clientTimeoutSecondsEnvVarName, "-3")
|
||||
_, err := getClientTimeoutSeconds()
|
||||
assert.Error(t, err)
|
||||
})
|
||||
|
|
|
|||
|
|
@ -83,8 +83,8 @@ func (c *GRPCClient) SubscribeConfigurationItems(ctx context.Context, storeName
|
|||
go func() {
|
||||
for {
|
||||
rsp, err := client.Recv()
|
||||
if err == io.EOF || rsp == nil {
|
||||
// receive goroutine would close if unsubscribe is called
|
||||
if errors.Is(err, io.EOF) || rsp == nil {
|
||||
// receive goroutine would close if unsubscribe is called.
|
||||
fmt.Println("dapr configuration subscribe finished.")
|
||||
close(stopCh)
|
||||
break
|
||||
|
|
|
|||
|
|
@ -70,7 +70,6 @@ func TestUnSubscribeConfigurationItems(t *testing.T) {
|
|||
counter := atomic.Int32{}
|
||||
totalCounter := atomic.Int32{}
|
||||
t.Run("Test unsubscribe configuration items", func(t *testing.T) {
|
||||
subscribeID := ""
|
||||
subscribeIDChan := make(chan string)
|
||||
go func() {
|
||||
keys := []string{"mykey1", "mykey2", "mykey3"}
|
||||
|
|
@ -88,7 +87,7 @@ func TestUnSubscribeConfigurationItems(t *testing.T) {
|
|||
})
|
||||
assert.Nil(t, err)
|
||||
}()
|
||||
subscribeID = <-subscribeIDChan
|
||||
subscribeID := <-subscribeIDChan
|
||||
time.Sleep(time.Second * 2)
|
||||
time.Sleep(time.Millisecond * 500)
|
||||
err := testClient.UnsubscribeConfigurationItems(ctx, "example-config", subscribeID)
|
||||
|
|
|
|||
|
|
@ -55,7 +55,7 @@ func TestInvokeErrors(t *testing.T) {
|
|||
}
|
||||
|
||||
func TestInvokeWithToken(t *testing.T) {
|
||||
_ = os.Setenv(cc.AppAPITokenEnvVar, "app-dapr-token")
|
||||
t.Setenv(cc.AppAPITokenEnvVar, "app-dapr-token")
|
||||
server := getTestServer()
|
||||
startTestServer(server)
|
||||
methodName := "test"
|
||||
|
|
|
|||
|
|
@ -49,6 +49,8 @@ func startTestServer(server *Server) {
|
|||
}
|
||||
|
||||
func stopTestServer(t *testing.T, server *Server) {
|
||||
t.Helper()
|
||||
|
||||
assert.NotNil(t, server)
|
||||
err := server.Stop()
|
||||
assert.Nilf(t, err, "error stopping server")
|
||||
|
|
|
|||
|
|
@ -39,7 +39,7 @@ func TestInvocationHandlerWithoutHandler(t *testing.T) {
|
|||
|
||||
func TestInvocationHandlerWithToken(t *testing.T) {
|
||||
data := `{"name": "test", "data": hello}`
|
||||
_ = os.Setenv(common.AppAPITokenEnvVar, "app-dapr-token")
|
||||
t.Setenv(common.AppAPITokenEnvVar, "app-dapr-token")
|
||||
s := newServer("", nil)
|
||||
err := s.AddServiceInvocationHandler("/hello", func(ctx context.Context, in *common.InvocationEvent) (out *common.Content, err error) {
|
||||
if in == nil || in.Data == nil || in.ContentType == "" {
|
||||
|
|
|
|||
|
|
@ -44,7 +44,7 @@ func newServer(address string, router *mux.Router) *Server {
|
|||
}
|
||||
return &Server{
|
||||
address: address,
|
||||
httpServer: &http.Server{
|
||||
httpServer: &http.Server{ //nolint:gosec
|
||||
Addr: address,
|
||||
Handler: router,
|
||||
},
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ limitations under the License.
|
|||
package http
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"io"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
|
|
@ -35,7 +36,7 @@ func TestStoppingStartedService(t *testing.T) {
|
|||
assert.NotNil(t, s)
|
||||
|
||||
go func() {
|
||||
if err := s.Start(); err != nil && err != http.ErrServerClosed {
|
||||
if err := s.Start(); err != nil && !errors.Is(err, http.ErrServerClosed) {
|
||||
panic(err)
|
||||
}
|
||||
}()
|
||||
|
|
@ -70,6 +71,8 @@ func TestSettingOptions(t *testing.T) {
|
|||
}
|
||||
|
||||
func testRequest(t *testing.T, s *Server, r *http.Request, expectedStatusCode int) {
|
||||
t.Helper()
|
||||
|
||||
rr := httptest.NewRecorder()
|
||||
s.mux.ServeHTTP(rr, r)
|
||||
resp := rr.Result()
|
||||
|
|
@ -79,6 +82,8 @@ func testRequest(t *testing.T, s *Server, r *http.Request, expectedStatusCode in
|
|||
}
|
||||
|
||||
func testRequestWithResponseBody(t *testing.T, s *Server, r *http.Request, expectedStatusCode int, expectedBody []byte) {
|
||||
t.Helper()
|
||||
|
||||
rr := httptest.NewRecorder()
|
||||
s.mux.ServeHTTP(rr, r)
|
||||
rez := rr.Result()
|
||||
|
|
|
|||
|
|
@ -334,18 +334,24 @@ func TestActorHandler(t *testing.T) {
|
|||
}
|
||||
|
||||
func makeRequest(t *testing.T, s *Server, route, data, method string, expectedStatusCode int) {
|
||||
t.Helper()
|
||||
|
||||
req, err := http.NewRequest(method, route, strings.NewReader(data))
|
||||
assert.NoErrorf(t, err, "error creating request: %s", data)
|
||||
testRequest(t, s, req, expectedStatusCode)
|
||||
}
|
||||
|
||||
func makeRequestWithExpectedBody(t *testing.T, s *Server, route, data, method string, expectedStatusCode int, expectedBody []byte) {
|
||||
t.Helper()
|
||||
|
||||
req, err := http.NewRequest(method, route, strings.NewReader(data))
|
||||
assert.NoErrorf(t, err, "error creating request: %s", data)
|
||||
testRequestWithResponseBody(t, s, req, expectedStatusCode, expectedBody)
|
||||
}
|
||||
|
||||
func makeEventRequest(t *testing.T, s *Server, route, data string, expectedStatusCode int) {
|
||||
t.Helper()
|
||||
|
||||
req, err := http.NewRequest(http.MethodPost, route, strings.NewReader(data))
|
||||
assert.NoErrorf(t, err, "error creating request: %s", data)
|
||||
req.Header.Set("Content-Type", "application/json")
|
||||
|
|
|
|||
|
|
@ -0,0 +1 @@
|
|||
v1.6.0
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
package version
|
||||
|
||||
import (
|
||||
// Required for go:embed.
|
||||
_ "embed"
|
||||
)
|
||||
|
||||
// SDKVersion contains the version of the SDK.
|
||||
//
|
||||
//go:embed sdk-version
|
||||
var SDKVersion string
|
||||
Loading…
Reference in New Issue