Consider the following protobuf:
message SendRequest {
/** The raw text of the message that the caller wishes to send. */
optional string message = 1;
}
Note that the string message is being used as a field name. The protobuf compilers seems to be fine with this, even though message is the protobuf keyword.
Is this usage kosher in the sense that keywords are defined by some standard to be ignored in field names, or could this break my application in the future?
Yes, it is possible because in runtime a proto field is identified by their id (in your case 1) and not with their name.
Related
I'm trying to implement data contract logic.
I've 2 services switching messages with each other.
Service A send messages in some format + the file descriptor proto of the .proto file used to generate it. Service B gets them both, the message and the file descriptor proto and has to ensure the message doesn't break the schema defenition.
What I've did until now is to create a dynamic message instance using the descriptor proto and tried to unmarshal the message into the dynamic message instance, and in case no error occurred during the unmarshal process it counts as a success (message doesn't break the schema).
Is it ok to rely on the unmarshal function in order to decide whether the message is ok?
I noticed that even in case I'm sending messages with totally different schemas the unmarshal succeed. the only way I found to cause the unmarshal to fail is by sending proto2 messages with missing required fields.
So is it by design that every message can be unmarshled using a totally different schema definition?
I'm using the official Go protobuf library
Yes, it is ok to use unmarshal function to check if your proto is valid or not.
No, it's not design to unmarshal arbitrary message but it is designed to unmarshal only that fields which are present in your protobuf message. For example, you have proto message with structure as follow:
message MyMessage {
uint64 id = 1;
string name = 2;
string surname = 3;
}
If your server receives message that contains just id and name and your server is trying to unmarshal this message, id and name fields would be unmarshaled while surname field in your structure would be empty.
This approach appliable for JSONs too.
I know there is a way to serialize a message in protobuf. But is there a easy way to print out the values in a protobuf message? Something like a toString() method in Java?
Thanks.
protocol buffer basics -- Java
quoted from the link, check the standard message methods:
Standard Message Methods
Each message and builder class also contains a number of other methods that let you check or manipulate the entire message, including:
isInitialized(): checks if all the required fields have been set.
toString(): returns a human-readable representation of the message, particularly useful for debugging.
mergeFrom(Message other): (builder only) merges the contents of other into this message, overwriting singular fields and concatenating repeated ones.
clear(): (builder only) clears all the fields back to the empty state.
Based on the documentation, %s will be replaced by field name when setting error messages.
If you include %s in your error string, it will be replaced with the
"human" name you used for your field when you set your rules.
Is there a way to have multiple %s in the string and define them differently?
This is the line in the form validation library that creates the error message:
// Build the error message
$message = sprintf($line, $this->_translate_fieldname($row['label']), $param);
$line: The error message template, for example "The % field is invalid"
$this->_translate_fieldname($row['label']): The field's label
$param: The parameter passed the the validation function, if any, max_length[5] would pass "5"
So that's the extent of what the form validation class does for you. If you need more flexibility you'll have to prepare the error message yourself <-- might be useful beforehand with the extra variables already populated.
It might be interesting to extend the form validation class via core/MY_form_validation.php and work this functionality in. Unfortunately this line is contained in the main function _execute which is very big and messy, and from looking at it now, you'd need to overload some other functions as well. I started to write an example but it actually looks like a chore. You might be better off using:
$this->form_validation->set_message('rule_name', 'Your custom message here');
More on setting error messages: http://ellislab.com/codeigniter/user_guide/libraries/form_validation.html#settingerrors
I am in reference to the following method from BindingResult:
BindingResult.html#resolveMessageCodes(java.lang.String, java.lang.String)
I am trying to figure out the difference between an error code and a message code. Can someone please provide an example, especially one that would illustrate why there could be several message codes for a given error code?
Because web applications are internationalized, when you reject an object and want to have a message displayed for it, you don't use a hardcoded text because that will show the same no matter the language.
Instead, you specify an error code that later server as a key to retrieving the proper message from the bundles (and now the error code is a message code from the point of view of the method that must find the proper message text).
Your error code resolves to more message codes because Spring (based on the implementation) adds some additional ones for you. Here is a snippet from the Spring documentation:
[...] What error codes it registers is determined by the MessageCodesResolver that is used. By default, the DefaultMessageCodesResolver is used, which for example not only registers a message with the code you gave, but also messages that include the field name you passed to the reject method. So in case you reject a field using rejectValue("age", "too.darn.old"), apart from the too.darn.old code, Spring will also register too.darn.old.age and too.darn.old.age.int (so the first will include the field name and the second will include the type of the field); this is done as a convenience to aid developers in targeting error messages and suchlike. [...]
The last statement is the reason there are more message codes, to have control on the message that is displayed to the user, from a generic one (e.g. "Value required") to a more specific one given the context (e.g. "A value is required for field XXX").
The javadoc for DefaultMessageCodesResolver explains it further and gives an example:
For example, in case of code "typeMismatch", object name "user", field "age":
try "typeMismatch.user.age"
try "typeMismatch.age"
try "typeMismatch.int"
try "typeMismatch"
This resolution algorithm thus can be leveraged for example to show specific messages for binding errors like "required" and "typeMismatch":
at the object + field level ("age" field, but only on "user");
at the field level (all "age" fields, no matter which object name);
or at the general level (all fields, on any object).
How can I pass a meaningful error message back to client? I can implement the ExceptionMapper to produce meaningful error message.
But how can I have writer to pass the message back to client?
I haven't used jersey personally, but my general approach here would be to simply include the result-state (including error message) in the returned message, i.e.
message GetCustomerResult {
optional string errorMessage = 1;
optional Customer customer = 2;
}
or similar, such that all your messages have a consistent way to report failure. If your error state is more than just a string, you could declare a message for that, and include it on all results, so you can just pass that to any shared error-handling code.
You can throw WebApplicationException which takes Response in a constructor and gets mapped by Jersey automatically to that response. You can put the meaningful message into the response body.