File: error.go

package info (click to toggle)
golang-github-ovn-org-libovsdb 0.7.0-1
  • links: PTS, VCS
  • area: main
  • in suites: experimental, forky, sid, trixie
  • size: 1,440 kB
  • sloc: makefile: 52; sh: 14
file content (373 lines) | stat: -rw-r--r-- 9,660 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
package ovsdb

import "fmt"

const (
	referentialIntegrityViolation = "referential integrity violation"
	constraintViolation           = "constraint violation"
	resourcesExhausted            = "resources exhausted"
	ioError                       = "I/O error"
	duplicateUUIDName             = "duplicate uuid name"
	domainError                   = "domain error"
	rangeError                    = "range error"
	timedOut                      = "timed out"
	notSupported                  = "not supported"
	aborted                       = "aborted"
	notOwner                      = "not owner"
)

// errorFromResult returns an specific OVSDB error type from
// an OperationResult
func errorFromResult(op *Operation, r OperationResult) OperationError {
	if r.Error == "" {
		return nil
	}
	switch r.Error {
	case referentialIntegrityViolation:
		return &ReferentialIntegrityViolation{r.Details, op}
	case constraintViolation:
		return &ConstraintViolation{r.Details, op}
	case resourcesExhausted:
		return &ResourcesExhausted{r.Details, op}
	case ioError:
		return &IOError{r.Details, op}
	case duplicateUUIDName:
		return &DuplicateUUIDName{r.Details, op}
	case domainError:
		return &DomainError{r.Details, op}
	case rangeError:
		return &RangeError{r.Details, op}
	case timedOut:
		return &TimedOut{r.Details, op}
	case notSupported:
		return &NotSupported{r.Details, op}
	case aborted:
		return &Aborted{r.Details, op}
	case notOwner:
		return &NotOwner{r.Details, op}
	default:
		return &Error{r.Error, r.Details, op}
	}
}

func ResultFromError(err error) OperationResult {
	if err == nil {
		panic("Program error: passed nil error to resultFromError")
	}
	switch e := err.(type) {
	case *ReferentialIntegrityViolation:
		return OperationResult{Error: referentialIntegrityViolation, Details: e.details}
	case *ConstraintViolation:
		return OperationResult{Error: constraintViolation, Details: e.details}
	case *ResourcesExhausted:
		return OperationResult{Error: resourcesExhausted, Details: e.details}
	case *IOError:
		return OperationResult{Error: ioError, Details: e.details}
	case *DuplicateUUIDName:
		return OperationResult{Error: duplicateUUIDName, Details: e.details}
	case *DomainError:
		return OperationResult{Error: domainError, Details: e.details}
	case *RangeError:
		return OperationResult{Error: rangeError, Details: e.details}
	case *TimedOut:
		return OperationResult{Error: timedOut, Details: e.details}
	case *NotSupported:
		return OperationResult{Error: notSupported, Details: e.details}
	case *Aborted:
		return OperationResult{Error: aborted, Details: e.details}
	case *NotOwner:
		return OperationResult{Error: notOwner, Details: e.details}
	default:
		return OperationResult{Error: e.Error()}
	}
}

// CheckOperationResults checks whether the provided operation was a success
// If the operation was a success, it will return nil, nil
// If the operation failed, due to a error committing the transaction it will
// return nil, error.
// Finally, in the case where one or more of the operations in the transaction
// failed, we return []OperationErrors, error
// Within []OperationErrors, the OperationErrors.Index() corresponds to the same index in
// the original Operations struct. You may also perform type assertions against
// the error so the caller can decide how best to handle it
func CheckOperationResults(result []OperationResult, ops []Operation) ([]OperationError, error) {
	// this shouldn't happen, but we'll cover the case to be certain
	if len(result) < len(ops) {
		return nil, fmt.Errorf("ovsdb transaction error. %d operations submitted but only %d results received", len(ops), len(result))
	}
	var errs []OperationError
	for i, op := range result {
		// RFC 7047: if all of the operations succeed, but the results cannot
		// be committed, then "result" will have one more element than "params",
		// with the additional element being an <error>.
		if i >= len(ops) {
			return errs, errorFromResult(nil, op)
		}
		if err := errorFromResult(&ops[i], op); err != nil {
			errs = append(errs, err)
		}
	}
	if len(errs) > 0 {
		return errs, fmt.Errorf("%d ovsdb operations failed", len(errs))
	}
	return nil, nil
}

// OperationError represents an error that occurred as part of an
// OVSDB Operation
type OperationError interface {
	error
	// Operation is a pointer to the operation which caused the error
	Operation() *Operation
}

// ReferentialIntegrityViolation is explained in RFC 7047 4.1.3
type ReferentialIntegrityViolation struct {
	details   string
	operation *Operation
}

func NewReferentialIntegrityViolation(details string) *ReferentialIntegrityViolation {
	return &ReferentialIntegrityViolation{details: details}
}

// Error implements the error interface
func (e *ReferentialIntegrityViolation) Error() string {
	msg := referentialIntegrityViolation
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *ReferentialIntegrityViolation) Operation() *Operation {
	return e.operation
}

// ConstraintViolation is described in RFC 7047: 4.1.3
type ConstraintViolation struct {
	details   string
	operation *Operation
}

func NewConstraintViolation(details string) *ConstraintViolation {
	return &ConstraintViolation{details: details}
}

// Error implements the error interface
func (e *ConstraintViolation) Error() string {
	msg := constraintViolation
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *ConstraintViolation) Operation() *Operation {
	return e.operation
}

// ResourcesExhausted is described in RFC 7047: 4.1.3
type ResourcesExhausted struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *ResourcesExhausted) Error() string {
	msg := resourcesExhausted
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *ResourcesExhausted) Operation() *Operation {
	return e.operation
}

// IOError is described in RFC7047: 4.1.3
type IOError struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *IOError) Error() string {
	msg := ioError
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *IOError) Operation() *Operation {
	return e.operation
}

// DuplicateUUIDName is described in RFC7047 5.2.1
type DuplicateUUIDName struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *DuplicateUUIDName) Error() string {
	msg := duplicateUUIDName
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *DuplicateUUIDName) Operation() *Operation {
	return e.operation
}

// DomainError is described in RFC 7047: 5.2.4
type DomainError struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *DomainError) Error() string {
	msg := domainError
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *DomainError) Operation() *Operation {
	return e.operation
}

// RangeError is described in RFC 7047: 5.2.4
type RangeError struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *RangeError) Error() string {
	msg := rangeError
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *RangeError) Operation() *Operation {
	return e.operation
}

// TimedOut is described in RFC 7047: 5.2.6
type TimedOut struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *TimedOut) Error() string {
	msg := timedOut
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *TimedOut) Operation() *Operation {
	return e.operation
}

// NotSupported is described in RFC 7047: 5.2.7
type NotSupported struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *NotSupported) Error() string {
	msg := notSupported
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *NotSupported) Operation() *Operation {
	return e.operation
}

// Aborted is described in RFC 7047: 5.2.8
type Aborted struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *Aborted) Error() string {
	msg := aborted
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *Aborted) Operation() *Operation {
	return e.operation
}

// NotOwner is described in RFC 7047: 5.2.9
type NotOwner struct {
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *NotOwner) Error() string {
	msg := notOwner
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *NotOwner) Operation() *Operation {
	return e.operation
}

// Error is a generic OVSDB Error type that implements the
// OperationError and error interfaces
type Error struct {
	name      string
	details   string
	operation *Operation
}

// Error implements the error interface
func (e *Error) Error() string {
	msg := e.name
	if e.details != "" {
		msg += ": " + e.details
	}
	return msg
}

// Operation implements the OperationError interface
func (e *Error) Operation() *Operation {
	return e.operation
}