github.com/letsencrypt/trillian@v1.1.2-0.20180615153820-ae375a99d36a/crypto/keys/handlers.go (about) 1 // Copyright 2017 Google Inc. All Rights Reserved. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package keys 16 17 import ( 18 "context" 19 "crypto" 20 "fmt" 21 22 "github.com/golang/glog" 23 "github.com/golang/protobuf/proto" 24 ) 25 26 // ProtoHandler uses the information in a protobuf message to obtain a crypto.Signer. 27 // For example, the protobuf message may contain a key or identify where a key can be found. 28 type ProtoHandler func(context.Context, proto.Message) (crypto.Signer, error) 29 30 // handlers convert a protobuf message into a crypto.Signer. 31 var handlers = make(map[string]ProtoHandler) 32 33 // RegisterHandler enables transformation of protobuf messages of the same 34 // type as keyProto into crypto.Signer by invoking the provided handler. 35 // The keyProto need only be an empty example of the type of protobuf message that 36 // the handler can process - only its type is examined. 37 // If a handler for this type of protobuf message has already been added, it will 38 // be replaced. 39 func RegisterHandler(keyProto proto.Message, handler ProtoHandler) { 40 keyProtoType := proto.MessageName(keyProto) 41 42 if _, alreadyExists := handlers[keyProtoType]; alreadyExists { 43 glog.Warningf("Overridding ProtoHandler for protobuf %q", keyProtoType) 44 } 45 46 handlers[keyProtoType] = handler 47 } 48 49 // UnregisterHandler removes a previously-added protobuf message handler. 50 // See RegisterHandler(). 51 func UnregisterHandler(keyProto proto.Message) { 52 delete(handlers, proto.MessageName(keyProto)) 53 } 54 55 // NewSigner uses a registered ProtoHandler (see RegisterHandler()) to convert a 56 // protobuf message into a crypto.Signer. 57 // If there is no ProtoHandler registered for this type of protobuf message, an 58 // error will be returned. 59 func NewSigner(ctx context.Context, keyProto proto.Message) (crypto.Signer, error) { 60 keyProtoType := proto.MessageName(keyProto) 61 62 if handler, ok := handlers[keyProtoType]; ok { 63 return handler(ctx, keyProto) 64 } 65 66 return nil, fmt.Errorf("no ProtoHandler registered for protobuf %q", keyProtoType) 67 }