github.com/authzed/spicedb@v1.32.1-0.20240520085336-ebda56537386/pkg/typesystem/errors.go (about) 1 package typesystem 2 3 import ( 4 "errors" 5 "fmt" 6 "strings" 7 8 "github.com/rs/zerolog" 9 10 "github.com/authzed/spicedb/internal/sharederrors" 11 ) 12 13 // ErrNamespaceNotFound occurs when a namespace was not found. 14 type ErrNamespaceNotFound struct { 15 error 16 namespaceName string 17 } 18 19 // NotFoundNamespaceName is the name of the namespace not found. 20 func (err ErrNamespaceNotFound) NotFoundNamespaceName() string { 21 return err.namespaceName 22 } 23 24 // MarshalZerologObject implements zerolog object marshalling. 25 func (err ErrNamespaceNotFound) MarshalZerologObject(e *zerolog.Event) { 26 e.Err(err.error).Str("namespace", err.namespaceName) 27 } 28 29 // DetailsMetadata returns the metadata for details for this error. 30 func (err ErrNamespaceNotFound) DetailsMetadata() map[string]string { 31 return map[string]string{ 32 "definition_name": err.namespaceName, 33 } 34 } 35 36 // ErrRelationNotFound occurs when a relation was not found under a namespace. 37 type ErrRelationNotFound struct { 38 error 39 namespaceName string 40 relationName string 41 } 42 43 // NamespaceName returns the name of the namespace in which the relation was not found. 44 func (err ErrRelationNotFound) NamespaceName() string { 45 return err.namespaceName 46 } 47 48 // NotFoundRelationName returns the name of the relation not found. 49 func (err ErrRelationNotFound) NotFoundRelationName() string { 50 return err.relationName 51 } 52 53 func (err ErrRelationNotFound) MarshalZerologObject(e *zerolog.Event) { 54 e.Err(err.error).Str("namespace", err.namespaceName).Str("relation", err.relationName) 55 } 56 57 // DetailsMetadata returns the metadata for details for this error. 58 func (err ErrRelationNotFound) DetailsMetadata() map[string]string { 59 return map[string]string{ 60 "definition_name": err.namespaceName, 61 "relation_or_permission_name": err.relationName, 62 } 63 } 64 65 // ErrCaveatNotFound occurs when a caveat was not found. 66 type ErrCaveatNotFound struct { 67 error 68 caveatName string 69 } 70 71 // CaveatName returns the name of the caveat not found. 72 func (err ErrCaveatNotFound) CaveatName() string { 73 return err.caveatName 74 } 75 76 func (err ErrCaveatNotFound) MarshalZerologObject(e *zerolog.Event) { 77 e.Err(err.error).Str("caveat", err.caveatName) 78 } 79 80 // DetailsMetadata returns the metadata for details for this error. 81 func (err ErrCaveatNotFound) DetailsMetadata() map[string]string { 82 return map[string]string{ 83 "caveat_name": err.caveatName, 84 } 85 } 86 87 // ErrDuplicateRelation occurs when a duplicate relation was found inside a namespace. 88 type ErrDuplicateRelation struct { 89 error 90 namespaceName string 91 relationName string 92 } 93 94 // MarshalZerologObject implements zerolog object marshalling. 95 func (err ErrDuplicateRelation) MarshalZerologObject(e *zerolog.Event) { 96 e.Err(err.error).Str("namespace", err.namespaceName).Str("relation", err.relationName) 97 } 98 99 // DetailsMetadata returns the metadata for details for this error. 100 func (err ErrDuplicateRelation) DetailsMetadata() map[string]string { 101 return map[string]string{ 102 "definition_name": err.namespaceName, 103 "relation_or_permission_name": err.relationName, 104 } 105 } 106 107 // ErrPermissionUsedOnLeftOfArrow occurs when a permission is used on the left side of an arrow 108 // expression. 109 type ErrPermissionUsedOnLeftOfArrow struct { 110 error 111 namespaceName string 112 parentPermissionName string 113 foundPermissionName string 114 } 115 116 // MarshalZerologObject implements zerolog object marshalling. 117 func (err ErrPermissionUsedOnLeftOfArrow) MarshalZerologObject(e *zerolog.Event) { 118 e.Err(err.error).Str("namespace", err.namespaceName).Str("permission", err.parentPermissionName).Str("usedPermission", err.foundPermissionName) 119 } 120 121 // DetailsMetadata returns the metadata for details for this error. 122 func (err ErrPermissionUsedOnLeftOfArrow) DetailsMetadata() map[string]string { 123 return map[string]string{ 124 "definition_name": err.namespaceName, 125 "permission_name": err.parentPermissionName, 126 "used_permission_name": err.foundPermissionName, 127 } 128 } 129 130 // ErrWildcardUsedInArrow occurs when an arrow operates over a relation that contains a wildcard. 131 type ErrWildcardUsedInArrow struct { 132 error 133 namespaceName string 134 parentPermissionName string 135 accessedRelationName string 136 } 137 138 // MarshalZerologObject implements zerolog object marshalling. 139 func (err ErrWildcardUsedInArrow) MarshalZerologObject(e *zerolog.Event) { 140 e.Err(err.error).Str("namespace", err.namespaceName).Str("parentPermissionName", err.parentPermissionName).Str("accessedRelationName", err.accessedRelationName) 141 } 142 143 // DetailsMetadata returns the metadata for details for this error. 144 func (err ErrWildcardUsedInArrow) DetailsMetadata() map[string]string { 145 return map[string]string{ 146 "definition_name": err.namespaceName, 147 "permission_name": err.parentPermissionName, 148 "accessed_relation_name": err.accessedRelationName, 149 } 150 } 151 152 // ErrMissingAllowedRelations occurs when a relation is defined without any type information. 153 type ErrMissingAllowedRelations struct { 154 error 155 namespaceName string 156 relationName string 157 } 158 159 // MarshalZerologObject implements zerolog object marshalling. 160 func (err ErrMissingAllowedRelations) MarshalZerologObject(e *zerolog.Event) { 161 e.Err(err.error).Str("namespace", err.namespaceName).Str("relation", err.relationName) 162 } 163 164 // DetailsMetadata returns the metadata for details for this error. 165 func (err ErrMissingAllowedRelations) DetailsMetadata() map[string]string { 166 return map[string]string{ 167 "definition_name": err.namespaceName, 168 "relation_name": err.relationName, 169 } 170 } 171 172 // ErrTransitiveWildcard occurs when a wildcard relation in turn references another wildcard 173 // relation. 174 type ErrTransitiveWildcard struct { 175 error 176 namespaceName string 177 relationName string 178 } 179 180 // MarshalZerologObject implements zerolog object marshalling. 181 func (err ErrTransitiveWildcard) MarshalZerologObject(e *zerolog.Event) { 182 e.Err(err.error).Str("namespace", err.namespaceName).Str("relation", err.relationName) 183 } 184 185 // DetailsMetadata returns the metadata for details for this error. 186 func (err ErrTransitiveWildcard) DetailsMetadata() map[string]string { 187 return map[string]string{ 188 "definition_name": err.namespaceName, 189 "relation_name": err.relationName, 190 } 191 } 192 193 // ErrPermissionsCycle occurs when a cycle exists within permissions. 194 type ErrPermissionsCycle struct { 195 error 196 namespaceName string 197 permissionNames []string 198 } 199 200 // MarshalZerologObject implements zerolog object marshalling. 201 func (err ErrPermissionsCycle) MarshalZerologObject(e *zerolog.Event) { 202 e.Err(err.error).Str("namespace", err.namespaceName).Str("permissions", strings.Join(err.permissionNames, ", ")) 203 } 204 205 // DetailsMetadata returns the metadata for details for this error. 206 func (err ErrPermissionsCycle) DetailsMetadata() map[string]string { 207 return map[string]string{ 208 "definition_name": err.namespaceName, 209 "permission_names": strings.Join(err.permissionNames, ","), 210 } 211 } 212 213 // ErrDuplicateAllowedRelation indicates that an allowed relation was redefined on a relation. 214 type ErrDuplicateAllowedRelation struct { 215 error 216 namespaceName string 217 relationName string 218 allowedRelationSource string 219 } 220 221 // MarshalZerologObject implements zerolog object marshalling. 222 func (err ErrDuplicateAllowedRelation) MarshalZerologObject(e *zerolog.Event) { 223 e.Err(err.error).Str("namespace", err.namespaceName).Str("relation", err.relationName).Str("allowed-relation", err.allowedRelationSource) 224 } 225 226 // DetailsMetadata returns the metadata for details for this error. 227 func (err ErrDuplicateAllowedRelation) DetailsMetadata() map[string]string { 228 return map[string]string{ 229 "definition_name": err.namespaceName, 230 "relation_name": err.relationName, 231 "allowed_relation": err.allowedRelationSource, 232 } 233 } 234 235 // ErrUnusedCaveatParameter indicates that a caveat parameter is unused in the caveat expression. 236 type ErrUnusedCaveatParameter struct { 237 error 238 caveatName string 239 paramName string 240 } 241 242 // MarshalZerologObject implements zerolog object marshalling. 243 func (err ErrUnusedCaveatParameter) MarshalZerologObject(e *zerolog.Event) { 244 e.Err(err.error).Str("caveat", err.caveatName).Str("param", err.paramName) 245 } 246 247 // DetailsMetadata returns the metadata for details for this error. 248 func (err ErrUnusedCaveatParameter) DetailsMetadata() map[string]string { 249 return map[string]string{ 250 "caveat_name": err.caveatName, 251 "parameter_name": err.paramName, 252 } 253 } 254 255 // NewNamespaceNotFoundErr constructs a new namespace not found error. 256 func NewNamespaceNotFoundErr(nsName string) error { 257 return ErrNamespaceNotFound{ 258 error: fmt.Errorf("object definition `%s` not found", nsName), 259 namespaceName: nsName, 260 } 261 } 262 263 // NewRelationNotFoundErr constructs a new relation not found error. 264 func NewRelationNotFoundErr(nsName string, relationName string) error { 265 return ErrRelationNotFound{ 266 error: fmt.Errorf("relation/permission `%s` not found under definition `%s`", relationName, nsName), 267 namespaceName: nsName, 268 relationName: relationName, 269 } 270 } 271 272 // NewCaveatNotFoundErr constructs a new caveat not found error. 273 func NewCaveatNotFoundErr(caveatName string) error { 274 return ErrCaveatNotFound{ 275 error: fmt.Errorf("caveat `%s` not found", caveatName), 276 caveatName: caveatName, 277 } 278 } 279 280 // NewDuplicateRelationError constructs an error indicating that a relation was defined more than once in a namespace. 281 func NewDuplicateRelationError(nsName string, relationName string) error { 282 return ErrDuplicateRelation{ 283 error: fmt.Errorf("found duplicate relation/permission name `%s` under definition `%s`", relationName, nsName), 284 namespaceName: nsName, 285 relationName: relationName, 286 } 287 } 288 289 // NewDuplicateAllowedRelationErr constructs an error indicating that an allowed relation was defined more than once for a relation. 290 func NewDuplicateAllowedRelationErr(nsName string, relationName string, allowedRelationSource string) error { 291 return ErrDuplicateAllowedRelation{ 292 error: fmt.Errorf("found duplicate allowed subject type `%s` on relation `%s` under definition `%s`", allowedRelationSource, relationName, nsName), 293 namespaceName: nsName, 294 relationName: relationName, 295 allowedRelationSource: allowedRelationSource, 296 } 297 } 298 299 // NewPermissionUsedOnLeftOfArrowErr constructs an error indicating that a permission was used on the left side of an arrow. 300 func NewPermissionUsedOnLeftOfArrowErr(nsName string, parentPermissionName string, foundPermissionName string) error { 301 return ErrPermissionUsedOnLeftOfArrow{ 302 error: fmt.Errorf("under permission `%s` under definition `%s`: permissions cannot be used on the left hand side of an arrow (found `%s`)", parentPermissionName, nsName, foundPermissionName), 303 namespaceName: nsName, 304 parentPermissionName: parentPermissionName, 305 foundPermissionName: foundPermissionName, 306 } 307 } 308 309 // NewWildcardUsedInArrowErr constructs an error indicating that an arrow operated over a relation with a wildcard type. 310 func NewWildcardUsedInArrowErr(nsName string, parentPermissionName string, foundRelationName string, wildcardTypeName string, wildcardRelationName string) error { 311 return ErrWildcardUsedInArrow{ 312 error: fmt.Errorf("for arrow under permission `%s`: relation `%s#%s` includes wildcard type `%s` via relation `%s`: wildcard relations cannot be used on the left side of arrows", parentPermissionName, nsName, foundRelationName, wildcardTypeName, wildcardRelationName), 313 namespaceName: nsName, 314 parentPermissionName: parentPermissionName, 315 accessedRelationName: foundRelationName, 316 } 317 } 318 319 // NewMissingAllowedRelationsErr constructs an error indicating that type information is missing for a relation. 320 func NewMissingAllowedRelationsErr(nsName string, relationName string) error { 321 return ErrMissingAllowedRelations{ 322 error: fmt.Errorf("at least one allowed relation/permission is required to be defined for relation `%s`", relationName), 323 namespaceName: nsName, 324 relationName: relationName, 325 } 326 } 327 328 // NewTransitiveWildcardErr constructs an error indicating that a transitive wildcard exists. 329 func NewTransitiveWildcardErr(nsName string, relationName string, foundRelationNamespace string, foundRelationName string, wildcardTypeName string, wildcardRelationReference string) error { 330 return ErrTransitiveWildcard{ 331 error: fmt.Errorf("for relation `%s`: relation/permission `%s#%s` includes wildcard type `%s` via relation `%s`: wildcard relations cannot be transitively included", relationName, foundRelationNamespace, foundRelationName, wildcardTypeName, wildcardRelationReference), 332 namespaceName: nsName, 333 relationName: relationName, 334 } 335 } 336 337 // NewPermissionsCycleErr constructs an error indicating that a cycle exists amongst permissions. 338 func NewPermissionsCycleErr(nsName string, permissionNames []string) error { 339 return ErrPermissionsCycle{ 340 error: fmt.Errorf("under definition `%s`, there exists a cycle in permissions: %s", nsName, strings.Join(permissionNames, ", ")), 341 namespaceName: nsName, 342 permissionNames: permissionNames, 343 } 344 } 345 346 // NewUnusedCaveatParameterErr constructs indicating that a parameter was unused in a caveat expression. 347 func NewUnusedCaveatParameterErr(caveatName string, paramName string) error { 348 return ErrUnusedCaveatParameter{ 349 error: fmt.Errorf("parameter `%s` for caveat `%s` is unused", paramName, caveatName), 350 caveatName: caveatName, 351 paramName: paramName, 352 } 353 } 354 355 // asTypeError wraps another error in a type error. 356 func asTypeError(wrapped error) error { 357 if wrapped == nil { 358 return nil 359 } 360 361 var te TypeError 362 if errors.As(wrapped, &te) { 363 return wrapped 364 } 365 366 return TypeError{wrapped} 367 } 368 369 // TypeError wraps another error as a type error. 370 type TypeError struct { 371 error 372 } 373 374 func (err TypeError) Unwrap() error { 375 return err.error 376 } 377 378 var ( 379 _ sharederrors.UnknownNamespaceError = ErrNamespaceNotFound{} 380 _ sharederrors.UnknownRelationError = ErrRelationNotFound{} 381 )