Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Sign in
Toggle navigation
D
distributed-calculator
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
tammam.alsoleman
distributed-calculator
Commits
94587262
Commit
94587262
authored
Nov 11, 2025
by
tammam.alsoleman
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
create addition service using go
parent
0c540ce5
Changes
5
Show whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
690 additions
and
0 deletions
+690
-0
calculator.pb.go
addition-service/generated/generated/calculator.pb.go
+380
-0
calculator_grpc.pb.go
addition-service/generated/generated/calculator_grpc.pb.go
+201
-0
go.mod
addition-service/go.mod
+8
-0
main.go
addition-service/main.go
+99
-0
calculator.proto
proto/calculator.proto
+2
-0
No files found.
addition-service/generated/generated/calculator.pb.go
0 → 100644
View file @
94587262
// Code generated by protoc-gen-go. DO NOT EDIT.
// versions:
// protoc-gen-go v1.36.10
// protoc v6.33.0
// source: calculator.proto
package
generated
import
(
protoreflect
"google.golang.org/protobuf/reflect/protoreflect"
protoimpl
"google.golang.org/protobuf/runtime/protoimpl"
reflect
"reflect"
sync
"sync"
unsafe
"unsafe"
)
const
(
// Verify that this generated code is sufficiently up-to-date.
_
=
protoimpl
.
EnforceVersion
(
20
-
protoimpl
.
MinVersion
)
// Verify that runtime/protoimpl is sufficiently up-to-date.
_
=
protoimpl
.
EnforceVersion
(
protoimpl
.
MaxVersion
-
20
)
)
type
Numbers
struct
{
state
protoimpl
.
MessageState
`protogen:"open.v1"`
A
int32
`protobuf:"varint,1,opt,name=a,proto3" json:"a,omitempty"`
B
int32
`protobuf:"varint,2,opt,name=b,proto3" json:"b,omitempty"`
unknownFields
protoimpl
.
UnknownFields
sizeCache
protoimpl
.
SizeCache
}
func
(
x
*
Numbers
)
Reset
()
{
*
x
=
Numbers
{}
mi
:=
&
file_calculator_proto_msgTypes
[
0
]
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
ms
.
StoreMessageInfo
(
mi
)
}
func
(
x
*
Numbers
)
String
()
string
{
return
protoimpl
.
X
.
MessageStringOf
(
x
)
}
func
(
*
Numbers
)
ProtoMessage
()
{}
func
(
x
*
Numbers
)
ProtoReflect
()
protoreflect
.
Message
{
mi
:=
&
file_calculator_proto_msgTypes
[
0
]
if
x
!=
nil
{
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
if
ms
.
LoadMessageInfo
()
==
nil
{
ms
.
StoreMessageInfo
(
mi
)
}
return
ms
}
return
mi
.
MessageOf
(
x
)
}
// Deprecated: Use Numbers.ProtoReflect.Descriptor instead.
func
(
*
Numbers
)
Descriptor
()
([]
byte
,
[]
int
)
{
return
file_calculator_proto_rawDescGZIP
(),
[]
int
{
0
}
}
func
(
x
*
Numbers
)
GetA
()
int32
{
if
x
!=
nil
{
return
x
.
A
}
return
0
}
func
(
x
*
Numbers
)
GetB
()
int32
{
if
x
!=
nil
{
return
x
.
B
}
return
0
}
type
Result
struct
{
state
protoimpl
.
MessageState
`protogen:"open.v1"`
Value
int32
`protobuf:"varint,1,opt,name=value,proto3" json:"value,omitempty"`
Operation
string
`protobuf:"bytes,2,opt,name=operation,proto3" json:"operation,omitempty"`
unknownFields
protoimpl
.
UnknownFields
sizeCache
protoimpl
.
SizeCache
}
func
(
x
*
Result
)
Reset
()
{
*
x
=
Result
{}
mi
:=
&
file_calculator_proto_msgTypes
[
1
]
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
ms
.
StoreMessageInfo
(
mi
)
}
func
(
x
*
Result
)
String
()
string
{
return
protoimpl
.
X
.
MessageStringOf
(
x
)
}
func
(
*
Result
)
ProtoMessage
()
{}
func
(
x
*
Result
)
ProtoReflect
()
protoreflect
.
Message
{
mi
:=
&
file_calculator_proto_msgTypes
[
1
]
if
x
!=
nil
{
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
if
ms
.
LoadMessageInfo
()
==
nil
{
ms
.
StoreMessageInfo
(
mi
)
}
return
ms
}
return
mi
.
MessageOf
(
x
)
}
// Deprecated: Use Result.ProtoReflect.Descriptor instead.
func
(
*
Result
)
Descriptor
()
([]
byte
,
[]
int
)
{
return
file_calculator_proto_rawDescGZIP
(),
[]
int
{
1
}
}
func
(
x
*
Result
)
GetValue
()
int32
{
if
x
!=
nil
{
return
x
.
Value
}
return
0
}
func
(
x
*
Result
)
GetOperation
()
string
{
if
x
!=
nil
{
return
x
.
Operation
}
return
""
}
type
OperationHistory
struct
{
state
protoimpl
.
MessageState
`protogen:"open.v1"`
ServiceName
string
`protobuf:"bytes,1,opt,name=service_name,json=serviceName,proto3" json:"service_name,omitempty"`
Operations
[]
*
Operation
`protobuf:"bytes,2,rep,name=operations,proto3" json:"operations,omitempty"`
unknownFields
protoimpl
.
UnknownFields
sizeCache
protoimpl
.
SizeCache
}
func
(
x
*
OperationHistory
)
Reset
()
{
*
x
=
OperationHistory
{}
mi
:=
&
file_calculator_proto_msgTypes
[
2
]
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
ms
.
StoreMessageInfo
(
mi
)
}
func
(
x
*
OperationHistory
)
String
()
string
{
return
protoimpl
.
X
.
MessageStringOf
(
x
)
}
func
(
*
OperationHistory
)
ProtoMessage
()
{}
func
(
x
*
OperationHistory
)
ProtoReflect
()
protoreflect
.
Message
{
mi
:=
&
file_calculator_proto_msgTypes
[
2
]
if
x
!=
nil
{
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
if
ms
.
LoadMessageInfo
()
==
nil
{
ms
.
StoreMessageInfo
(
mi
)
}
return
ms
}
return
mi
.
MessageOf
(
x
)
}
// Deprecated: Use OperationHistory.ProtoReflect.Descriptor instead.
func
(
*
OperationHistory
)
Descriptor
()
([]
byte
,
[]
int
)
{
return
file_calculator_proto_rawDescGZIP
(),
[]
int
{
2
}
}
func
(
x
*
OperationHistory
)
GetServiceName
()
string
{
if
x
!=
nil
{
return
x
.
ServiceName
}
return
""
}
func
(
x
*
OperationHistory
)
GetOperations
()
[]
*
Operation
{
if
x
!=
nil
{
return
x
.
Operations
}
return
nil
}
type
Operation
struct
{
state
protoimpl
.
MessageState
`protogen:"open.v1"`
Type
string
`protobuf:"bytes,1,opt,name=type,proto3" json:"type,omitempty"`
A
int32
`protobuf:"varint,2,opt,name=a,proto3" json:"a,omitempty"`
B
int32
`protobuf:"varint,3,opt,name=b,proto3" json:"b,omitempty"`
Result
int32
`protobuf:"varint,4,opt,name=result,proto3" json:"result,omitempty"`
Timestamp
string
`protobuf:"bytes,5,opt,name=timestamp,proto3" json:"timestamp,omitempty"`
unknownFields
protoimpl
.
UnknownFields
sizeCache
protoimpl
.
SizeCache
}
func
(
x
*
Operation
)
Reset
()
{
*
x
=
Operation
{}
mi
:=
&
file_calculator_proto_msgTypes
[
3
]
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
ms
.
StoreMessageInfo
(
mi
)
}
func
(
x
*
Operation
)
String
()
string
{
return
protoimpl
.
X
.
MessageStringOf
(
x
)
}
func
(
*
Operation
)
ProtoMessage
()
{}
func
(
x
*
Operation
)
ProtoReflect
()
protoreflect
.
Message
{
mi
:=
&
file_calculator_proto_msgTypes
[
3
]
if
x
!=
nil
{
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
if
ms
.
LoadMessageInfo
()
==
nil
{
ms
.
StoreMessageInfo
(
mi
)
}
return
ms
}
return
mi
.
MessageOf
(
x
)
}
// Deprecated: Use Operation.ProtoReflect.Descriptor instead.
func
(
*
Operation
)
Descriptor
()
([]
byte
,
[]
int
)
{
return
file_calculator_proto_rawDescGZIP
(),
[]
int
{
3
}
}
func
(
x
*
Operation
)
GetType
()
string
{
if
x
!=
nil
{
return
x
.
Type
}
return
""
}
func
(
x
*
Operation
)
GetA
()
int32
{
if
x
!=
nil
{
return
x
.
A
}
return
0
}
func
(
x
*
Operation
)
GetB
()
int32
{
if
x
!=
nil
{
return
x
.
B
}
return
0
}
func
(
x
*
Operation
)
GetResult
()
int32
{
if
x
!=
nil
{
return
x
.
Result
}
return
0
}
func
(
x
*
Operation
)
GetTimestamp
()
string
{
if
x
!=
nil
{
return
x
.
Timestamp
}
return
""
}
type
Empty
struct
{
state
protoimpl
.
MessageState
`protogen:"open.v1"`
unknownFields
protoimpl
.
UnknownFields
sizeCache
protoimpl
.
SizeCache
}
func
(
x
*
Empty
)
Reset
()
{
*
x
=
Empty
{}
mi
:=
&
file_calculator_proto_msgTypes
[
4
]
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
ms
.
StoreMessageInfo
(
mi
)
}
func
(
x
*
Empty
)
String
()
string
{
return
protoimpl
.
X
.
MessageStringOf
(
x
)
}
func
(
*
Empty
)
ProtoMessage
()
{}
func
(
x
*
Empty
)
ProtoReflect
()
protoreflect
.
Message
{
mi
:=
&
file_calculator_proto_msgTypes
[
4
]
if
x
!=
nil
{
ms
:=
protoimpl
.
X
.
MessageStateOf
(
protoimpl
.
Pointer
(
x
))
if
ms
.
LoadMessageInfo
()
==
nil
{
ms
.
StoreMessageInfo
(
mi
)
}
return
ms
}
return
mi
.
MessageOf
(
x
)
}
// Deprecated: Use Empty.ProtoReflect.Descriptor instead.
func
(
*
Empty
)
Descriptor
()
([]
byte
,
[]
int
)
{
return
file_calculator_proto_rawDescGZIP
(),
[]
int
{
4
}
}
var
File_calculator_proto
protoreflect
.
FileDescriptor
const
file_calculator_proto_rawDesc
=
""
+
"
\n
"
+
"
\x10
calculator.proto
\x12\n
"
+
"calculator
\"
%
\n
"
+
"
\a
Numbers
\x12\f\n
"
+
"
\x01
a
\x18\x01
\x01
(
\x05
R
\x01
a
\x12\f\n
"
+
"
\x01
b
\x18\x02
\x01
(
\x05
R
\x01
b
\"
<
\n
"
+
"
\x06
Result
\x12\x14\n
"
+
"
\x05
value
\x18\x01
\x01
(
\x05
R
\x05
value
\x12\x1c\n
"
+
"
\t
operation
\x18\x02
\x01
(
\t
R
\t
operation
\"
l
\n
"
+
"
\x10
OperationHistory
\x12
!
\n
"
+
"
\f
service_name
\x18\x01
\x01
(
\t
R
\v
serviceName
\x12
5
\n
"
+
"
\n
"
+
"operations
\x18\x02
\x03
(
\v
2
\x15
.calculator.OperationR
\n
"
+
"operations
\"
q
\n
"
+
"
\t
Operation
\x12\x12\n
"
+
"
\x04
type
\x18\x01
\x01
(
\t
R
\x04
type
\x12\f\n
"
+
"
\x01
a
\x18\x02
\x01
(
\x05
R
\x01
a
\x12\f\n
"
+
"
\x01
b
\x18\x03
\x01
(
\x05
R
\x01
b
\x12\x16\n
"
+
"
\x06
result
\x18\x04
\x01
(
\x05
R
\x06
result
\x12\x1c\n
"
+
"
\t
timestamp
\x18\x05
\x01
(
\t
R
\t
timestamp
\"\a\n
"
+
"
\x05
Empty2
\xbb\x01\n
"
+
"
\n
"
+
"Calculator
\x12
.
\n
"
+
"
\x03
Add
\x12\x13
.calculator.Numbers
\x1a\x12
.calculator.Result
\x12
3
\n
"
+
"
\b
Multiply
\x12\x13
.calculator.Numbers
\x1a\x12
.calculator.Result
\x12
H
\n
"
+
"
\x13
GetOperationHistory
\x12\x11
.calculator.Empty
\x1a\x1c
.calculator.OperationHistory0
\x01
B8
\n
"
+
"'com.calculator.multiplication.generatedP
\x01
Z
\v
./generatedb
\x06
proto3"
var
(
file_calculator_proto_rawDescOnce
sync
.
Once
file_calculator_proto_rawDescData
[]
byte
)
func
file_calculator_proto_rawDescGZIP
()
[]
byte
{
file_calculator_proto_rawDescOnce
.
Do
(
func
()
{
file_calculator_proto_rawDescData
=
protoimpl
.
X
.
CompressGZIP
(
unsafe
.
Slice
(
unsafe
.
StringData
(
file_calculator_proto_rawDesc
),
len
(
file_calculator_proto_rawDesc
)))
})
return
file_calculator_proto_rawDescData
}
var
file_calculator_proto_msgTypes
=
make
([]
protoimpl
.
MessageInfo
,
5
)
var
file_calculator_proto_goTypes
=
[]
any
{
(
*
Numbers
)(
nil
),
// 0: calculator.Numbers
(
*
Result
)(
nil
),
// 1: calculator.Result
(
*
OperationHistory
)(
nil
),
// 2: calculator.OperationHistory
(
*
Operation
)(
nil
),
// 3: calculator.Operation
(
*
Empty
)(
nil
),
// 4: calculator.Empty
}
var
file_calculator_proto_depIdxs
=
[]
int32
{
3
,
// 0: calculator.OperationHistory.operations:type_name -> calculator.Operation
0
,
// 1: calculator.Calculator.Add:input_type -> calculator.Numbers
0
,
// 2: calculator.Calculator.Multiply:input_type -> calculator.Numbers
4
,
// 3: calculator.Calculator.GetOperationHistory:input_type -> calculator.Empty
1
,
// 4: calculator.Calculator.Add:output_type -> calculator.Result
1
,
// 5: calculator.Calculator.Multiply:output_type -> calculator.Result
2
,
// 6: calculator.Calculator.GetOperationHistory:output_type -> calculator.OperationHistory
4
,
// [4:7] is the sub-list for method output_type
1
,
// [1:4] is the sub-list for method input_type
1
,
// [1:1] is the sub-list for extension type_name
1
,
// [1:1] is the sub-list for extension extendee
0
,
// [0:1] is the sub-list for field type_name
}
func
init
()
{
file_calculator_proto_init
()
}
func
file_calculator_proto_init
()
{
if
File_calculator_proto
!=
nil
{
return
}
type
x
struct
{}
out
:=
protoimpl
.
TypeBuilder
{
File
:
protoimpl
.
DescBuilder
{
GoPackagePath
:
reflect
.
TypeOf
(
x
{})
.
PkgPath
(),
RawDescriptor
:
unsafe
.
Slice
(
unsafe
.
StringData
(
file_calculator_proto_rawDesc
),
len
(
file_calculator_proto_rawDesc
)),
NumEnums
:
0
,
NumMessages
:
5
,
NumExtensions
:
0
,
NumServices
:
1
,
},
GoTypes
:
file_calculator_proto_goTypes
,
DependencyIndexes
:
file_calculator_proto_depIdxs
,
MessageInfos
:
file_calculator_proto_msgTypes
,
}
.
Build
()
File_calculator_proto
=
out
.
File
file_calculator_proto_goTypes
=
nil
file_calculator_proto_depIdxs
=
nil
}
addition-service/generated/generated/calculator_grpc.pb.go
0 → 100644
View file @
94587262
// Code generated by protoc-gen-go-grpc. DO NOT EDIT.
// versions:
// - protoc-gen-go-grpc v1.5.1
// - protoc v6.33.0
// source: calculator.proto
package
generated
import
(
context
"context"
grpc
"google.golang.org/grpc"
codes
"google.golang.org/grpc/codes"
status
"google.golang.org/grpc/status"
)
// This is a compile-time assertion to ensure that this generated file
// is compatible with the grpc package it is being compiled against.
// Requires gRPC-Go v1.64.0 or later.
const
_
=
grpc
.
SupportPackageIsVersion9
const
(
Calculator_Add_FullMethodName
=
"/calculator.Calculator/Add"
Calculator_Multiply_FullMethodName
=
"/calculator.Calculator/Multiply"
Calculator_GetOperationHistory_FullMethodName
=
"/calculator.Calculator/GetOperationHistory"
)
// CalculatorClient is the client API for Calculator service.
//
// For semantics around ctx use and closing/ending streaming RPCs, please refer to https://pkg.go.dev/google.golang.org/grpc/?tab=doc#ClientConn.NewStream.
type
CalculatorClient
interface
{
Add
(
ctx
context
.
Context
,
in
*
Numbers
,
opts
...
grpc
.
CallOption
)
(
*
Result
,
error
)
Multiply
(
ctx
context
.
Context
,
in
*
Numbers
,
opts
...
grpc
.
CallOption
)
(
*
Result
,
error
)
GetOperationHistory
(
ctx
context
.
Context
,
in
*
Empty
,
opts
...
grpc
.
CallOption
)
(
grpc
.
ServerStreamingClient
[
OperationHistory
],
error
)
}
type
calculatorClient
struct
{
cc
grpc
.
ClientConnInterface
}
func
NewCalculatorClient
(
cc
grpc
.
ClientConnInterface
)
CalculatorClient
{
return
&
calculatorClient
{
cc
}
}
func
(
c
*
calculatorClient
)
Add
(
ctx
context
.
Context
,
in
*
Numbers
,
opts
...
grpc
.
CallOption
)
(
*
Result
,
error
)
{
cOpts
:=
append
([]
grpc
.
CallOption
{
grpc
.
StaticMethod
()},
opts
...
)
out
:=
new
(
Result
)
err
:=
c
.
cc
.
Invoke
(
ctx
,
Calculator_Add_FullMethodName
,
in
,
out
,
cOpts
...
)
if
err
!=
nil
{
return
nil
,
err
}
return
out
,
nil
}
func
(
c
*
calculatorClient
)
Multiply
(
ctx
context
.
Context
,
in
*
Numbers
,
opts
...
grpc
.
CallOption
)
(
*
Result
,
error
)
{
cOpts
:=
append
([]
grpc
.
CallOption
{
grpc
.
StaticMethod
()},
opts
...
)
out
:=
new
(
Result
)
err
:=
c
.
cc
.
Invoke
(
ctx
,
Calculator_Multiply_FullMethodName
,
in
,
out
,
cOpts
...
)
if
err
!=
nil
{
return
nil
,
err
}
return
out
,
nil
}
func
(
c
*
calculatorClient
)
GetOperationHistory
(
ctx
context
.
Context
,
in
*
Empty
,
opts
...
grpc
.
CallOption
)
(
grpc
.
ServerStreamingClient
[
OperationHistory
],
error
)
{
cOpts
:=
append
([]
grpc
.
CallOption
{
grpc
.
StaticMethod
()},
opts
...
)
stream
,
err
:=
c
.
cc
.
NewStream
(
ctx
,
&
Calculator_ServiceDesc
.
Streams
[
0
],
Calculator_GetOperationHistory_FullMethodName
,
cOpts
...
)
if
err
!=
nil
{
return
nil
,
err
}
x
:=
&
grpc
.
GenericClientStream
[
Empty
,
OperationHistory
]{
ClientStream
:
stream
}
if
err
:=
x
.
ClientStream
.
SendMsg
(
in
);
err
!=
nil
{
return
nil
,
err
}
if
err
:=
x
.
ClientStream
.
CloseSend
();
err
!=
nil
{
return
nil
,
err
}
return
x
,
nil
}
// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name.
type
Calculator_GetOperationHistoryClient
=
grpc
.
ServerStreamingClient
[
OperationHistory
]
// CalculatorServer is the server API for Calculator service.
// All implementations must embed UnimplementedCalculatorServer
// for forward compatibility.
type
CalculatorServer
interface
{
Add
(
context
.
Context
,
*
Numbers
)
(
*
Result
,
error
)
Multiply
(
context
.
Context
,
*
Numbers
)
(
*
Result
,
error
)
GetOperationHistory
(
*
Empty
,
grpc
.
ServerStreamingServer
[
OperationHistory
])
error
mustEmbedUnimplementedCalculatorServer
()
}
// UnimplementedCalculatorServer must be embedded to have
// forward compatible implementations.
//
// NOTE: this should be embedded by value instead of pointer to avoid a nil
// pointer dereference when methods are called.
type
UnimplementedCalculatorServer
struct
{}
func
(
UnimplementedCalculatorServer
)
Add
(
context
.
Context
,
*
Numbers
)
(
*
Result
,
error
)
{
return
nil
,
status
.
Errorf
(
codes
.
Unimplemented
,
"method Add not implemented"
)
}
func
(
UnimplementedCalculatorServer
)
Multiply
(
context
.
Context
,
*
Numbers
)
(
*
Result
,
error
)
{
return
nil
,
status
.
Errorf
(
codes
.
Unimplemented
,
"method Multiply not implemented"
)
}
func
(
UnimplementedCalculatorServer
)
GetOperationHistory
(
*
Empty
,
grpc
.
ServerStreamingServer
[
OperationHistory
])
error
{
return
status
.
Errorf
(
codes
.
Unimplemented
,
"method GetOperationHistory not implemented"
)
}
func
(
UnimplementedCalculatorServer
)
mustEmbedUnimplementedCalculatorServer
()
{}
func
(
UnimplementedCalculatorServer
)
testEmbeddedByValue
()
{}
// UnsafeCalculatorServer may be embedded to opt out of forward compatibility for this service.
// Use of this interface is not recommended, as added methods to CalculatorServer will
// result in compilation errors.
type
UnsafeCalculatorServer
interface
{
mustEmbedUnimplementedCalculatorServer
()
}
func
RegisterCalculatorServer
(
s
grpc
.
ServiceRegistrar
,
srv
CalculatorServer
)
{
// If the following call pancis, it indicates UnimplementedCalculatorServer was
// embedded by pointer and is nil. This will cause panics if an
// unimplemented method is ever invoked, so we test this at initialization
// time to prevent it from happening at runtime later due to I/O.
if
t
,
ok
:=
srv
.
(
interface
{
testEmbeddedByValue
()
});
ok
{
t
.
testEmbeddedByValue
()
}
s
.
RegisterService
(
&
Calculator_ServiceDesc
,
srv
)
}
func
_Calculator_Add_Handler
(
srv
interface
{},
ctx
context
.
Context
,
dec
func
(
interface
{})
error
,
interceptor
grpc
.
UnaryServerInterceptor
)
(
interface
{},
error
)
{
in
:=
new
(
Numbers
)
if
err
:=
dec
(
in
);
err
!=
nil
{
return
nil
,
err
}
if
interceptor
==
nil
{
return
srv
.
(
CalculatorServer
)
.
Add
(
ctx
,
in
)
}
info
:=
&
grpc
.
UnaryServerInfo
{
Server
:
srv
,
FullMethod
:
Calculator_Add_FullMethodName
,
}
handler
:=
func
(
ctx
context
.
Context
,
req
interface
{})
(
interface
{},
error
)
{
return
srv
.
(
CalculatorServer
)
.
Add
(
ctx
,
req
.
(
*
Numbers
))
}
return
interceptor
(
ctx
,
in
,
info
,
handler
)
}
func
_Calculator_Multiply_Handler
(
srv
interface
{},
ctx
context
.
Context
,
dec
func
(
interface
{})
error
,
interceptor
grpc
.
UnaryServerInterceptor
)
(
interface
{},
error
)
{
in
:=
new
(
Numbers
)
if
err
:=
dec
(
in
);
err
!=
nil
{
return
nil
,
err
}
if
interceptor
==
nil
{
return
srv
.
(
CalculatorServer
)
.
Multiply
(
ctx
,
in
)
}
info
:=
&
grpc
.
UnaryServerInfo
{
Server
:
srv
,
FullMethod
:
Calculator_Multiply_FullMethodName
,
}
handler
:=
func
(
ctx
context
.
Context
,
req
interface
{})
(
interface
{},
error
)
{
return
srv
.
(
CalculatorServer
)
.
Multiply
(
ctx
,
req
.
(
*
Numbers
))
}
return
interceptor
(
ctx
,
in
,
info
,
handler
)
}
func
_Calculator_GetOperationHistory_Handler
(
srv
interface
{},
stream
grpc
.
ServerStream
)
error
{
m
:=
new
(
Empty
)
if
err
:=
stream
.
RecvMsg
(
m
);
err
!=
nil
{
return
err
}
return
srv
.
(
CalculatorServer
)
.
GetOperationHistory
(
m
,
&
grpc
.
GenericServerStream
[
Empty
,
OperationHistory
]{
ServerStream
:
stream
})
}
// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name.
type
Calculator_GetOperationHistoryServer
=
grpc
.
ServerStreamingServer
[
OperationHistory
]
// Calculator_ServiceDesc is the grpc.ServiceDesc for Calculator service.
// It's only intended for direct use with grpc.RegisterService,
// and not to be introspected or modified (even as a copy)
var
Calculator_ServiceDesc
=
grpc
.
ServiceDesc
{
ServiceName
:
"calculator.Calculator"
,
HandlerType
:
(
*
CalculatorServer
)(
nil
),
Methods
:
[]
grpc
.
MethodDesc
{
{
MethodName
:
"Add"
,
Handler
:
_Calculator_Add_Handler
,
},
{
MethodName
:
"Multiply"
,
Handler
:
_Calculator_Multiply_Handler
,
},
},
Streams
:
[]
grpc
.
StreamDesc
{
{
StreamName
:
"GetOperationHistory"
,
Handler
:
_Calculator_GetOperationHistory_Handler
,
ServerStreams
:
true
,
},
},
Metadata
:
"calculator.proto"
,
}
addition-service/go.mod
0 → 100644
View file @
94587262
module addition-service
go 1.21
require (
google.golang.org/grpc v1.59.0
google.golang.org/protobuf v1.31.0
)
\ No newline at end of file
addition-service/main.go
0 → 100644
View file @
94587262
package
main
import
(
"context"
"fmt"
"log"
"net"
"os"
"sync"
"time"
"addition-service/generated"
"google.golang.org/grpc"
)
type
additionServer
struct
{
generated
.
UnimplementedCalculatorServer
operations
[]
*
generated
.
Operation
mutex
sync
.
RWMutex
}
func
(
s
*
additionServer
)
Add
(
ctx
context
.
Context
,
req
*
generated
.
Numbers
)
(
*
generated
.
Result
,
error
)
{
result
:=
req
.
A
+
req
.
B
op
:=
&
generated
.
Operation
{
Type
:
"ADDITION"
,
A
:
req
.
A
,
B
:
req
.
B
,
Result
:
result
,
Timestamp
:
time
.
Now
()
.
Format
(
"2006-01-02 15:04:05"
),
}
s
.
mutex
.
Lock
()
s
.
operations
=
append
(
s
.
operations
,
op
)
s
.
mutex
.
Unlock
()
go
s
.
logToFile
(
op
)
fmt
.
Printf
(
" Addition operation: %d + %d = %d
\n
"
,
req
.
A
,
req
.
B
,
result
)
return
&
generated
.
Result
{
Value
:
result
,
Operation
:
"ADDITION"
,
},
nil
}
func
(
s
*
additionServer
)
GetOperationHistory
(
req
*
generated
.
Empty
,
stream
generated
.
Calculator_GetOperationHistoryServer
)
error
{
s
.
mutex
.
RLock
()
defer
s
.
mutex
.
RUnlock
()
history
:=
&
generated
.
OperationHistory
{
ServiceName
:
"Addition Service"
,
Operations
:
s
.
operations
,
}
if
err
:=
stream
.
Send
(
history
);
err
!=
nil
{
return
err
}
return
nil
}
func
(
s
*
additionServer
)
logToFile
(
op
*
generated
.
Operation
)
{
file
,
err
:=
os
.
OpenFile
(
"operation_log.txt"
,
os
.
O_APPEND
|
os
.
O_CREATE
|
os
.
O_WRONLY
,
0644
)
if
err
!=
nil
{
log
.
Printf
(
"Failed to open log file: %v"
,
err
)
return
}
defer
file
.
Close
()
logEntry
:=
fmt
.
Sprintf
(
"[%s] %s: %d + %d = %d
\n
"
,
op
.
Timestamp
,
op
.
Type
,
op
.
A
,
op
.
B
,
op
.
Result
)
if
_
,
err
:=
file
.
WriteString
(
logEntry
);
err
!=
nil
{
log
.
Printf
(
"Failed to write to log file: %v"
,
err
)
}
}
func
main
()
{
lis
,
err
:=
net
.
Listen
(
"tcp"
,
":50052"
)
if
err
!=
nil
{
log
.
Fatalf
(
"Failed to listen: %v"
,
err
)
}
server
:=
grpc
.
NewServer
()
additionServer
:=
&
additionServer
{
operations
:
make
([]
*
generated
.
Operation
,
0
),
}
generated
.
RegisterCalculatorServer
(
server
,
additionServer
)
fmt
.
Println
(
" Addition Service running on port 50052"
)
fmt
.
Println
(
" Ready to receive addition requests..."
)
if
err
:=
server
.
Serve
(
lis
);
err
!=
nil
{
log
.
Fatalf
(
"Failed to serve: %v"
,
err
)
}
}
\ No newline at end of file
proto/calculator.proto
View file @
94587262
...
@@ -2,6 +2,8 @@ syntax = "proto3";
...
@@ -2,6 +2,8 @@ syntax = "proto3";
package
calculator
;
package
calculator
;
option
go_package
=
"./generated"
;
option
java_package
=
"com.calculator.multiplication.generated"
;
option
java_package
=
"com.calculator.multiplication.generated"
;
option
java_multiple_files
=
true
;
option
java_multiple_files
=
true
;
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment