blob: 139c9cd3f47cea92c1c28eaf1695a018118612b5 [file] [log] [blame]
Zack Williamse940c7a2019-08-21 14:25:39 -07001package internal
2
3import (
4 "unicode"
5 "unicode/utf8"
6)
7
8const (
9 // MaxTag is the maximum allowed tag number for a field.
10 MaxTag = 536870911 // 2^29 - 1
11
12 // SpecialReservedStart is the first tag in a range that is reserved and not
13 // allowed for use in message definitions.
14 SpecialReservedStart = 19000
15 // SpecialReservedEnd is the last tag in a range that is reserved and not
16 // allowed for use in message definitions.
17 SpecialReservedEnd = 19999
18
19 // NB: It would be nice to use constants from generated code instead of
20 // hard-coding these here. But code-gen does not emit these as constants
21 // anywhere. The only places they appear in generated code are struct tags
22 // on fields of the generated descriptor protos.
23
24 // File_packageTag is the tag number of the package element in a file
25 // descriptor proto.
26 File_packageTag = 2
27 // File_dependencyTag is the tag number of the dependencies element in a
28 // file descriptor proto.
29 File_dependencyTag = 3
30 // File_messagesTag is the tag number of the messages element in a file
31 // descriptor proto.
32 File_messagesTag = 4
33 // File_enumsTag is the tag number of the enums element in a file descriptor
34 // proto.
35 File_enumsTag = 5
36 // File_servicesTag is the tag number of the services element in a file
37 // descriptor proto.
38 File_servicesTag = 6
39 // File_extensionsTag is the tag number of the extensions element in a file
40 // descriptor proto.
41 File_extensionsTag = 7
42 // File_optionsTag is the tag number of the options element in a file
43 // descriptor proto.
44 File_optionsTag = 8
45 // File_syntaxTag is the tag number of the syntax element in a file
46 // descriptor proto.
47 File_syntaxTag = 12
48 // Message_nameTag is the tag number of the name element in a message
49 // descriptor proto.
50 Message_nameTag = 1
51 // Message_fieldsTag is the tag number of the fields element in a message
52 // descriptor proto.
53 Message_fieldsTag = 2
54 // Message_nestedMessagesTag is the tag number of the nested messages
55 // element in a message descriptor proto.
56 Message_nestedMessagesTag = 3
57 // Message_enumsTag is the tag number of the enums element in a message
58 // descriptor proto.
59 Message_enumsTag = 4
60 // Message_extensionRangeTag is the tag number of the extension ranges
61 // element in a message descriptor proto.
62 Message_extensionRangeTag = 5
63 // Message_extensionsTag is the tag number of the extensions element in a
64 // message descriptor proto.
65 Message_extensionsTag = 6
66 // Message_optionsTag is the tag number of the options element in a message
67 // descriptor proto.
68 Message_optionsTag = 7
69 // Message_oneOfsTag is the tag number of the one-ofs element in a message
70 // descriptor proto.
71 Message_oneOfsTag = 8
72 // Message_reservedRangeTag is the tag number of the reserved ranges element
73 // in a message descriptor proto.
74 Message_reservedRangeTag = 9
75 // Message_reservedNameTag is the tag number of the reserved names element
76 // in a message descriptor proto.
77 Message_reservedNameTag = 10
78 // ExtensionRange_startTag is the tag number of the start index in an
79 // extension range proto.
80 ExtensionRange_startTag = 1
81 // ExtensionRange_endTag is the tag number of the end index in an
82 // extension range proto.
83 ExtensionRange_endTag = 2
84 // ExtensionRange_optionsTag is the tag number of the options element in an
85 // extension range proto.
86 ExtensionRange_optionsTag = 3
87 // ReservedRange_startTag is the tag number of the start index in a reserved
88 // range proto.
89 ReservedRange_startTag = 1
90 // ReservedRange_endTag is the tag number of the end index in a reserved
91 // range proto.
92 ReservedRange_endTag = 2
93 // Field_nameTag is the tag number of the name element in a field descriptor
94 // proto.
95 Field_nameTag = 1
96 // Field_extendeeTag is the tag number of the extendee element in a field
97 // descriptor proto.
98 Field_extendeeTag = 2
99 // Field_numberTag is the tag number of the number element in a field
100 // descriptor proto.
101 Field_numberTag = 3
102 // Field_labelTag is the tag number of the label element in a field
103 // descriptor proto.
104 Field_labelTag = 4
105 // Field_typeTag is the tag number of the type element in a field descriptor
106 // proto.
107 Field_typeTag = 5
Scott Baker4a35a702019-11-26 08:17:33 -0800108 // Field_typeNameTag is the tag number of the type name element in a field
109 // descriptor proto.
110 Field_typeNameTag = 6
Zack Williamse940c7a2019-08-21 14:25:39 -0700111 // Field_defaultTag is the tag number of the default value element in a
112 // field descriptor proto.
113 Field_defaultTag = 7
114 // Field_optionsTag is the tag number of the options element in a field
115 // descriptor proto.
116 Field_optionsTag = 8
117 // Field_jsonNameTag is the tag number of the JSON name element in a field
118 // descriptor proto.
119 Field_jsonNameTag = 10
120 // OneOf_nameTag is the tag number of the name element in a one-of
121 // descriptor proto.
122 OneOf_nameTag = 1
123 // OneOf_optionsTag is the tag number of the options element in a one-of
124 // descriptor proto.
125 OneOf_optionsTag = 2
126 // Enum_nameTag is the tag number of the name element in an enum descriptor
127 // proto.
128 Enum_nameTag = 1
129 // Enum_valuesTag is the tag number of the values element in an enum
130 // descriptor proto.
131 Enum_valuesTag = 2
132 // Enum_optionsTag is the tag number of the options element in an enum
133 // descriptor proto.
134 Enum_optionsTag = 3
135 // Enum_reservedRangeTag is the tag number of the reserved ranges element in
136 // an enum descriptor proto.
137 Enum_reservedRangeTag = 4
138 // Enum_reservedNameTag is the tag number of the reserved names element in
139 // an enum descriptor proto.
140 Enum_reservedNameTag = 5
141 // EnumVal_nameTag is the tag number of the name element in an enum value
142 // descriptor proto.
143 EnumVal_nameTag = 1
144 // EnumVal_numberTag is the tag number of the number element in an enum
145 // value descriptor proto.
146 EnumVal_numberTag = 2
147 // EnumVal_optionsTag is the tag number of the options element in an enum
148 // value descriptor proto.
149 EnumVal_optionsTag = 3
150 // Service_nameTag is the tag number of the name element in a service
151 // descriptor proto.
152 Service_nameTag = 1
153 // Service_methodsTag is the tag number of the methods element in a service
154 // descriptor proto.
155 Service_methodsTag = 2
156 // Service_optionsTag is the tag number of the options element in a service
157 // descriptor proto.
158 Service_optionsTag = 3
159 // Method_nameTag is the tag number of the name element in a method
160 // descriptor proto.
161 Method_nameTag = 1
162 // Method_inputTag is the tag number of the input type element in a method
163 // descriptor proto.
164 Method_inputTag = 2
165 // Method_outputTag is the tag number of the output type element in a method
166 // descriptor proto.
167 Method_outputTag = 3
168 // Method_optionsTag is the tag number of the options element in a method
169 // descriptor proto.
170 Method_optionsTag = 4
171 // Method_inputStreamTag is the tag number of the input stream flag in a
172 // method descriptor proto.
173 Method_inputStreamTag = 5
174 // Method_outputStreamTag is the tag number of the output stream flag in a
175 // method descriptor proto.
176 Method_outputStreamTag = 6
177
178 // UninterpretedOptionsTag is the tag number of the uninterpreted options
179 // element. All *Options messages use the same tag for the field that stores
180 // uninterpreted options.
181 UninterpretedOptionsTag = 999
182
183 // Uninterpreted_nameTag is the tag number of the name element in an
184 // uninterpreted options proto.
185 Uninterpreted_nameTag = 2
186 // Uninterpreted_identTag is the tag number of the identifier value in an
187 // uninterpreted options proto.
188 Uninterpreted_identTag = 3
189 // Uninterpreted_posIntTag is the tag number of the positive int value in an
190 // uninterpreted options proto.
191 Uninterpreted_posIntTag = 4
192 // Uninterpreted_negIntTag is the tag number of the negative int value in an
193 // uninterpreted options proto.
194 Uninterpreted_negIntTag = 5
195 // Uninterpreted_doubleTag is the tag number of the double value in an
196 // uninterpreted options proto.
197 Uninterpreted_doubleTag = 6
198 // Uninterpreted_stringTag is the tag number of the string value in an
199 // uninterpreted options proto.
200 Uninterpreted_stringTag = 7
201 // Uninterpreted_aggregateTag is the tag number of the aggregate value in an
202 // uninterpreted options proto.
203 Uninterpreted_aggregateTag = 8
204 // UninterpretedName_nameTag is the tag number of the name element in an
205 // uninterpreted option name proto.
206 UninterpretedName_nameTag = 1
207)
208
209// JsonName returns the default JSON name for a field with the given name.
210func JsonName(name string) string {
211 var js []rune
212 nextUpper := false
213 for i, r := range name {
214 if r == '_' {
215 nextUpper = true
216 continue
217 }
218 if i == 0 {
219 js = append(js, r)
220 } else if nextUpper {
221 nextUpper = false
222 js = append(js, unicode.ToUpper(r))
223 } else {
224 js = append(js, r)
225 }
226 }
227 return string(js)
228}
229
230// InitCap returns the given field name, but with the first letter capitalized.
231func InitCap(name string) string {
232 r, sz := utf8.DecodeRuneInString(name)
233 return string(unicode.ToUpper(r)) + name[sz:]
234}
235
236// CreatePrefixList returns a list of package prefixes to search when resolving
237// a symbol name. If the given package is blank, it returns only the empty
238// string. If the given package contains only one token, e.g. "foo", it returns
239// that token and the empty string, e.g. ["foo", ""]. Otherwise, it returns
240// successively shorter prefixes of the package and then the empty string. For
241// example, for a package named "foo.bar.baz" it will return the following list:
242// ["foo.bar.baz", "foo.bar", "foo", ""]
243func CreatePrefixList(pkg string) []string {
244 if pkg == "" {
245 return []string{""}
246 }
247
248 numDots := 0
249 // one pass to pre-allocate the returned slice
250 for i := 0; i < len(pkg); i++ {
251 if pkg[i] == '.' {
252 numDots++
253 }
254 }
255 if numDots == 0 {
256 return []string{pkg, ""}
257 }
258
259 prefixes := make([]string, numDots+2)
260 // second pass to fill in returned slice
261 for i := 0; i < len(pkg); i++ {
262 if pkg[i] == '.' {
263 prefixes[numDots] = pkg[:i]
264 numDots--
265 }
266 }
267 prefixes[0] = pkg
268
269 return prefixes
270}