We can define a map value in our .proto file:
map<key_type, value_type> map_field = N;where the key_type can be integral or string type, but enum is not a vaild key_type.The value_type can be any type except another map.
Well, you can define the map like this:
map<string, Project> projects = 3;There are also some note:
Map field cannot be repeated.You cannot rely on your map items being in a particular order.When generating text format for a .protp, maps are sorted by key. Numeric keys are sorted numerically.When parsing a map from text format, parsing may fail if there are duplicate keys.If you provide a key but no value for a map field, the behavior when the field is serialized is language-dependent. In C++, Java, and Python the default value for the type is serialized, while in other languages (like Go) nothing is serialized.Any protocol buffers implementation that supports maps must both produce and accept data that can be accepted by the following definition.
message MapFieldEntry { key_type key = 1; value_type value = 2; } repeated MapFieldEntry map_field = N;We can add an optional package specifier to a .proto file.
package foo.bar; message Open {...}You can then use the package specifier when defining fields of your message type:
message Foo { ... foo.bar.Open open = 1; ... }In Go, the package is used as the Go package name, unless you explicitly provide an option go_package in your .proto file.
If you want to use your message types with an RPC system, you can define an RPC services interface in a .proto file.
service SearchService { rpc Search (SearchRequest) return (SearchResponse); }The most straightforward RPC system to use with protocol buffers is gRPC: a language- and platform-neutral open source RPC system developed at Google. gRPC works particularly well with protocol buffers and lets you generate the relevant RPC code directly from your .proto files using a special protocol buffer compiler plugin.
Proto3 supports a canonical encoding in JSON, making it easier to share data between systems. The encoding is described on a type-by-type basis in the table below.
proto3JSONJSON exampleNotesmessageobject{“fooBar”:v, “g”:null, …}Message field names are mapped to lowerCamelCase and become JSON object keys.null is an accepted value for all field types and treated as the default value of the corresponding field type.enumstring“FOO_BAR”The name of the enum value as specified in proto is used. Parsers accept both enum names and integer values.map<K,V>object{“k”:v, …}All keys are converted to strings.repeated Varray[v, …]null is accepted as the empty list [].booltrue, falsetrue, falsestringstring“Hello World!”bytesbase64 string"YWJjMTIzIT8kKiYoKSctPUB+"JSON value will be the data encoded as a string using standard base64 encoding with paddings.int32, fixed32, uint32number1, -10, 0JSON value will be a decimal number. Either numbers or strings are accepted.int64, fixed64, uint64string“1”, “-10”JSON value will be a decimal string. Either numbers or strings are accepted.float, doublenumber1.1, “NaN”, “Infinity”JSON value will be a number or one of the special string values “NaN”, “Infinity”, and “-Infinity”.Anyobject{"@type": “url”, “f”: v, …}If the Any contains a value that has a special JSON mapping, it will be converted as follows: {"@type": xxx, "value": yyy}.Otherwise, the value will be converted into a JSON object, and the "@type" field will be inserted to indicate the actual data type.Timestampstring"1972-01-01T10:00:20.021Z"Uses RFC 3339, where generated output will always be Z-normalized and uses 0, 3, 6 or 9 fractional digits.Durationstring"1.000340012s", "1s"Generated output always contains 0, 3, 6 or 9 fractional digits, depending on required precision, followed by the suffix “s”.Structobject{ … }Wrapper typesvarious types2, “2”, “foo”, trueWrappers use the same representation in JSON as the wrapped primitive type, except that null is allowed and preserved during data conversion and transfer.FieldMaskstring“f.fooBar, h”ListValuearray[foo, bar, …]ValuevalueAny JSON valueNullValuenullJSON nullEmptyobject{}An empty JSON objectThere are many options that we always use, but mostly are affect Java, C++ or Obeject-C, so we jump this part. But we can see the full options from the google/protobuf/descriptor.proto.
If you want to use .proto file to generate Go code, you need to run the protocol buffer compile protoc on the .proto.
The Protocol Compiler is invoked as follows:
protoc --proto_path=IMPORT_PATH --go_out=DST_DIR path/to/file.proto IMPORT_PATH specifies a directory in which to look for .proto files when resolving import directives. If omitted, the current directory is used.--go_out generates Go code in DST_DIR. See the Go generated code reference for more.You must provide one or more .proto files as input. Multiple .proto files can be specified at once. Although the files are named relative to the current directory, each file must reside in one of the IMPORT_PATHs so that the compiler can determine its canonical name.