github.com/CiscoM31/godata@v1.0.10/request_model.go (about) 1 package godata 2 3 type GoDataIdentifier map[string]string 4 5 type RequestKind int 6 7 const ( 8 RequestKindUnknown RequestKind = iota 9 RequestKindMetadata 10 RequestKindService 11 RequestKindEntity 12 RequestKindCollection 13 RequestKindSingleton 14 RequestKindProperty 15 RequestKindPropertyValue 16 RequestKindRef 17 RequestKindCount 18 ) 19 20 type SemanticType int 21 22 const ( 23 SemanticTypeUnknown SemanticType = iota 24 SemanticTypeEntity 25 SemanticTypeEntitySet 26 SemanticTypeDerivedEntity 27 SemanticTypeAction 28 SemanticTypeFunction 29 SemanticTypeProperty 30 SemanticTypePropertyValue 31 SemanticTypeRef 32 SemanticTypeCount 33 SemanticTypeMetadata 34 ) 35 36 type GoDataRequest struct { 37 FirstSegment *GoDataSegment 38 LastSegment *GoDataSegment 39 Query *GoDataQuery 40 RequestKind RequestKind 41 } 42 43 // Represents a segment (slash-separated) part of the URI path. Each segment 44 // has a link to the next segment (the last segment precedes nil). 45 type GoDataSegment struct { 46 // The raw segment parsed from the URI 47 RawValue string 48 49 // The kind of resource being pointed at by this segment 50 SemanticType SemanticType 51 52 // A pointer to the metadata type this object represents, as defined by a 53 // particular service 54 SemanticReference interface{} 55 56 // The name of the entity, type, collection, etc. 57 Name string 58 59 // map[string]string of identifiers passed to this segment. If the identifier 60 // is not key/value pair(s), then all values will be nil. If there is no 61 // identifier, it will be nil. 62 Identifier *GoDataIdentifier 63 64 // The next segment in the path. 65 Next *GoDataSegment 66 // The previous segment in the path. 67 Prev *GoDataSegment 68 } 69 70 type GoDataQuery struct { 71 Filter *GoDataFilterQuery 72 At *GoDataFilterQuery 73 Apply *GoDataApplyQuery 74 Expand *GoDataExpandQuery 75 Select *GoDataSelectQuery 76 OrderBy *GoDataOrderByQuery 77 Top *GoDataTopQuery 78 Skip *GoDataSkipQuery 79 Count *GoDataCountQuery 80 InlineCount *GoDataInlineCountQuery 81 Search *GoDataSearchQuery 82 Compute *GoDataComputeQuery 83 Format *GoDataFormatQuery 84 } 85 86 // GoDataExpression encapsulates the tree representation of an expression 87 // as defined in the OData ABNF grammar. 88 type GoDataExpression struct { 89 Tree *ParseNode 90 // The raw string representing an expression 91 RawValue string 92 } 93 94 // Stores a parsed version of the filter query string. Can be used by 95 // providers to apply the filter based on their own implementation. The filter 96 // is stored as a parse tree that can be traversed. 97 type GoDataFilterQuery struct { 98 Tree *ParseNode 99 // The raw filter string 100 RawValue string 101 } 102 103 type GoDataApplyQuery string 104 105 type GoDataExpandQuery struct { 106 ExpandItems []*ExpandItem 107 } 108 109 type GoDataSelectQuery struct { 110 SelectItems []*SelectItem 111 // The raw select string 112 RawValue string 113 } 114 115 type GoDataOrderByQuery struct { 116 OrderByItems []*OrderByItem 117 // The raw orderby string 118 RawValue string 119 } 120 121 type GoDataTopQuery int 122 123 type GoDataSkipQuery int 124 125 type GoDataCountQuery bool 126 127 type GoDataInlineCountQuery string 128 129 type GoDataSearchQuery struct { 130 Tree *ParseNode 131 // The raw search string 132 RawValue string 133 } 134 135 type GoDataComputeQuery struct { 136 ComputeItems []*ComputeItem 137 // The raw compute string 138 RawValue string 139 } 140 141 type GoDataFormatQuery struct { 142 } 143 144 // Check if this identifier has more than one key/value pair. 145 func (id *GoDataIdentifier) HasMultiple() bool { 146 count := 0 147 for range map[string]string(*id) { 148 count++ 149 } 150 return count > 1 151 } 152 153 // Return the first key in the map. This is how you should get the identifier 154 // for single values, e.g. when the path is Employee(1), etc. 155 func (id *GoDataIdentifier) Get() string { 156 for k := range map[string]string(*id) { 157 return k 158 } 159 return "" 160 } 161 162 // Return a specific value for a specific key. 163 func (id *GoDataIdentifier) GetKey(key string) (string, bool) { 164 v, ok := map[string]string(*id)[key] 165 return v, ok 166 } 167 168 // GoDataCommonStructure represents either a GoDataQuery or ExpandItem in a uniform manner 169 // as a Go interface. This allows the writing of functional logic that can work on either type, 170 // such as a provider implementation which starts at the GoDataQuery and walks any nested ExpandItem 171 // in an identical manner. 172 type GoDataCommonStructure interface { 173 GetFilter() *GoDataFilterQuery 174 GetAt() *GoDataFilterQuery 175 GetApply() *GoDataApplyQuery 176 GetExpand() *GoDataExpandQuery 177 GetSelect() *GoDataSelectQuery 178 GetOrderBy() *GoDataOrderByQuery 179 GetTop() *GoDataTopQuery 180 GetSkip() *GoDataSkipQuery 181 GetCount() *GoDataCountQuery 182 GetInlineCount() *GoDataInlineCountQuery 183 GetSearch() *GoDataSearchQuery 184 GetCompute() *GoDataComputeQuery 185 GetFormat() *GoDataFormatQuery 186 // AddExpandItem adds an item to the list of expand clauses in the underlying GoDataQuery/ExpandItem 187 // structure. 188 // AddExpandItem may be used to add items based on the requirements of the application using godata. 189 // For example applications may support the introduction of dynamic navigational fields using $compute. 190 // A possible implementation is to parse the request url using godata and then during semantic 191 // post-processing identify dynamic navigation properties and call AddExpandItem to add them to the 192 // list of expanded fields. 193 AddExpandItem(*ExpandItem) 194 } 195 196 // GoDataQuery implementation of GoDataCommonStructure interface 197 func (o *GoDataQuery) GetFilter() *GoDataFilterQuery { return o.Filter } 198 func (o *GoDataQuery) GetAt() *GoDataFilterQuery { return o.At } 199 func (o *GoDataQuery) GetApply() *GoDataApplyQuery { return o.Apply } 200 func (o *GoDataQuery) GetExpand() *GoDataExpandQuery { return o.Expand } 201 func (o *GoDataQuery) GetSelect() *GoDataSelectQuery { return o.Select } 202 func (o *GoDataQuery) GetOrderBy() *GoDataOrderByQuery { return o.OrderBy } 203 func (o *GoDataQuery) GetTop() *GoDataTopQuery { return o.Top } 204 func (o *GoDataQuery) GetSkip() *GoDataSkipQuery { return o.Skip } 205 func (o *GoDataQuery) GetCount() *GoDataCountQuery { return o.Count } 206 func (o *GoDataQuery) GetInlineCount() *GoDataInlineCountQuery { return o.InlineCount } 207 func (o *GoDataQuery) GetSearch() *GoDataSearchQuery { return o.Search } 208 func (o *GoDataQuery) GetCompute() *GoDataComputeQuery { return o.Compute } 209 func (o *GoDataQuery) GetFormat() *GoDataFormatQuery { return o.Format } 210 211 // AddExpandItem adds an expand clause to the toplevel odata request structure 'o'. 212 func (o *GoDataQuery) AddExpandItem(item *ExpandItem) { 213 if o.Expand == nil { 214 o.Expand = &GoDataExpandQuery{} 215 } 216 o.Expand.ExpandItems = append(o.Expand.ExpandItems, item) 217 } 218 219 // ExpandItem implementation of GoDataCommonStructure interface 220 func (o *ExpandItem) GetFilter() *GoDataFilterQuery { return o.Filter } 221 func (o *ExpandItem) GetAt() *GoDataFilterQuery { return o.At } 222 func (o *ExpandItem) GetApply() *GoDataApplyQuery { return nil } 223 func (o *ExpandItem) GetExpand() *GoDataExpandQuery { return o.Expand } 224 func (o *ExpandItem) GetSelect() *GoDataSelectQuery { return o.Select } 225 func (o *ExpandItem) GetOrderBy() *GoDataOrderByQuery { return o.OrderBy } 226 func (o *ExpandItem) GetTop() *GoDataTopQuery { return o.Top } 227 func (o *ExpandItem) GetSkip() *GoDataSkipQuery { return o.Skip } 228 func (o *ExpandItem) GetCount() *GoDataCountQuery { return nil } 229 func (o *ExpandItem) GetInlineCount() *GoDataInlineCountQuery { return nil } 230 func (o *ExpandItem) GetSearch() *GoDataSearchQuery { return o.Search } 231 func (o *ExpandItem) GetCompute() *GoDataComputeQuery { return o.Compute } 232 func (o *ExpandItem) GetFormat() *GoDataFormatQuery { return nil } 233 234 // AddExpandItem adds an expand clause to 'o' creating a nested expand, ie $expand 'item' 235 // nested within $expand 'o'. 236 func (o *ExpandItem) AddExpandItem(item *ExpandItem) { 237 if o.Expand == nil { 238 o.Expand = &GoDataExpandQuery{} 239 } 240 o.Expand.ExpandItems = append(o.Expand.ExpandItems, item) 241 }