/
githubmirror
/
client
Обзор
Документация
Войти
/
githubmirror
/
client
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
master
go/kbfs/libkbfs/errors.go
1 055 строк
32 KB
zoom-ua
modernize error handling with errors.As/Is (#29350)
25 июн 2026, 17:41
Не верифицирован
25 июн 2026, 17:41
e09e254
Код
Авторство
О чём код?
// Copyright 2016 Keybase Inc. All rights reserved. // Use of this source code is governed by a BSD // license that can be found in the LICENSE file. package libkbfs import ( "fmt" "time" "github.com/keybase/client/go/kbfs/data" "github.com/keybase/client/go/kbfs/idutil" "github.com/keybase/client/go/kbfs/kbfsblock" "github.com/keybase/client/go/kbfs/kbfscrypto" "github.com/keybase/client/go/kbfs/kbfsmd" "github.com/keybase/client/go/kbfs/tlf" "github.com/keybase/client/go/kbfs/tlfhandle" kbname "github.com/keybase/client/go/kbun" "github.com/keybase/client/go/protocol/keybase1" ) // WrapError simply wraps an error in a fmt.Stringer interface, so // that it can be reported. type WrapError struct { Err error } // String implements the fmt.Stringer interface for WrapError func (e WrapError) String() string { return e.Err.Error() } // InvalidBlockRefError indicates an invalid block reference was // encountered. type InvalidBlockRefError struct { ref data.BlockRef } func (e InvalidBlockRefError) Error() string { return fmt.Sprintf("Invalid block ref %s", e.ref) } // InvalidPathError indicates an invalid path was encountered. type InvalidPathError struct { p data.Path } // Error implements the error interface for InvalidPathError. func (e InvalidPathError) Error() string { return fmt.Sprintf("Invalid path %s", e.p.DebugString()) } // InvalidParentPathError indicates a path without a valid parent was // encountered. type InvalidParentPathError struct { p data.Path } // Error implements the error interface for InvalidParentPathError. func (e InvalidParentPathError) Error() string { return fmt.Sprintf("Path with invalid parent %s", e.p.DebugString()) } // DirNotEmptyError indicates that the user tried to unlink a // subdirectory that was not empty. type DirNotEmptyError struct { Name data.PathPartString } // Error implements the error interface for DirNotEmptyError func (e DirNotEmptyError) Error() string { return fmt.Sprintf("Directory %s is not empty and can't be removed", e.Name) } // TlfAccessError that the user tried to perform an unpermitted // operation on a top-level folder. type TlfAccessError struct { ID tlf.ID } // Error implements the error interface for TlfAccessError func (e TlfAccessError) Error() string { return fmt.Sprintf("Operation not permitted on folder %s", e.ID) } // RenameAcrossDirsError indicates that the user tried to do an atomic // rename across directories. type RenameAcrossDirsError struct { // ApplicationExecPath, if not empty, is the exec path of the application // that issued the rename. ApplicationExecPath string } // Error implements the error interface for RenameAcrossDirsError func (e RenameAcrossDirsError) Error() string { return "Cannot rename across directories" } // WriteUnsupportedError indicates an error when trying to write a file type WriteUnsupportedError struct { Filename string } // Error implements the error interface for WriteUnsupportedError func (e WriteUnsupportedError) Error() string { return fmt.Sprintf("Writing to %s is unsupported", e.Filename) } // WriteToReadonlyNodeError indicates an error when trying to write a // node that's marked as read-only. type WriteToReadonlyNodeError struct { Filename string } // Error implements the error interface for WriteToReadonlyNodeError func (e WriteToReadonlyNodeError) Error() string { return fmt.Sprintf("%s is read-only and writes are not allowed", e.Filename) } // UnsupportedOpInUnlinkedDirError indicates an error when trying to // create a file. type UnsupportedOpInUnlinkedDirError struct { Dirpath string } // Error implements the error interface for UnsupportedOpInUnlinkedDirError. func (e UnsupportedOpInUnlinkedDirError) Error() string { return fmt.Sprintf( "Operation is unsupported in unlinked directory %s", e.Dirpath) } // NewWriteUnsupportedError returns unsupported error trying to write a file func NewWriteUnsupportedError(filename string) error { return WriteUnsupportedError{ Filename: filename, } } // NeedSelfRekeyError indicates that the folder in question needs to // be rekeyed for the local device, and can be done so by one of the // other user's devices. type NeedSelfRekeyError struct { Tlf tlf.CanonicalName Err error } // Error implements the error interface for NeedSelfRekeyError func (e NeedSelfRekeyError) Error() string { return fmt.Sprintf("This device does not yet have read access to "+ "directory %s, log into Keybase from one of your other "+ "devices to grant access: %+v", tlfhandle.BuildCanonicalPathForTlfName(tlf.Private, e.Tlf), e.Err) } func (e NeedSelfRekeyError) Unwrap() error { return e.Err } // ToStatus exports error to status func (e NeedSelfRekeyError) ToStatus() keybase1.Status { kv := keybase1.StringKVPair{ Key: "Tlf", Value: string(e.Tlf), } return keybase1.Status{ Code: int(keybase1.StatusCode_SCNeedSelfRekey), Name: "SC_NEED_SELF_REKEY", Desc: e.Error(), Fields: []keybase1.StringKVPair{kv}, } } // NeedOtherRekeyError indicates that the folder in question needs to // be rekeyed for the local device, and can only done so by one of the // other users. type NeedOtherRekeyError struct { Tlf tlf.CanonicalName Err error } // Error implements the error interface for NeedOtherRekeyError func (e NeedOtherRekeyError) Error() string { return fmt.Sprintf("This device does not yet have read access to "+ "directory %s, ask one of the other directory participants to "+ "log into Keybase to grant you access automatically: %+v", tlfhandle.BuildCanonicalPathForTlfName(tlf.Private, e.Tlf), e.Err) } func (e NeedOtherRekeyError) Unwrap() error { return e.Err } // ToStatus exports error to status func (e NeedOtherRekeyError) ToStatus() keybase1.Status { kv := keybase1.StringKVPair{ Key: "Tlf", Value: string(e.Tlf), } return keybase1.Status{ Code: int(keybase1.StatusCode_SCNeedOtherRekey), Name: "SC_NEED_OTHER_REKEY", Desc: e.Error(), Fields: []keybase1.StringKVPair{kv}, } } // NotFileBlockError indicates that a file block was expected but a // block of a different type was found. // // ptr and branch should be filled in, but p may be empty. type NotFileBlockError struct { ptr data.BlockPointer branch data.BranchName p data.Path } func (e NotFileBlockError) Error() string { return fmt.Sprintf("The block at %s is not a file block (branch=%s, path=%s)", e.ptr, e.branch, e.p) } // NotDirBlockError indicates that a file block was expected but a // block of a different type was found. // // ptr and branch should be filled in, but p may be empty. type NotDirBlockError struct { ptr data.BlockPointer branch data.BranchName p data.Path } func (e NotDirBlockError) Error() string { return fmt.Sprintf("The block at %s is not a dir block (branch=%s, path=%s)", e.ptr, e.branch, e.p) } // NotFileError indicates that the user tried to perform a // file-specific operation on something that isn't a file. type NotFileError struct { path data.Path } // Error implements the error interface for NotFileError func (e NotFileError) Error() string { return fmt.Sprintf("%s is not a file (folder %s)", e.path, e.path.Tlf) } // NotDirError indicates that the user tried to perform a // dir-specific operation on something that isn't a directory. type NotDirError struct { path data.Path } // Error implements the error interface for NotDirError func (e NotDirError) Error() string { return fmt.Sprintf("%s is not a directory (folder %s)", e.path, e.path.Tlf) } // BlockDecodeError indicates that a block couldn't be decoded as // expected; probably it is the wrong type. type BlockDecodeError struct { decodeErr error } // Error implements the error interface for BlockDecodeError func (e BlockDecodeError) Error() string { return fmt.Sprintf("Decode error for a block: %v", e.decodeErr) } func (e BlockDecodeError) Unwrap() error { return e.decodeErr } // BadCryptoError indicates that KBFS performed a bad crypto operation. type BadCryptoError struct { ID kbfsblock.ID } // Error implements the error interface for BadCryptoError func (e BadCryptoError) Error() string { return fmt.Sprintf("Bad crypto for block %v", e.ID) } // BadCryptoMDError indicates that KBFS performed a bad crypto // operation, specifically on a MD object. type BadCryptoMDError struct { ID tlf.ID } // Error implements the error interface for BadCryptoMDError func (e BadCryptoMDError) Error() string { return fmt.Sprintf("Bad crypto for the metadata of directory %v", e.ID) } // BadMDError indicates that the system is storing corrupt MD object // for the given TLF ID. type BadMDError struct { ID tlf.ID } // Error implements the error interface for BadMDError func (e BadMDError) Error() string { return fmt.Sprintf("Wrong format for metadata for directory %v", e.ID) } // MDMismatchError indicates an inconsistent or unverifiable MD object // for the given top-level folder. type MDMismatchError struct { Revision kbfsmd.Revision Dir string TlfID tlf.ID Err error } // Error implements the error interface for MDMismatchError func (e MDMismatchError) Error() string { return fmt.Sprintf("Could not verify metadata (revision=%d) for directory %s (id=%s): %s", e.Revision, e.Dir, e.TlfID, e.Err) } func (e MDMismatchError) Unwrap() error { return e.Err } // NoSuchMDError indicates that there is no MD object for the given // folder, revision, and merged status. type NoSuchMDError struct { Tlf tlf.ID Rev kbfsmd.Revision BID kbfsmd.BranchID } // Error implements the error interface for NoSuchMDError func (e NoSuchMDError) Error() string { return fmt.Sprintf("Couldn't get metadata for folder %v, revision %d, "+ "%s", e.Tlf, e.Rev, e.BID) } // InvalidDataVersionError indicates that an invalid data version was // used. type InvalidDataVersionError struct { DataVer data.Ver } // Error implements the error interface for InvalidDataVersionError. func (e InvalidDataVersionError) Error() string { return fmt.Sprintf("Invalid data version %d", int(e.DataVer)) } // NewDataVersionError indicates that the data at the given path has // been written using a new data version that our client doesn't // understand. type NewDataVersionError struct { path data.Path DataVer data.Ver } // Error implements the error interface for NewDataVersionError. func (e NewDataVersionError) Error() string { return fmt.Sprintf( "The data at path %s is of a version (%d) that we can't read "+ "(in folder %s)", e.path, e.DataVer, e.path.Tlf) } // OutdatedVersionError indicates that we have encountered some new // data version we don't understand, and the user should be prompted // to upgrade. type OutdatedVersionError struct{} // Error implements the error interface for OutdatedVersionError. func (e OutdatedVersionError) Error() string { return "Your software is out of date, and cannot read this data. " + "Please use `keybase update check` to upgrade your software." } // InvalidVersionError indicates that we have encountered some new data version // we don't understand, and we don't know how to handle it. type InvalidVersionError struct { msg string } // Error implements the error interface for InvalidVersionError. func (e InvalidVersionError) Error() string { if e.msg != "" { return e.msg } return "The version provided is not valid." } // TooLowByteCountError indicates that size of a block is smaller than // the expected size. type TooLowByteCountError struct { ExpectedMinByteCount int ByteCount int } // Error implements the error interface for TooLowByteCountError func (e TooLowByteCountError) Error() string { return fmt.Sprintf("Expected at least %d bytes, got %d bytes", e.ExpectedMinByteCount, e.ByteCount) } // InconsistentEncodedSizeError is raised when a dirty block has a // non-zero encoded size. type InconsistentEncodedSizeError struct { info data.BlockInfo } // Error implements the error interface for InconsistentEncodedSizeError func (e InconsistentEncodedSizeError) Error() string { return fmt.Sprintf("Block pointer to dirty block %v with non-zero "+ "encoded size = %d bytes", e.info.ID, e.info.EncodedSize) } // MDWriteNeededInRequest indicates that the system needs MD write // permissions to successfully complete an operation, so it should // retry in mdWrite mode. type MDWriteNeededInRequest struct{} // Error implements the error interface for MDWriteNeededInRequest func (e MDWriteNeededInRequest) Error() string { return "This request needs MD write access, but doesn't have it." } // VerifyingKeyNotFoundError indicates that a verifying key matching // the given one couldn't be found. type VerifyingKeyNotFoundError struct { key kbfscrypto.VerifyingKey } func (e VerifyingKeyNotFoundError) Error() string { return fmt.Sprintf("Could not find verifying key %s", e.key) } // UnverifiableTlfUpdateError indicates that a MD update could not be // verified. type UnverifiableTlfUpdateError struct { Tlf string User kbname.NormalizedUsername Err error } // Error implements the error interface for UnverifiableTlfUpdateError. func (e UnverifiableTlfUpdateError) Error() string { return fmt.Sprintf("%s was last written by an unknown device claiming "+ "to belong to user %s. The device has possibly been revoked by the "+ "user. Use `keybase log send` to file an issue with the Keybase "+ "admins.", e.Tlf, e.User) } // KeyCacheMissError indicates that a key matching the given TLF ID // and key generation wasn't found in cache. type KeyCacheMissError struct { tlf tlf.ID keyGen kbfsmd.KeyGen } // Error implements the error interface for KeyCacheMissError. func (e KeyCacheMissError) Error() string { return fmt.Sprintf("Could not find key with tlf=%s, keyGen=%d", e.tlf, e.keyGen) } // KeyCacheHitError indicates that a key matching the given TLF ID // and key generation was found in cache but the object type was unknown. type KeyCacheHitError struct { tlf tlf.ID keyGen kbfsmd.KeyGen } // Error implements the error interface for KeyCacheHitError. func (e KeyCacheHitError) Error() string { return fmt.Sprintf("Invalid key with tlf=%s, keyGen=%d", e.tlf, e.keyGen) } // NoKeysError indicates that no keys were provided for a decryption allowing // multiple device keys type NoKeysError struct{} func (e NoKeysError) Error() string { return "No keys provided" } // WrongOpsError indicates that an unexpected path got passed into a // FolderBranchOps instance type WrongOpsError struct { nodeFB data.FolderBranch opsFB data.FolderBranch } // Error implements the error interface for WrongOpsError. func (e WrongOpsError) Error() string { return fmt.Sprintf("Ops for folder %v, branch %s, was given path %s, "+ "branch %s", e.opsFB.Tlf, e.opsFB.Branch, e.nodeFB.Tlf, e.nodeFB.Branch) } // NodeNotFoundError indicates that we tried to find a node for the // given BlockPointer and failed. type NodeNotFoundError struct { ptr data.BlockPointer } // Error implements the error interface for NodeNotFoundError. func (e NodeNotFoundError) Error() string { return fmt.Sprintf("No node found for pointer %v", e.ptr) } // ParentNodeNotFoundError indicates that we tried to update a Node's // parent with a BlockPointer that we don't yet know about. type ParentNodeNotFoundError struct { parent data.BlockRef } // Error implements the error interface for ParentNodeNotFoundError. func (e ParentNodeNotFoundError) Error() string { return fmt.Sprintf("No such parent node found for %v", e.parent) } // EmptyNameError indicates that the user tried to use an empty name // for the given BlockRef. type EmptyNameError struct { ref data.BlockRef } // Error implements the error interface for EmptyNameError. func (e EmptyNameError) Error() string { return fmt.Sprintf("Cannot use empty name for %v", e.ref) } // KeyHalfMismatchError is returned when the key server doesn't return the expected key half. type KeyHalfMismatchError struct { Expected kbfscrypto.TLFCryptKeyServerHalfID Actual kbfscrypto.TLFCryptKeyServerHalfID } // Error implements the error interface for KeyHalfMismatchError. func (e KeyHalfMismatchError) Error() string { return fmt.Sprintf("Key mismatch, expected ID: %s, actual ID: %s", e.Expected, e.Actual) } // MDServerDisconnected indicates the MDServer has been disconnected for clients waiting // on an update channel. type MDServerDisconnected struct{} // Error implements the error interface for MDServerDisconnected. func (e MDServerDisconnected) Error() string { return "MDServer is disconnected" } // MDUpdateInvertError indicates that we tried to apply a revision that // was not the next in line. type MDUpdateInvertError struct { rev kbfsmd.Revision curr kbfsmd.Revision } // Error implements the error interface for MDUpdateInvertError. func (e MDUpdateInvertError) Error() string { return fmt.Sprintf("MD revision %d isn't next in line for our "+ "current revision %d while inverting", e.rev, e.curr) } // NotPermittedWhileDirtyError indicates that some operation failed // because of outstanding dirty files, and may be retried later. type NotPermittedWhileDirtyError struct{} // Error implements the error interface for NotPermittedWhileDirtyError. func (e NotPermittedWhileDirtyError) Error() string { return "Not permitted while writes are dirty" } // NoChainFoundError indicates that a conflict resolution chain // corresponding to the given pointer could not be found. type NoChainFoundError struct { ptr data.BlockPointer } // Error implements the error interface for NoChainFoundError. func (e NoChainFoundError) Error() string { return fmt.Sprintf("No chain found for %v", e.ptr) } // DisallowedPrefixError indicates that the user attempted to create // an entry using a name with a disallowed prefix. type DisallowedPrefixError struct { name data.PathPartString prefix string } // Error implements the error interface for DisallowedPrefixError. func (e DisallowedPrefixError) Error() string { return fmt.Sprintf("Cannot create %s because it has the prefix %s", e.name, e.prefix) } // DisallowedNameError indicates that the user attempted to create an // entry using a disallowed name. It includes the plaintext name on // purpose, for clarity in the error message. type DisallowedNameError struct { name string } // Error implements the error interface for DisallowedNameError. func (e DisallowedNameError) Error() string { return fmt.Sprintf("Cannot create \"%s\" because it is a disallowed name", e.name) } // NameTooLongError indicates that the user tried to write a directory // entry name that would be bigger than KBFS's supported size. type NameTooLongError struct { name string maxAllowedBytes uint32 } // Error implements the error interface for NameTooLongError. func (e NameTooLongError) Error() string { return fmt.Sprintf("New directory entry name %s has more than the maximum "+ "allowed number of bytes (%d)", e.name, e.maxAllowedBytes) } // NoCurrentSessionExpectedError is the error text that will get // converted into a NoCurrentSessionError. var NoCurrentSessionExpectedError = "no current session" // RekeyPermissionError indicates that the user tried to rekey a // top-level folder in a manner inconsistent with their permissions. type RekeyPermissionError struct { User kbname.NormalizedUsername Dir string } // Error implements the error interface for RekeyPermissionError func (e RekeyPermissionError) Error() string { return fmt.Sprintf("%s is trying to rekey directory %s in a manner "+ "inconsistent with their role", e.User, e.Dir) } // NewRekeyPermissionError constructs a RekeyPermissionError for the given // directory and user. func NewRekeyPermissionError( dir *tlfhandle.Handle, username kbname.NormalizedUsername, ) error { dirname := dir.GetCanonicalPath() return RekeyPermissionError{username, dirname} } // RekeyIncompleteError is returned when a rekey is partially done but // needs a writer to finish it. type RekeyIncompleteError struct{} func (e RekeyIncompleteError) Error() string { return "Rekey did not complete due to insufficient user permissions" } // TimeoutError is just a replacement for context.DeadlineExceeded // with a more friendly error string. type TimeoutError struct{} func (e TimeoutError) Error() string { return "Operation timed out" } // InvalidOpError is returned when an operation is called that isn't supported // by the current implementation. type InvalidOpError struct { op string } func (e InvalidOpError) Error() string { return fmt.Sprintf("Invalid operation: %s", e.op) } // NoSuchFolderListError indicates that the user tried to access a // subdirectory of /keybase that doesn't exist. type NoSuchFolderListError struct { Name string NameToLog string PrivName string PubName string } // Error implements the error interface for NoSuchFolderListError func (e NoSuchFolderListError) Error() string { return fmt.Sprintf("/keybase/%s is not a Keybase folder. "+ "All folders begin with /keybase/%s or /keybase/%s.", e.NameToLog, e.PrivName, e.PubName) } // UnexpectedUnmergedPutError indicates that we tried to do an // unmerged put when that was disallowed. type UnexpectedUnmergedPutError struct{} // Error implements the error interface for UnexpectedUnmergedPutError func (e UnexpectedUnmergedPutError) Error() string { return "Unmerged puts are not allowed" } // NoSuchTlfHandleError indicates we were unable to resolve a folder // ID to a folder handle. type NoSuchTlfHandleError struct { ID tlf.ID } // Error implements the error interface for NoSuchTlfHandleError func (e NoSuchTlfHandleError) Error() string { return fmt.Sprintf("Folder handle for %s not found", e.ID) } // NoSuchTlfIDError indicates we were unable to resolve a folder // handle to a folder ID. type NoSuchTlfIDError struct { handle *tlfhandle.Handle } // Error implements the error interface for NoSuchTlfIDError func (e NoSuchTlfIDError) Error() string { return fmt.Sprintf("Folder ID for %s not found", e.handle.GetCanonicalPath()) } // IncompatibleHandleError indicates that somethine tried to update // the head of a TLF with a RootMetadata with an incompatible handle. type IncompatibleHandleError struct { oldName tlf.CanonicalName partiallyResolvedOldName tlf.CanonicalName newName tlf.CanonicalName } func (e IncompatibleHandleError) Error() string { return fmt.Sprintf( "old head %q resolves to %q instead of new head %q", e.oldName, e.partiallyResolvedOldName, e.newName) } // UnmergedError indicates that fbo is on an unmerged local revision type UnmergedError struct{} // Error implements the error interface for UnmergedError. func (e UnmergedError) Error() string { return "fbo is on an unmerged local revision" } // ExclOnUnmergedError happens when an operation with O_EXCL set when fbo is on // an unmerged local revision type ExclOnUnmergedError struct{} // Error implements the error interface for ExclOnUnmergedError. func (e ExclOnUnmergedError) Error() string { return "an operation with O_EXCL set is called but fbo is on an unmerged local version" } // OverQuotaWarning indicates that the user is over their quota, and // is being slowed down by the server. type OverQuotaWarning struct { UsageBytes int64 LimitBytes int64 } // Error implements the error interface for OverQuotaWarning. func (w OverQuotaWarning) Error() string { return fmt.Sprintf("You are using %d bytes, and your plan limits you "+ "to %d bytes. Please delete some data.", w.UsageBytes, w.LimitBytes) } // OpsCantHandleFavorite means that folderBranchOps wasn't able to // deal with a favorites request. type OpsCantHandleFavorite struct { Msg string } // Error implements the error interface for OpsCantHandleFavorite. func (e OpsCantHandleFavorite) Error() string { return fmt.Sprintf("Couldn't handle the favorite operation: %s", e.Msg) } // RekeyConflictError indicates a conflict happened while trying to rekey. type RekeyConflictError struct { Err error } // Error implements the error interface for RekeyConflictError. func (e RekeyConflictError) Error() string { return fmt.Sprintf("Conflict during a rekey, not retrying: %v", e.Err) } func (e RekeyConflictError) Unwrap() error { return e.Err } // UnmergedSelfConflictError indicates that we hit a conflict on the // unmerged branch, so a previous MD PutUnmerged we thought had // failed, had actually succeeded. type UnmergedSelfConflictError struct { Err error } // Error implements the error interface for UnmergedSelfConflictError. func (e UnmergedSelfConflictError) Error() string { return fmt.Sprintf("Unmerged self conflict: %v", e.Err) } func (e UnmergedSelfConflictError) Unwrap() error { return e.Err } // blockNonExistentError is returned when a block doesn't exist. This // is a generic error, suitable for use by non-server types, whereas // kbfsblock.ServerErrorBlockNonExistent is used only by servers. type blockNonExistentError struct { id kbfsblock.ID } func (e blockNonExistentError) Error() string { return fmt.Sprintf("block %s does not exist", e.id) } // NoMergedMDError indicates that no MDs for this folder have been // created yet. type NoMergedMDError struct { tlf tlf.ID } // Error implements the error interface for NoMergedMDError. func (e NoMergedMDError) Error() string { return fmt.Sprintf("No MD yet for TLF %s", e.tlf) } // InvalidFavoritesOpError indicates an unknown FavoritesOp has been provided. type InvalidFavoritesOpError struct{} // Error implements the error interface for InvalidFavoritesOpError. func (InvalidFavoritesOpError) Error() string { return "invalid FavoritesOp" } // DiskCacheClosedError indicates that the disk cache has been // closed, and thus isn't accepting any more operations. type DiskCacheClosedError struct { op string } // Error implements the error interface for DiskCacheClosedError. func (e DiskCacheClosedError) Error() string { return fmt.Sprintf("Error performing %s operation: the disk cache is "+ "closed", e.op) } // DiskCacheStartingError indicates that the disk cache has not yet started, so // it isn't yet accepting operations. type DiskCacheStartingError struct { op string } // Error implements the error interface for DiskCacheStartingError. func (e DiskCacheStartingError) Error() string { return fmt.Sprintf("Error performing %s operation: the disk cache is "+ "still starting", e.op) } // NoUpdatesWhileDirtyError indicates that updates aren't being // accepted while a TLF is locally dirty. type NoUpdatesWhileDirtyError struct{} // Error implements the error interface for NoUpdatesWhileDirtyError. func (e NoUpdatesWhileDirtyError) Error() string { return "Ignoring MD updates while writes are dirty" } // Disk Cache Errors const ( // StatusCodeDiskBlockCacheError is a generic disk cache error. StatusCodeDiskBlockCacheError = 0x666 // StatusCodeDiskMDCacheError is a generic disk cache error. StatusCodeDiskMDCacheError = 0x667 // StatusCodeDiskQuotaCacheError is a generic disk cache error. StatusCodeDiskQuotaCacheError = 0x668 ) // DiskBlockCacheError is a generic disk cache error. type DiskBlockCacheError struct { Msg string } func newDiskBlockCacheError(err error) DiskBlockCacheError { return DiskBlockCacheError{err.Error()} } // ToStatus implements the ExportableError interface for DiskBlockCacheError. func (e DiskBlockCacheError) ToStatus() (s keybase1.Status) { s.Code = StatusCodeDiskBlockCacheError s.Name = "DISK_BLOCK_CACHE_ERROR" s.Desc = e.Msg return } // Error implements the Error interface for DiskBlockCacheError. func (e DiskBlockCacheError) Error() string { return "DiskBlockCacheError{" + e.Msg + "}" } // DiskMDCacheError is a generic disk cache error. type DiskMDCacheError struct { Msg string } // ToStatus implements the ExportableError interface for DiskMDCacheError. func (e DiskMDCacheError) ToStatus() (s keybase1.Status) { s.Code = StatusCodeDiskMDCacheError s.Name = "DISK_MD_CACHE_ERROR" s.Desc = e.Msg return } // Error implements the Error interface for DiskMDCacheError. func (e DiskMDCacheError) Error() string { return "DiskMDCacheError{" + e.Msg + "}" } // DiskQuotaCacheError is a generic disk cache error. type DiskQuotaCacheError struct { Msg string } // ToStatus implements the ExportableError interface for DiskQuotaCacheError. func (e DiskQuotaCacheError) ToStatus() (s keybase1.Status) { s.Code = StatusCodeDiskQuotaCacheError s.Name = "DISK_QUOTA_CACHE_ERROR" s.Desc = e.Msg return } // Error implements the Error interface for DiskQuotaCacheError. func (e DiskQuotaCacheError) Error() string { return "DiskQuotaCacheError{" + e.Msg + "}" } // RevokedDeviceVerificationError indicates that the user is trying to // verify a key that has been revoked. It includes useful information // about the revocation, so the code receiving the error can check if // the device was valid at the time of the data being checked. type RevokedDeviceVerificationError struct { info idutil.RevokedKeyInfo } // Error implements the Error interface for RevokedDeviceVerificationError. func (e RevokedDeviceVerificationError) Error() string { return fmt.Sprintf("Device was revoked at time %s, root seqno %d", e.info.Time.Time().Format(time.RFC3339Nano), e.info.MerkleRoot.Seqno) } // MDWrittenAfterRevokeError indicates that we failed to verify an MD // revision because it was written after the last valid revision that // the corresponding device could have written. type MDWrittenAfterRevokeError struct { tlfID tlf.ID revBad kbfsmd.Revision revLimit kbfsmd.Revision verifyingKey kbfscrypto.VerifyingKey } // Error implements the Error interface for MDWrittenAfterRevokeError. func (e MDWrittenAfterRevokeError) Error() string { return fmt.Sprintf("Failed to verify revision %d of folder %s by key %s; "+ "last valid revision would have been %d", e.revBad, e.tlfID, e.verifyingKey, e.revLimit) } // RevGarbageCollectedError indicates that the user is trying to // access a revision that's already been garbage-collected. type RevGarbageCollectedError struct { rev kbfsmd.Revision lastGCRev kbfsmd.Revision } // Error implements the Error interface for RevGarbageCollectedError. func (e RevGarbageCollectedError) Error() string { return fmt.Sprintf("Requested revision %d has already been garbage "+ "collected (last GC'd rev=%d)", e.rev, e.lastGCRev) } // FolderNotResetOnServer indicates that a folder can't be reset by // the user, because it hasn't yet been reset on the mdserver. type FolderNotResetOnServer struct { h *tlfhandle.Handle } // Error implements the Error interface for FolderNotResetOnServer. func (e FolderNotResetOnServer) Error() string { return fmt.Sprintf("Folder %s is not yet reset on the server; "+ "contact Keybase for help", e.h.GetCanonicalPath()) } // OfflineArchivedError indicates trying to access archived data while // offline. type OfflineArchivedError struct { h *tlfhandle.Handle } // Error implements the Error interface for OfflineArchivedError. func (e OfflineArchivedError) Error() string { return fmt.Sprintf("Archived data from %s is not available while offline", e.h.GetCanonicalPath()) } // OfflineUnsyncedError indicates trying to access unsynced data while // offline. type OfflineUnsyncedError struct { h *tlfhandle.Handle } // Error implements the Error interface for OfflineUnsyncedError. func (e OfflineUnsyncedError) Error() string { return fmt.Sprintf("Unsynced data from %s is not available while offline", e.h.GetCanonicalPath()) } // NextMDNotCachedError indicates we haven't cached the next MD after // the given Merkle seqno. type NextMDNotCachedError struct { TlfID tlf.ID RootSeqno keybase1.Seqno } // Error implements the Error interface for NextMDNotCachedError. func (e NextMDNotCachedError) Error() string { return fmt.Sprintf("The MD following %d for folder %s is not cached", e.RootSeqno, e.TlfID) } // DiskCacheTooFullForBlockError indicates that the disk cache is too // full to fetch a block requested with the `StopIfFull` action type. type DiskCacheTooFullForBlockError struct { Ptr data.BlockPointer Action BlockRequestAction } // Error implements the Error interface for DiskCacheTooFullForBlockError. func (e DiskCacheTooFullForBlockError) Error() string { return fmt.Sprintf( "Disk cache too full for block %s requested with action %s", e.Ptr, e.Action) } // NonExistentTeamForHandleError indicates that we're trying to create // a TLF for a handle that has no corresponding implicit team yet. // Likely a writer needs to create the implicit team first. type NonExistentTeamForHandleError struct { h *tlfhandle.Handle } // Error implements the Error interface for NonExistentTeamForHandleError. func (e NonExistentTeamForHandleError) Error() string { return fmt.Sprintf("Can't create TLF ID for non-team-backed handle %s", e.h.GetCanonicalPath()) }