[ 
https://issues.apache.org/jira/browse/THRIFT-5803?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
 ]

Sylwester Lachiewicz resolved THRIFT-5803.
------------------------------------------
    Resolution: Not A Bug

Per the Thrift IDL specification (doc/specs/idl.md):
{quote}
*required*
- Write: Required fields are always written
- Read: Required fields are always read and are expected to be contained in the 
input stream.
- Defaults values: are always written

If a required field is missing during read, the expected behaviour is to 
indicate an unsuccessful read operation to the caller, e.g. by throwing an 
exception or returning an error.
{quote}

Write validation and initialization behavior across language implementations:
- In Go and C++, required scalar fields are stored as direct values (not 
pointers/nullable references) and carry the language default/zero-value (e.g. 
empty string ""). When written, both Go and C++ always serialize the field to 
the wire, satisfying the IDL requirement that "Required fields are always 
written" and allowing peer deserializers to succeed.
- In Rust, required fields must be supplied to the constructor 
(StructRequired::new(f_1: String)), preventing uninitialized required fields at 
compile time.
- In Java, struct.validate() is called before write, throwing a 
TProtocolException if a required field is null.
- In Python and Node.js, an unset required field defaults to None/null and is 
silently omitted during serialization (writing an empty struct 00), which 
causes peer receivers to throw a TProtocolException on read.

In Go, instantiating a struct with required fields without explicitly assigning 
a value will serialize the Go zero-value for that type. This is consistent with 
Go idioms and fulfills the Thrift wire requirement that required fields be 
present on the wire.

Resolving as Not A Bug.

> Inconsistencies in Handling Default Values for Required Fields Across Thrift 
> Implementations
> --------------------------------------------------------------------------------------------
>
>                 Key: THRIFT-5803
>                 URL: https://issues.apache.org/jira/browse/THRIFT-5803
>             Project: Thrift
>          Issue Type: Bug
>          Components: Go - Compiler
>    Affects Versions: 0.19.0, 0.20.0
>            Reporter: Team_RPCtester
>            Priority: Major
>
> Hi,
> We discover an inconsistent behavior with respect to default values for 
> required string fields. Specifically, in Go, a required string field is 
> automatically initialized to an empty string if not explicitly set, whereas 
> other languages do not automatically initialize this field. This 
> inconsistency can be illustrated with the following example: 
> Thrift Definition:
> {code:java}
> namespace go commonResource
> struct StructClass_0 {
>  1: required string f_1,
> }
> service DataService {
>    StructClass_0 Method_1(1: StructClass_0 agr_method_1)
> }
> {code}
> Go client side,
> {code:java}
> agr_method_1_0 := commonResource.NewStructClass_0()
> fmt.Println(agr_method_1_0)
> // method_1_re_agr_method_1_0: StructClass_0({F_1:})
> {code}
> python client side 
> {code:java}
>    agr_method_1 = StructClass_0()
>    print(agr_method_1)
>   # StructClass_0(f_1=None)
> {code}
> nodejs client side 
> {code:java}
> arg_Method_1 = new ttypes.StructClass_0();
> console.log(arg_Method_1);
> // { f_1: null }
> {code}
> GO server side 
> {code:java}
> func (d DataServiceHandler) Method_1(ctx context.Context, agr_method_1 
> *commonResource.StructClass_0) (re_agr_method_1 
> *commonResource.StructClass_0, _err error) {
>    re_agr_method_1 = agr_method_1
>    return re_agr_method_1,  nil
> }
> {code}
> *Behavior Observed:*
>  * On the Go client side, if agr_method_1_0 is sent with an uninitialized 
> f_1, Go automatically sets f_1 to an empty string. The server receives this 
> empty string and processes it accordingly.
>  * On the Node.js client side, if arg_Method_1 is sent with an uninitialized 
> f_1, Node.js client reports an error: "Required field f_1 is unset!" and does 
> not allow the call to proceed.
>  * On the Python client side, if agr_method_1 is sent with f_1 as null, the 
> Go server reports: "*commonResource.StructClass_0 error reading struct: 
> Required field F_1 is not, the Nodejs server will prompt “"Required field f_1 
> is unset!"”, the Python server will return what it receives.
> Can you help check this issue.
> Thank you.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

Reply via email to