1 // Copyright 2011 Google Inc. All rights reserved.
2 // Use of this source code is governed by the Apache 2.0
3 // license that can be found in the LICENSE file.
5 // Package internal provides support for package appengine.
7 // Programs should not use this package directly. Its API is not stable.
8 // Use packages appengine and appengine/* instead.
14 "github.com/golang/protobuf/proto"
16 remotepb "google.golang.org/appengine/internal/remote_api"
19 // errorCodeMaps is a map of service name to the error code map for the service.
20 var errorCodeMaps = make(map[string]map[int32]string)
22 // RegisterErrorCodeMap is called from API implementations to register their
23 // error code map. This should only be called from init functions.
24 func RegisterErrorCodeMap(service string, m map[int32]string) {
25 errorCodeMaps[service] = m
28 type timeoutCodeKey struct {
33 // timeoutCodes is the set of service+code pairs that represent timeouts.
34 var timeoutCodes = make(map[timeoutCodeKey]bool)
36 func RegisterTimeoutErrorCode(service string, code int32) {
37 timeoutCodes[timeoutCodeKey{service, code}] = true
40 // APIError is the type returned by appengine.Context's Call method
41 // when an API call fails in an API-specific way. This may be, for instance,
42 // a taskqueue API call failing with TaskQueueServiceError::UNKNOWN_QUEUE.
43 type APIError struct {
46 Code int32 // API-specific error code
49 func (e *APIError) Error() string {
52 return "APIError <empty>"
56 s := fmt.Sprintf("API error %d", e.Code)
57 if m, ok := errorCodeMaps[e.Service]; ok {
58 s += " (" + e.Service + ": " + m[e.Code] + ")"
60 // Shouldn't happen, but provide a bit more detail if it does.
61 s = e.Service + " " + s
69 func (e *APIError) IsTimeout() bool {
70 return timeoutCodes[timeoutCodeKey{e.Service, e.Code}]
73 // CallError is the type returned by appengine.Context's Call method when an
74 // API call fails in a generic way, such as RpcError::CAPABILITY_DISABLED.
75 type CallError struct {
78 // TODO: Remove this if we get a distinguishable error code.
82 func (e *CallError) Error() string {
84 switch remotepb.RpcError_ErrorCode(e.Code) {
85 case remotepb.RpcError_UNKNOWN:
87 case remotepb.RpcError_OVER_QUOTA:
89 case remotepb.RpcError_CAPABILITY_DISABLED:
90 msg = "Capability disabled"
91 case remotepb.RpcError_CANCELLED:
94 msg = fmt.Sprintf("Call error %d", e.Code)
96 s := msg + ": " + e.Detail
103 func (e *CallError) IsTimeout() bool {
107 // NamespaceMods is a map from API service to a function that will mutate an RPC request to attach a namespace.
108 // The function should be prepared to be called on the same message more than once; it should only modify the
109 // RPC request the first time.
110 var NamespaceMods = make(map[string]func(m proto.Message, namespace string))