Skip to content

Commit 356eaf0

Browse files
committed
feat: add event dispatching example
1 parent a5e88a2 commit 356eaf0

12 files changed

+328
-0
lines changed
+29
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
# Copyright 2025 protobox
2+
#
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
version: '3'
16+
17+
tasks:
18+
proto:generate:
19+
run: once
20+
deps:
21+
cmds:
22+
- mkdir -p gen/proto
23+
- |
24+
protoc -I ./proto \
25+
--go_out=gen/proto \
26+
--go_opt=paths=source_relative \
27+
--go-protobox_out=gen/proto \
28+
--go-protobox_opt=paths=source_relative \
29+
$(find proto -name '*.proto')
+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
version: v2
2+
clean: true
3+
managed:
4+
enabled: true
5+
inputs:
6+
- directory: proto
7+
plugins:
8+
- remote: buf.build/protocolbuffers/go
9+
out: gen/proto
10+
opt: paths=source_relative
11+
include_imports: false
12+
- remote: buf.build/connectrpc/go
13+
out: gen/proto
14+
opt: paths=source_relative
15+
- local: protoc-gen-go-protobox
16+
out: gen/proto
17+
opt: paths=source_relative

examples/event-dispatching/buf.lock

+6
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
# Generated by buf. DO NOT EDIT.
2+
version: v2
3+
deps:
4+
- name: buf.build/notjustmoney/protobox
5+
commit: de039ccac0bf4759bbb7b02fb39191f7
6+
digest: b5:132f5a3d9d00ebe637c2951930b72c9a394510bea3f5e71a8e9a22d104b8e630cb0f853c63719d6edd86590ef042687ad1c9ad5dddf768335e5b5a4391737a88

examples/event-dispatching/buf.yaml

+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
# For details on buf.yaml configuration, visit https://buf.build/docs/configuration/v2/buf-yaml
2+
version: v2
3+
modules:
4+
- path: proto
5+
name: buf.build/notjustmoney/protobox-example-event-dispatching
6+
lint:
7+
use:
8+
- STANDARD
9+
breaking:
10+
use:
11+
- FILE
12+
deps:
13+
- buf.build/notjustmoney/protobox
+50
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
/*
2+
* Copyright (c) 2025. protobox
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package main
18+
19+
import (
20+
"context"
21+
"fmt"
22+
23+
"github.com/notjustmoney/protobox"
24+
exampleeventv1 "github.com/notjustmoney/protobox/examples/event-dispatching/gen/proto/event/example/v1"
25+
examplerpcv1 "github.com/notjustmoney/protobox/examples/event-dispatching/gen/proto/rpc/example/v1"
26+
"github.com/notjustmoney/protobox/examples/event-dispatching/internal/example"
27+
)
28+
29+
func main() {
30+
sendNotificationOnExampleCreatedHandler := example.NewSendNotificationOnExampleCreatedHandler()
31+
publishExampleCreatedOnExampleCreatedHandler := example.NewPublishExampleCreatedOnExampleCreatedHandler()
32+
33+
exampleDispatcher := exampleeventv1.NewSequentialEventDispatcher(
34+
exampleeventv1.WithExampleCreatedEventHandler(
35+
sendNotificationOnExampleCreatedHandler,
36+
publishExampleCreatedOnExampleCreatedHandler,
37+
),
38+
)
39+
examplePublisher := protobox.NewPublisher(exampleDispatcher)
40+
createExampleHandler := example.NewCreateExampleHandler(examplePublisher)
41+
resp, err := createExampleHandler.Handle(context.Background(), &examplerpcv1.CreateExampleRequest{
42+
Name: "example",
43+
Description: "example description",
44+
})
45+
if err != nil {
46+
fmt.Println("Error:", err)
47+
return
48+
}
49+
fmt.Println("Response:", resp)
50+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
/*
2+
* Copyright (c) 2025. protobox
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package example
18+
19+
import (
20+
"context"
21+
"fmt"
22+
23+
exampleeventv1 "github.com/notjustmoney/protobox/examples/event-dispatching/gen/proto/event/example/v1"
24+
)
25+
26+
type PublishExampleCreatedOnExampleCreatedHandler struct{}
27+
28+
func NewPublishExampleCreatedOnExampleCreatedHandler() *PublishExampleCreatedOnExampleCreatedHandler {
29+
return &PublishExampleCreatedOnExampleCreatedHandler{}
30+
}
31+
32+
func (h *PublishExampleCreatedOnExampleCreatedHandler) Handle(ctx context.Context, event *exampleeventv1.ExampleCreated) error {
33+
fmt.Println("PublishExampleCreatedOnExampleCreatedHandler: ", event)
34+
return nil
35+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
/*
2+
* Copyright (c) 2025. protobox
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package example
18+
19+
import (
20+
"context"
21+
"time"
22+
23+
"github.com/google/uuid"
24+
"google.golang.org/protobuf/types/known/timestamppb"
25+
26+
"github.com/notjustmoney/protobox"
27+
exampleeventv1 "github.com/notjustmoney/protobox/examples/event-dispatching/gen/proto/event/example/v1"
28+
examplerpcv1 "github.com/notjustmoney/protobox/examples/event-dispatching/gen/proto/rpc/example/v1"
29+
)
30+
31+
type CreateExampleHandler struct {
32+
publisher protobox.Publisher
33+
}
34+
35+
func NewCreateExampleHandler(
36+
publisher protobox.Publisher,
37+
) *CreateExampleHandler {
38+
return &CreateExampleHandler{
39+
publisher: publisher,
40+
}
41+
}
42+
43+
func (h *CreateExampleHandler) Handle(ctx context.Context, req *examplerpcv1.CreateExampleRequest) (*examplerpcv1.CreateExampleResponse, error) {
44+
id := uuid.NewString()
45+
now := time.Now()
46+
if err := h.publisher.Publish(ctx, &exampleeventv1.ExampleCreated{
47+
Id: id,
48+
Name: req.Name,
49+
Description: req.Description,
50+
CreatedAt: timestamppb.New(now),
51+
}); err != nil {
52+
return nil, err
53+
}
54+
return &examplerpcv1.CreateExampleResponse{
55+
Id: id,
56+
Name: req.Name,
57+
Description: req.Description,
58+
CreatedAt: timestamppb.New(now),
59+
}, nil
60+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
/*
2+
* Copyright (c) 2025. protobox
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package example
18+
19+
import (
20+
"context"
21+
"fmt"
22+
23+
exampleeventv1 "github.com/notjustmoney/protobox/examples/event-dispatching/gen/proto/event/example/v1"
24+
)
25+
26+
type SendNotificationOnExampleCreatedHandler struct {
27+
}
28+
29+
func NewSendNotificationOnExampleCreatedHandler() *SendNotificationOnExampleCreatedHandler {
30+
return &SendNotificationOnExampleCreatedHandler{}
31+
}
32+
33+
func (h *SendNotificationOnExampleCreatedHandler) Handle(ctx context.Context, event *exampleeventv1.ExampleCreated) error {
34+
fmt.Println("SendNotificationOnExampleCreatedHandler: ", event)
35+
return nil
36+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
syntax = "proto3";
2+
3+
package event.example.v1;
4+
5+
option go_package = "github.com/notjustmoney/event-dispatching/examples/event-dispatching/proto/event/example/v1;exampleeventv1";
6+
7+
import "google/protobuf/timestamp.proto";
8+
import "protobox/options.proto";
9+
10+
message EventDispatcher {
11+
option(protobox.dispatcher) = {
12+
sequential: true
13+
parallel: false
14+
};
15+
}
16+
17+
message ExampleCreated {
18+
option(protobox.event) = {
19+
topic: "protobox.example.created"
20+
version: "v1"
21+
};
22+
23+
string id = 1;
24+
string name = 2;
25+
string description = 3;
26+
google.protobuf.Timestamp created_at = 4;
27+
}
28+
29+
message ExampleDeleted {
30+
option(protobox.event) = {
31+
topic: "protobox.example.deleted"
32+
version: "v1"
33+
};
34+
35+
string id = 1;
36+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
syntax = "proto3";
2+
3+
package rpc.example.v1;
4+
5+
option go_package = "github.com/notjustmoney/event-dispatching/examples/event-dispatching/proto/rpc/example/v1;examplerpcv1";
6+
7+
import "google/protobuf/timestamp.proto";
8+
9+
message CreateExampleRequest {
10+
string name = 1;
11+
string description = 2;
12+
}
13+
14+
message CreateExampleResponse {
15+
string id = 1;
16+
string name = 2;
17+
string description = 3;
18+
google.protobuf.Timestamp created_at = 4;
19+
}

examples/go.mod

+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
module github.com/notjustmoney/protobox/examples
2+
3+
go 1.23.4
4+
5+
require google.golang.org/protobuf v1.36.3
6+
7+
require github.com/google/uuid v1.6.0
8+
9+
require (
10+
golang.org/x/mod v0.22.0 // indirect
11+
golang.org/x/sync v0.10.0 // indirect
12+
golang.org/x/tools v0.29.0 // indirect
13+
)

examples/go.sum

+14
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU=
2+
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
3+
github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0=
4+
github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
5+
golang.org/x/mod v0.22.0 h1:D4nJWe9zXqHOmWqj4VMOJhvzj7bEZg4wEYa759z1pH4=
6+
golang.org/x/mod v0.22.0/go.mod h1:6SkKJ3Xj0I0BrPOZoBy3bdMptDDU9oJrpohJ3eWZ1fY=
7+
golang.org/x/sync v0.10.0 h1:3NQrjDixjgGwUOCaF8w2+VYHv0Ve/vGYSbdkTa98gmQ=
8+
golang.org/x/sync v0.10.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
9+
golang.org/x/tools v0.29.0 h1:Xx0h3TtM9rzQpQuR4dKLrdglAmCEN5Oi+P74JdhdzXE=
10+
golang.org/x/tools v0.29.0/go.mod h1:KMQVMRsVxU6nHCFXrBPhDB8XncLNLM0lIy/F14RP588=
11+
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4=
12+
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
13+
google.golang.org/protobuf v1.36.3 h1:82DV7MYdb8anAVi3qge1wSnMDrnKK7ebr+I0hHRN1BU=
14+
google.golang.org/protobuf v1.36.3/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE=

0 commit comments

Comments
 (0)