MCPcopy Create free account
hub / github.com/couchbase/sync_gateway / documentRevisionForRequest

Method documentRevisionForRequest

db/crud.go:374–431  ·  view source on GitHub ↗

documentRevisionForRequest processes the given DocumentRevision and returns a version of it for a given client request, depending on access, deleted, etc.

(ctx context.Context, docID string, revision DocumentRevision, revID *string, cv *Version, maxHistory int, historyFrom []string)

Source from the content-addressed store, hash-verified

372
373// documentRevisionForRequest processes the given DocumentRevision and returns a version of it for a given client request, depending on access, deleted, etc.
374func (db *DatabaseCollectionWithUser) documentRevisionForRequest(ctx context.Context, docID string, revision DocumentRevision, revID *string, cv *Version, maxHistory int, historyFrom []string) (DocumentRevision, error) {
375 // ensure only one of cv or revID is specified
376 if cv != nil && revID != nil {
377 return DocumentRevision{}, fmt.Errorf("must have one of cv or revID in documentRevisionForRequest (had cv=%v revID=%v)", cv, revID)
378 }
379 var requestedVersion string
380 if revID != nil {
381 requestedVersion = *revID
382 } else if cv != nil {
383 requestedVersion = cv.String()
384 }
385
386 if revision.BodyBytes == nil {
387 if db.ForceAPIForbiddenErrors() {
388 base.InfofCtx(ctx, base.KeyCRUD, "Doc: %s %s is missing", base.UD(docID), base.MD(requestedVersion))
389 return DocumentRevision{}, ErrForbidden
390 }
391 return DocumentRevision{}, ErrMissing
392 }
393
394 db.collectionStats.NumDocReads.Add(1)
395 db.collectionStats.DocReadsBytes.Add(int64(len(revision.BodyBytes)))
396
397 // RequestedHistory is the _revisions returned in the body. Avoids mutating revision.History, in case it's needed
398 // during attachment processing below
399 requestedHistory := revision.History
400 if maxHistory == 0 {
401 requestedHistory = nil
402 }
403 if requestedHistory != nil {
404 _, requestedHistory = trimEncodedRevisionsToAncestor(ctx, requestedHistory, historyFrom, maxHistory)
405 }
406
407 isAuthorized, redactedRevision := db.authorizeUserForChannels(docID, revision.RevID, cv, revision.Channels, revision.Deleted, requestedHistory)
408 if !isAuthorized {
409 // client just wanted active revision, not a specific one
410 if requestedVersion == "" {
411 return DocumentRevision{}, ErrForbidden
412 }
413 if db.ForceAPIForbiddenErrors() {
414 base.InfofCtx(ctx, base.KeyCRUD, "Not authorized to view doc: %s %s", base.UD(docID), base.MD(requestedVersion))
415 return DocumentRevision{}, ErrForbidden
416 }
417 return redactedRevision, nil
418 }
419
420 // If the revision is a removal cache entry (no body), but the user has access to that removal, then just
421 // return 404 missing to indicate that the body of the revision is no longer available.
422 if revision.Removed {
423 return DocumentRevision{}, ErrMissing
424 }
425
426 if revision.Deleted && requestedVersion == "" {
427 return DocumentRevision{}, ErrDeleted
428 }
429
430 return revision, nil
431}

Callers 2

getRevMethod · 0.95
GetCVMethod · 0.95

Calls 9

InfofCtxFunction · 0.92
UDFunction · 0.92
MDFunction · 0.92
ErrorfMethod · 0.80
StringMethod · 0.65
AddMethod · 0.45

Tested by

no test coverage detected